Browse Source

Bug 1786: Hints for synchronization action icons on synchronization checklist window

+ Improving hints for synchronization checklist window statusbar

https://winscp.net/tracker/1786

Source commit: 8ce26c1628e4d3d68d9081a8be1dfc0d1e5b626f
Martin Prikryl 6 years ago
parent
commit
fe5e2931a0

+ 100 - 24
source/forms/SynchronizeChecklist.cpp

@@ -71,13 +71,14 @@ __fastcall TSynchronizeChecklistDialog::TSynchronizeChecklistDialog(
   FChangingItem = NULL;
   FChangingItemIgnore = false;
   FChangingItemMass = false;
-  FGeneralHint = StatusBar->Hint;
   FSynchronizing = false;
 
   SelectScaledImageList(ActionImages);
 
   FOrigListViewWindowProc = ListView->WindowProc;
   ListView->WindowProc = ListViewWindowProc;
+  FOrigStatusBarWindowProc = StatusBar->WindowProc;
+  StatusBar->WindowProc = StatusBarWindowProc;
 
   UpdateImages();
 
@@ -89,6 +90,7 @@ __fastcall TSynchronizeChecklistDialog::TSynchronizeChecklistDialog(
 //---------------------------------------------------------------------
 __fastcall TSynchronizeChecklistDialog::~TSynchronizeChecklistDialog()
 {
+  StatusBar->WindowProc = FOrigStatusBarWindowProc;
   ListView->WindowProc = FOrigListViewWindowProc;
 }
 //---------------------------------------------------------------------
@@ -496,9 +498,105 @@ void __fastcall TSynchronizeChecklistDialog::ListViewWindowProc(TMessage & Messa
           R.Left, ((R.Top + R.Bottom - ActionImages->Height) / 2), ILD_TRANSPARENT);
       }
     }
+
+    FOrigListViewWindowProc(Message);
+  }
+  else if (Message.Msg == CM_HINTSHOW)
+  {
+    ListViewHintShow(reinterpret_cast<TCMHintShow &>(Message));
+  }
+  else if (Message.Msg == WM_WANTS_SCREEN_TIPS)
+  {
+    Message.Result = 1;
+  }
+  else
+  {
+    FOrigListViewWindowProc(Message);
+  }
+}
+//---------------------------------------------------------------------------
+void __fastcall TSynchronizeChecklistDialog::ListViewHintShow(TCMHintShow & HintShow)
+{
+  TLVHitTestInfo HitTest;
+  HitTest.pt = HintShow.HintInfo->CursorPos;
+  int Index = ListView_SubItemHitTest(ListView->Handle, &HitTest);
+  if ((Index >= 0) && (HitTest.iSubItem == ImageColumnIndex))
+  {
+    TListItem * Item = ListView->Items->Item[Index];
+    const TSynchronizeChecklist::TItem * ChecklistItem = GetChecklistItem(Item);
+    int ActionHint = 0;
+    switch (int(GetChecklistItemAction(ChecklistItem)))
+    {
+      case TSynchronizeChecklist::saUploadNew:
+        ActionHint = SYNCHRONIZE_CHECKLIST_UPLOAD_NEW;
+        break;
+      case TSynchronizeChecklist::saDownloadNew:
+        ActionHint = SYNCHRONIZE_CHECKLIST_DOWNLOAD_NEW;
+        break;
+      case TSynchronizeChecklist::saUploadUpdate:
+        ActionHint = SYNCHRONIZE_CHECKLIST_UPLOAD_UPDATE;
+        break;
+      case TSynchronizeChecklist::saDownloadUpdate:
+        ActionHint = SYNCHRONIZE_CHECKLIST_DOWNLOAD_UPDATE;
+        break;
+      case TSynchronizeChecklist::saDeleteRemote:
+        ActionHint = SYNCHRONIZE_CHECKLIST_DELETE_REMOTE;
+        break;
+      case TSynchronizeChecklist::saDeleteLocal:
+        ActionHint = SYNCHRONIZE_CHECKLIST_DELETE_LOCAL;
+        break;
+    }
+    if (DebugAlwaysTrue(ActionHint != 0))
+    {
+      HintShow.HintInfo->HintStr = FORMAT(L"%s|%s", (LoadStr(ActionHint), LoadStr(SYNCHRONIZE_CHECKLIST_REVERSE)));
+      ListView_GetSubItemRect(ListView->Handle, Index, ImageColumnIndex, LVIR_BOUNDS, &HintShow.HintInfo->CursorRect);
+      HintShow.Result = 0;
+    }
   }
 
-  FOrigListViewWindowProc(Message);
+  FOrigListViewWindowProc(reinterpret_cast<TMessage &>(HintShow));
+}
+//---------------------------------------------------------------------------
+void __fastcall TSynchronizeChecklistDialog::StatusBarHintShow(TCMHintShow & HintShow)
+{
+  int IPanel = PanelAt(HintShow.HintInfo->CursorPos.x);
+
+  if (IPanel >= 0)
+  {
+    TStatusPanel * Panel = StatusBar->Panels->Items[IPanel];
+    HintShow.HintInfo->HintStr = FORMAT(L"%s|%s", (Panel->Text, StatusBar->Hint));
+
+    HintShow.HintInfo->CursorRect.Left = 0;
+    while (IPanel > 0)
+    {
+      IPanel--;
+      HintShow.HintInfo->CursorRect.Left += StatusBar->Panels->Items[IPanel]->Width;
+    }
+
+    HintShow.HintInfo->CursorRect.Top = 0;
+    HintShow.HintInfo->CursorRect.Bottom = StatusBar->ClientHeight;
+    HintShow.HintInfo->CursorRect.Right = HintShow.HintInfo->CursorRect.Left + Panel->Width;
+
+    HintShow.Result = 0;
+  }
+
+  FOrigListViewWindowProc(reinterpret_cast<TMessage &>(HintShow));
+}
+//---------------------------------------------------------------------------
+void __fastcall TSynchronizeChecklistDialog::StatusBarWindowProc(TMessage & Message)
+{
+  if (Message.Msg == WM_WANTS_SCREEN_TIPS)
+  {
+    Message.Result = 1;
+  }
+  else if (Message.Msg == CM_HINTSHOW)
+  {
+    StatusBarHintShow(reinterpret_cast<TCMHintShow &>(Message));
+  }
+  else
+  {
+    FOrigStatusBarWindowProc(Message);
+  }
 }
 //---------------------------------------------------------------------------
 void __fastcall TSynchronizeChecklistDialog::ListViewAdvancedCustomDrawSubItem(
@@ -615,28 +713,6 @@ int __fastcall TSynchronizeChecklistDialog::PanelAt(int X)
   return ((Result < StatusBar->Panels->Count - 1) ? Result : -1);
 }
 //---------------------------------------------------------------------------
-void __fastcall TSynchronizeChecklistDialog::StatusBarMouseMove(
-  TObject * /*Sender*/, TShiftState /*Shift*/, int X, int /*Y*/)
-{
-  UnicodeString Hint;
-  int IPanel = PanelAt(X);
-
-  if (IPanel >= 0)
-  {
-    Hint = StatusBar->Panels->Items[IPanel]->Text;
-    if (IPanel > 0)
-    {
-      Hint = FORMAT(L"%s\n%s", (Hint, FGeneralHint));
-    }
-  }
-
-  if (Hint != StatusBar->Hint)
-  {
-    Application->CancelHint();
-    StatusBar->Hint = Hint;
-  }
-}
-//---------------------------------------------------------------------------
 void __fastcall TSynchronizeChecklistDialog::ListViewChange(
   TObject * /*Sender*/, TListItem * Item, TItemChange Change)
 {

+ 2 - 1
source/forms/SynchronizeChecklist.dfm

@@ -1493,7 +1493,9 @@ object SynchronizeChecklistDialog: TSynchronizeChecklistDialog
     ReadOnly = True
     RowSelect = True
     ParentDoubleBuffered = False
+    ParentShowHint = False
     PopupMenu = ListViewPopupMenu
+    ShowHint = True
     TabOrder = 0
     ViewStyle = vsReport
     OnChange = ListViewChange
@@ -1603,7 +1605,6 @@ object SynchronizeChecklistDialog: TSynchronizeChecklistDialog
     ParentShowHint = False
     ShowHint = True
     OnMouseDown = StatusBarMouseDown
-    OnMouseMove = StatusBarMouseMove
     OnDrawPanel = StatusBarDrawPanel
     OnResize = StatusBarResize
   end

+ 4 - 3
source/forms/SynchronizeChecklist.h

@@ -72,8 +72,6 @@ __published:
   void __fastcall FormShow(TObject * Sender);
   void __fastcall StatusBarDrawPanel(TStatusBar *StatusBar,
           TStatusPanel *Panel, const TRect &Rect);
-  void __fastcall StatusBarMouseMove(TObject *Sender, TShiftState Shift,
-          int X, int Y);
   void __fastcall ListViewChange(TObject *Sender, TListItem *Item,
           TItemChange Change);
   void __fastcall ListViewChanging(TObject *Sender, TListItem *Item,
@@ -128,6 +126,7 @@ protected:
   UnicodeString FLocalDirectory;
   UnicodeString FRemoteDirectory;
   TWndMethod FOrigListViewWindowProc;
+  TWndMethod FOrigStatusBarWindowProc;
   int FTotals[1 + TSynchronizeChecklist::ActionCount];
   int FChecked[1 + TSynchronizeChecklist::ActionCount];
   __int64 FCheckedSize[1 + TSynchronizeChecklist::ActionCount];
@@ -135,7 +134,6 @@ protected:
   bool FChangingItemChecked;
   bool FChangingItemIgnore;
   bool FChangingItemMass;
-  UnicodeString FGeneralHint;
   TCustomCommandMenuEvent FOnCustomCommandMenu;
   TSynchronizeChecklistCalculateSize FOnSynchronizeChecklistCalculateSize;
   TSynchronizeMoveEvent FOnSynchronizeMove;
@@ -154,6 +152,7 @@ protected:
   void __fastcall LoadItem(TListItem * Item);
   void __fastcall LoadList();
   void __fastcall ListViewWindowProc(TMessage & Message);
+  void __fastcall StatusBarWindowProc(TMessage & Message);
   int __fastcall PanelAt(int X);
   void __fastcall CheckAll(bool Check);
   void __fastcall Check(bool Check);
@@ -181,6 +180,8 @@ protected:
   void __fastcall CheckDirectory(bool Check);
   void __fastcall DoBrowse(TOperationSide Side);
   static int __fastcall CompareNumber(__int64 Value1, __int64 Value2);
+  void __fastcall ListViewHintShow(TCMHintShow & HintShow);
+  void __fastcall StatusBarHintShow(TCMHintShow & HintShow);
 };
 //----------------------------------------------------------------------------
 #endif

+ 7 - 0
source/resource/TextsWin.h

@@ -625,6 +625,13 @@
 #define SITE_RAW_ADD            6024
 #define SITE_RAW_ADD_CAPTION    6025
 #define SITE_RAW_ADD_LABEL      6026
+#define SYNCHRONIZE_CHECKLIST_UPLOAD_NEW 6027
+#define SYNCHRONIZE_CHECKLIST_DOWNLOAD_NEW 6028
+#define SYNCHRONIZE_CHECKLIST_UPLOAD_UPDATE 6029
+#define SYNCHRONIZE_CHECKLIST_DOWNLOAD_UPDATE 6030
+#define SYNCHRONIZE_CHECKLIST_DELETE_REMOTE 6031
+#define SYNCHRONIZE_CHECKLIST_DELETE_LOCAL 6032
+#define SYNCHRONIZE_CHECKLIST_REVERSE 6033
 
 // 2xxx is reserved for TextsFileZilla.h
 

+ 7 - 0
source/resource/TextsWin1.rc

@@ -630,6 +630,13 @@ BEGIN
         SITE_RAW_ADD, "&Add..."
         SITE_RAW_ADD_CAPTION, "Add Raw Site Setting"
         SITE_RAW_ADD_LABEL, "&Site Setting:"
+        SYNCHRONIZE_CHECKLIST_UPLOAD_NEW, "Upload new local file"
+        SYNCHRONIZE_CHECKLIST_DOWNLOAD_NEW, "Download new remote file"
+        SYNCHRONIZE_CHECKLIST_UPLOAD_UPDATE, "Upload updated local file"
+        SYNCHRONIZE_CHECKLIST_DOWNLOAD_UPDATE, "Download updated remote file"
+        SYNCHRONIZE_CHECKLIST_DELETE_REMOTE, "Delete obsolete remote file"
+        SYNCHRONIZE_CHECKLIST_DELETE_LOCAL, "Delete obsolete local file"
+        SYNCHRONIZE_CHECKLIST_REVERSE, "Click to reverse"
 
         WIN_VARIABLE_STRINGS, "WIN_VARIABLE"
         WINSCP_COPYRIGHT, "Copyright © 2000-2019 Martin Prikryl"

+ 1 - 0
source/windows/CustomWinConfiguration.h

@@ -14,6 +14,7 @@
 #define WM_CAN_DISPLAY_UPDATES (WM_WINSCP_USER + 10)
 // CM_DPICHANGED + 10 (packages/my/PasTools.pas)
 #define WM_WANTS_MOUSEWHEEL_INACTIVE (WM_WINSCP_USER + 11)
+#define WM_WANTS_SCREEN_TIPS (WM_WINSCP_USER + 12)
 //---------------------------------------------------------------------------
 #define C(Property) (Property != rhc.Property) ||
 struct TSynchronizeChecklistConfiguration

+ 2 - 1
source/windows/GUITools.cpp

@@ -1791,7 +1791,8 @@ bool __fastcall TScreenTipHintWindow::UseBoldShortHint(TControl * HintControl)
 {
   return
     (dynamic_cast<TTBCustomDockableWindow *>(HintControl) != NULL) ||
-    (dynamic_cast<TTBPopupWindow *>(HintControl) != NULL);
+    (dynamic_cast<TTBPopupWindow *>(HintControl) != NULL) ||
+    (HintControl->Perform(WM_WANTS_SCREEN_TIPS, 0, 0) == 1);
 }
 //---------------------------------------------------------------------------
 bool __fastcall TScreenTipHintWindow::IsPathLabel(TControl * HintControl)