mirror of
https://github.com/winscp/winscp.git
synced 2026-10-24 02:28:55 +03:00
Issue 912 – Thumbnail view in file panel (local)
https://winscp.net/tracker/912 Source commit: 4326a2efd8333867e5697a63f320f4cdf919708b
This commit is contained in:
@@ -159,6 +159,7 @@ __published:
|
||||
__property MultiSelect;
|
||||
__property TNotifyEvent OnDisplayProperties = { read = FOnDisplayProperties, write = FOnDisplayProperties };
|
||||
__property ReadOnly;
|
||||
__property DirViewStyle;
|
||||
__property TNotifyEvent OnRead = { read = FOnRead, write = FOnRead };
|
||||
|
||||
// The only way to make Items stored automatically and survive handle recreation.
|
||||
|
||||
@@ -9327,6 +9327,13 @@ TColor __fastcall TCustomScpExplorerForm::DisabledPanelColor()
|
||||
return Result;
|
||||
}
|
||||
//---------------------------------------------------------------------------
|
||||
void TCustomScpExplorerForm::UpdatePanelControls(TCustomDirView * ADirView, TCustomDriveView * ADriveView)
|
||||
{
|
||||
bool UseDarkTheme = WinConfiguration->UseDarkTheme();
|
||||
ADirView->DarkMode = UseDarkTheme;
|
||||
ADriveView->DarkMode = UseDarkTheme;
|
||||
}
|
||||
//---------------------------------------------------------------------------
|
||||
void __fastcall TCustomScpExplorerForm::UpdateControls()
|
||||
{
|
||||
if (!FSessionChanging)
|
||||
@@ -9371,9 +9378,8 @@ void __fastcall TCustomScpExplorerForm::UpdateControls()
|
||||
QueueFileList->Font->Color = QueueView3->Font->Color;
|
||||
QueueLabelUpdateStatus();
|
||||
|
||||
UpdatePanelControls(RemoteDirView, RemoteDriveView);
|
||||
bool UseDarkTheme = WinConfiguration->UseDarkTheme();
|
||||
RemoteDirView->DarkMode = UseDarkTheme;
|
||||
RemoteDriveView->DarkMode = RemoteDirView->DarkMode;
|
||||
if (FImmersiveDarkMode != UseDarkTheme)
|
||||
{
|
||||
UpdateDarkMode();
|
||||
@@ -11671,11 +11677,11 @@ TListItem * __fastcall TCustomScpExplorerForm::SearchFile(const UnicodeString &
|
||||
Matches = ContainsTextSemiCaseSensitive(ADirView->ItemFileName(Item), Text);
|
||||
break;
|
||||
case isAll:
|
||||
int ColCount = (ADirView->ViewStyle == vsReport) ? ADirView->ColProperties->Count : 1;
|
||||
int ColCount = (ADirView->DirViewStyle == dvsReport) ? ADirView->ColProperties->Count : 1;
|
||||
int Index = 0;
|
||||
while ((Index < ColCount) && !Matches)
|
||||
{
|
||||
bool Visible = (ADirView->ViewStyle == vsReport) ? ADirView->ColProperties->Visible[Index] : true;
|
||||
bool Visible = (ADirView->DirViewStyle == dvsReport) ? ADirView->ColProperties->Visible[Index] : true;
|
||||
if (Visible)
|
||||
{
|
||||
Matches = ContainsTextSemiCaseSensitive(ADirView->GetColumnText(Item, Index), Text);
|
||||
|
||||
@@ -86,7 +86,6 @@ object CustomScpExplorerForm: TCustomScpExplorerForm
|
||||
ParentDoubleBuffered = False
|
||||
PopupMenu = NonVisualDataModule.RemoteDirViewPopup
|
||||
TabOrder = 0
|
||||
ViewStyle = vsReport
|
||||
OnColumnRightClick = DirViewColumnRightClick
|
||||
OnEditing = DirViewEditing
|
||||
OnEnter = RemoteDirViewEnter
|
||||
@@ -118,6 +117,7 @@ object CustomScpExplorerForm: TCustomScpExplorerForm
|
||||
OnContextPopup = RemoteDirViewContextPopup
|
||||
OnHistoryChange = DirViewHistoryChange
|
||||
OnDisplayProperties = RemoteDirViewDisplayProperties
|
||||
DirViewStyle = dvsReport
|
||||
OnRead = RemoteDirViewRead
|
||||
end
|
||||
object ReconnectToolbar: TTBXToolbar
|
||||
|
||||
@@ -592,7 +592,7 @@ protected:
|
||||
TTBXStatusBar * StatusBar, const TStatusFileInfo & FileInfo);
|
||||
void __fastcall FileStatusBarPanelClick(TTBXStatusPanel * Panel, TOperationSide Side);
|
||||
virtual void __fastcall DoDirViewLoaded(TCustomDirView * Sender);
|
||||
virtual void __fastcall UpdateControls();
|
||||
virtual void UpdatePanelControls(TCustomDirView * ADirView, TCustomDriveView * ADriveView);
|
||||
void __fastcall UpdateTransferList();
|
||||
void __fastcall UpdateTransferLabel();
|
||||
void __fastcall StartUpdates();
|
||||
@@ -922,6 +922,7 @@ public:
|
||||
void IncrementalSearchStart();
|
||||
virtual void * SaveFocus();
|
||||
virtual void RestoreFocus(void * Focus);
|
||||
virtual void __fastcall UpdateControls();
|
||||
|
||||
__property bool ComponentVisible[Byte Component] = { read = GetComponentVisible, write = SetComponentVisible };
|
||||
__property bool EnableFocusedOperation[TOperationSide Side] = { read = GetEnableFocusedOperation, index = 0 };
|
||||
|
||||
@@ -266,14 +266,17 @@ void __fastcall TNonVisualDataModule::ExplorerActionsUpdate(
|
||||
UPD(RemoteSelectAllAction2, DirView(osRemote)->FilesCount)
|
||||
|
||||
//style
|
||||
UPDACT(CurrentCycleStyleAction,
|
||||
CurrentCycleStyleAction->ImageIndex = 8 + (DirView(osCurrent)->ViewStyle + 1) % 4)
|
||||
#define STYLEACTION(Style) UPDACT(Current ## Style ## Action, \
|
||||
Current ## Style ## Action->Checked = (DirView(osCurrent)->ViewStyle == vs ## Style))
|
||||
STYLEACTION(Icon)
|
||||
STYLEACTION(SmallIcon)
|
||||
STYLEACTION(List)
|
||||
STYLEACTION(Report)
|
||||
UPDACT(RemoteCycleStyleAction,
|
||||
RemoteCycleStyleAction->ImageIndex = 8 + (DirView(osRemote)->DirViewStyle + 1) % 4)
|
||||
#define STYLEACTION(SIDE, STYLE) UPDACT(SIDE ## STYLE ## Action, \
|
||||
SIDE ## STYLE ## Action->Checked = (DirView(os ## SIDE)->DirViewStyle == dvs ## STYLE))
|
||||
STYLEACTION(Remote, Icon)
|
||||
STYLEACTION(Remote, SmallIcon)
|
||||
STYLEACTION(Remote, List)
|
||||
STYLEACTION(Remote, Report)
|
||||
STYLEACTION(Remote, Thumbnail)
|
||||
STYLEACTION(Local, Report)
|
||||
STYLEACTION(Local, Thumbnail)
|
||||
#undef STYLEACTION
|
||||
|
||||
// REMOTE+LOCAL
|
||||
@@ -627,16 +630,20 @@ void __fastcall TNonVisualDataModule::ExplorerActionsExecute(
|
||||
EXE(PasteAction3, ScpExplorer->PasteFromClipBoard())
|
||||
|
||||
// style
|
||||
EXE(CurrentCycleStyleAction,
|
||||
if (DirView(osCurrent)->ViewStyle == vsReport) DirView(osCurrent)->ViewStyle = vsIcon;
|
||||
else DirView(osCurrent)->ViewStyle = (TViewStyle)(DirView(osCurrent)->ViewStyle + 1);
|
||||
EXE(RemoteCycleStyleAction,
|
||||
if (DirView(osRemote)->DirViewStyle == dvsReport) DirView(osRemote)->DirViewStyle = dvsIcon;
|
||||
else DirView(osRemote)->DirViewStyle = (TDirViewStyle)(DirView(osRemote)->DirViewStyle + 1);
|
||||
ScpExplorer->UpdateControls();
|
||||
)
|
||||
#define STYLEACTION(Style) EXE(Current ## Style ## Action, \
|
||||
DirView(osCurrent)->ViewStyle = vs ## Style)
|
||||
STYLEACTION(Icon)
|
||||
STYLEACTION(SmallIcon)
|
||||
STYLEACTION(List)
|
||||
STYLEACTION(Report)
|
||||
#define STYLEACTION(SIDE, STYLE) EXE(SIDE ## STYLE ## Action, \
|
||||
DirView(os ## SIDE)->DirViewStyle = dvs ## STYLE; ScpExplorer->UpdateControls())
|
||||
STYLEACTION(Remote, Icon)
|
||||
STYLEACTION(Remote, SmallIcon)
|
||||
STYLEACTION(Remote, List)
|
||||
STYLEACTION(Remote, Report)
|
||||
STYLEACTION(Remote, Thumbnail)
|
||||
STYLEACTION(Local, Report)
|
||||
STYLEACTION(Local, Thumbnail)
|
||||
#undef STYLEACTION
|
||||
|
||||
#define PANEL_ACTIONS(SIDE) \
|
||||
|
||||
@@ -343,40 +343,40 @@ object NonVisualDataModule: TNonVisualDataModule
|
||||
ImageIndex = 6
|
||||
ShortCut = 32805
|
||||
end
|
||||
object CurrentCycleStyleAction: TAction
|
||||
Tag = 7
|
||||
object RemoteCycleStyleAction: TAction
|
||||
Tag = 15
|
||||
Category = 'Style'
|
||||
Caption = 'View'
|
||||
HelpKeyword = 'ui_file_panel#view_style'
|
||||
Hint = 'View|Cycle thru directory view styles'
|
||||
ImageIndex = 8
|
||||
end
|
||||
object CurrentIconAction: TAction
|
||||
Tag = 7
|
||||
object RemoteIconAction: TAction
|
||||
Tag = 15
|
||||
Category = 'Style'
|
||||
Caption = '&Large Icons'
|
||||
HelpKeyword = 'ui_file_panel#view_style'
|
||||
Hint = 'Large Icons|View large icons'
|
||||
ImageIndex = 8
|
||||
end
|
||||
object CurrentSmallIconAction: TAction
|
||||
Tag = 7
|
||||
object RemoteSmallIconAction: TAction
|
||||
Tag = 15
|
||||
Category = 'Style'
|
||||
Caption = '&Small Icons'
|
||||
HelpKeyword = 'ui_file_panel#view_style'
|
||||
Hint = 'Small Icons|View small icons'
|
||||
ImageIndex = 9
|
||||
end
|
||||
object CurrentListAction: TAction
|
||||
Tag = 7
|
||||
object RemoteListAction: TAction
|
||||
Tag = 15
|
||||
Category = 'Style'
|
||||
Caption = 'Lis&t'
|
||||
HelpKeyword = 'ui_file_panel#view_style'
|
||||
Hint = 'List|View list'
|
||||
ImageIndex = 10
|
||||
end
|
||||
object CurrentReportAction: TAction
|
||||
Tag = 7
|
||||
object RemoteReportAction: TAction
|
||||
Tag = 15
|
||||
Category = 'Style'
|
||||
Caption = '&Details'
|
||||
HelpKeyword = 'ui_file_panel#view_style'
|
||||
@@ -2465,6 +2465,28 @@ object NonVisualDataModule: TNonVisualDataModule
|
||||
Caption = 'IncrementalSearchStartAction'
|
||||
ShortCut = 16454
|
||||
end
|
||||
object RemoteThumbnailAction: TAction
|
||||
Tag = 15
|
||||
Category = 'Style'
|
||||
Caption = '&Thumbnails'
|
||||
HelpKeyword = 'ui_file_panel#view_style'
|
||||
Hint = 'Thumbnails|View thumbnails'
|
||||
end
|
||||
object LocalReportAction: TAction
|
||||
Tag = 15
|
||||
Category = 'Style'
|
||||
Caption = '&Details'
|
||||
HelpKeyword = 'ui_file_panel#view_style'
|
||||
Hint = 'Details|View details'
|
||||
ImageIndex = 11
|
||||
end
|
||||
object LocalThumbnailAction: TAction
|
||||
Tag = 15
|
||||
Category = 'Style'
|
||||
Caption = '&Thumbnails'
|
||||
HelpKeyword = 'ui_file_panel#view_style'
|
||||
Hint = 'Thumbnails|View thumbnails'
|
||||
end
|
||||
end
|
||||
object ExplorerBarPopup: TTBXPopupMenu
|
||||
Images = GlyphsModule.ExplorerImages
|
||||
|
||||
@@ -81,11 +81,11 @@ __published: // IDE-managed Components
|
||||
TAction *CurrentRenameAction;
|
||||
TAction *CurrentDeleteAction;
|
||||
TAction *CurrentCreateDirAction;
|
||||
TAction *CurrentCycleStyleAction;
|
||||
TAction *CurrentIconAction;
|
||||
TAction *CurrentSmallIconAction;
|
||||
TAction *CurrentReportAction;
|
||||
TAction *CurrentListAction;
|
||||
TAction *RemoteCycleStyleAction;
|
||||
TAction *RemoteIconAction;
|
||||
TAction *RemoteSmallIconAction;
|
||||
TAction *RemoteReportAction;
|
||||
TAction *RemoteListAction;
|
||||
TAction *CurrentDeleteFocusedAction;
|
||||
TAction *CurrentPropertiesFocusedAction;
|
||||
TAction *CurrentPropertiesAction;
|
||||
@@ -711,6 +711,9 @@ __published: // IDE-managed Components
|
||||
TTBXSeparatorItem *TBXSeparatorItem23;
|
||||
TTBXItem *TBXItem116;
|
||||
TAction *IncrementalSearchStartAction;
|
||||
TAction *RemoteThumbnailAction;
|
||||
TAction *LocalReportAction;
|
||||
TAction *LocalThumbnailAction;
|
||||
void __fastcall ExplorerActionsUpdate(TBasicAction *Action, bool &Handled);
|
||||
void __fastcall ExplorerActionsExecute(TBasicAction *Action, bool &Handled);
|
||||
void __fastcall SessionIdleTimerTimer(TObject *Sender);
|
||||
|
||||
@@ -165,6 +165,7 @@ void __fastcall TScpCommanderForm::RestorePanelParams(
|
||||
const TScpCommanderPanelConfiguration & PanelConfiguration)
|
||||
{
|
||||
DirView->ColProperties->ParamsStr = PanelConfiguration.DirViewParams;
|
||||
DirView->DirViewStyle = (TDirViewStyle)PanelConfiguration.ViewStyle;
|
||||
StatusBar->Visible = PanelConfiguration.StatusBar;
|
||||
DriveControl->Visible = PanelConfiguration.DriveView;
|
||||
if (DriveControl->Align == alTop)
|
||||
@@ -194,6 +195,7 @@ void __fastcall TScpCommanderForm::RestoreParams()
|
||||
RestorePanelParams(LocalDirView, LocalDriveView, LocalStatusBar, WinConfiguration->ScpCommander.LocalPanel);
|
||||
RestorePanelParams(RemoteDirView, RemoteDrivePanel, RemoteStatusBar, WinConfiguration->ScpCommander.RemotePanel);
|
||||
OtherLocalDirView->ColProperties->ParamsStr = WinConfiguration->ScpCommander.OtherLocalPanelDirViewParams;
|
||||
OtherLocalDirView->DirViewStyle = (TDirViewStyle)WinConfiguration->ScpCommander.OtherLocalPanelViewStyle;
|
||||
FPanelsRestored = true;
|
||||
|
||||
// just to make sure
|
||||
@@ -207,6 +209,7 @@ void __fastcall TScpCommanderForm::StorePanelParams(
|
||||
TScpCommanderPanelConfiguration & PanelConfiguration)
|
||||
{
|
||||
PanelConfiguration.DirViewParams = DirView->ColProperties->ParamsStr;
|
||||
PanelConfiguration.ViewStyle = DirView->DirViewStyle;
|
||||
PanelConfiguration.StatusBar = StatusBar->Visible;
|
||||
PanelConfiguration.DriveView = DriveControl->Visible;
|
||||
if (DriveControl->Align == alTop)
|
||||
@@ -242,6 +245,7 @@ void __fastcall TScpCommanderForm::StoreParams()
|
||||
StorePanelParams(LocalDirView, LocalDriveView, LocalStatusBar, CommanderConfiguration.LocalPanel);
|
||||
StorePanelParams(RemoteDirView, RemoteDrivePanel, RemoteStatusBar, CommanderConfiguration.RemotePanel);
|
||||
CommanderConfiguration.OtherLocalPanelDirViewParams = OtherLocalDirView->ColProperties->ParamsStr;
|
||||
CommanderConfiguration.OtherLocalPanelViewStyle = reinterpret_cast<TDirViewStyle>(OtherLocalDirView->DirViewStyle);
|
||||
|
||||
CommanderConfiguration.LocalPanel.LastPath = LocalDirView->Path;
|
||||
CommanderConfiguration.OtherLocalPanelLastPath = OtherLocalDirView->Path;
|
||||
@@ -1024,6 +1028,12 @@ void __fastcall TScpCommanderForm::SetToolbar2ItemAction(TTBXItem * Item, TBasic
|
||||
}
|
||||
}
|
||||
//---------------------------------------------------------------------------
|
||||
void TScpCommanderForm::UpdatePanelControls(TCustomDirView * ADirView, TCustomDriveView * ADriveView)
|
||||
{
|
||||
TCustomScpExplorerForm::UpdatePanelControls(ADirView, ADriveView);
|
||||
ADirView->AddParentDir = (ADirView->DirViewStyle == dvsReport);
|
||||
}
|
||||
//---------------------------------------------------------------------------
|
||||
void __fastcall TScpCommanderForm::UpdateControls()
|
||||
{
|
||||
// Before TCustomScpExplorerForm disables them (when disconnecting)
|
||||
@@ -1057,10 +1067,8 @@ void __fastcall TScpCommanderForm::UpdateControls()
|
||||
// command line combo width needs to be updated as caption width has probably changed
|
||||
ToolBarResize(CommandLineToolbar);
|
||||
}
|
||||
LocalDirView->DarkMode = WinConfiguration->UseDarkTheme();
|
||||
LocalDriveView->DarkMode = LocalDirView->DarkMode;
|
||||
OtherLocalDirView->DarkMode = LocalDirView->DarkMode;
|
||||
OtherLocalDriveView->DarkMode = LocalDirView->DarkMode;
|
||||
UpdatePanelControls(LocalDirView, LocalDriveView);
|
||||
UpdatePanelControls(OtherLocalDirView, OtherLocalDriveView);
|
||||
LocalDirView->Color = PanelColor();
|
||||
LocalDriveView->Color = LocalDirView->Color;
|
||||
OtherLocalDirView->Color = LocalDirView->Color;
|
||||
@@ -1070,6 +1078,9 @@ void __fastcall TScpCommanderForm::UpdateControls()
|
||||
OtherLocalDirView->Font->Color = LocalDirView->Font->Color;
|
||||
OtherLocalDriveView->Font->Color = LocalDirView->Font->Color;
|
||||
|
||||
LocalColumnsSubmenuItem->Enabled = (DirView(osLocal)->DirViewStyle == dvsReport);
|
||||
RemoteColumnsSubmenuItem->Enabled = (DirView(osRemote)->DirViewStyle == dvsReport);
|
||||
|
||||
if (IsLocalBrowserMode())
|
||||
{
|
||||
CurrentCopyItem->Visible = false;
|
||||
|
||||
@@ -93,6 +93,19 @@ inherited ScpCommanderForm: TScpCommanderForm
|
||||
end
|
||||
object TBXSeparatorItem4: TTBXSeparatorItem
|
||||
end
|
||||
object TBXSubmenuItem17: TTBXSubmenuItem
|
||||
Caption = '&View'
|
||||
HelpKeyword = 'ui_file_panel#view_style'
|
||||
Hint = 'Change directory view style'
|
||||
object TBXItem270: TTBXItem
|
||||
Action = NonVisualDataModule.LocalReportAction
|
||||
end
|
||||
object TBXSeparatorItem76: TTBXSeparatorItem
|
||||
end
|
||||
object TBXItem271: TTBXItem
|
||||
Action = NonVisualDataModule.LocalThumbnailAction
|
||||
end
|
||||
end
|
||||
object TBXSubmenuItem3: TTBXSubmenuItem
|
||||
Caption = '&Sort'
|
||||
HelpKeyword = 'ui_file_panel#sorting_files'
|
||||
@@ -1195,7 +1208,6 @@ inherited ScpCommanderForm: TScpCommanderForm
|
||||
ParentDoubleBuffered = False
|
||||
PopupMenu = NonVisualDataModule.RemoteDirViewPopup
|
||||
TabOrder = 1
|
||||
ViewStyle = vsReport
|
||||
OnColumnRightClick = DirViewColumnRightClick
|
||||
OnEditing = DirViewEditing
|
||||
OnEnter = OtherLocalDirViewEnter
|
||||
@@ -1224,6 +1236,7 @@ inherited ScpCommanderForm: TScpCommanderForm
|
||||
OnPathChange = OtherLocalDirViewPathChange
|
||||
OnBusy = DirViewBusy
|
||||
OnChangeFocus = DirViewChangeFocus
|
||||
DirViewStyle = dvsReport
|
||||
end
|
||||
end
|
||||
inherited RemoteDrivePanel: TPanel
|
||||
@@ -1600,7 +1613,6 @@ inherited ScpCommanderForm: TScpCommanderForm
|
||||
ParentDoubleBuffered = False
|
||||
PopupMenu = NonVisualDataModule.LocalDirViewPopup
|
||||
TabOrder = 1
|
||||
ViewStyle = vsReport
|
||||
OnColumnRightClick = DirViewColumnRightClick
|
||||
OnEditing = DirViewEditing
|
||||
OnEnter = LocalDirViewEnter
|
||||
@@ -1630,6 +1642,7 @@ inherited ScpCommanderForm: TScpCommanderForm
|
||||
OnPathChange = LocalDirViewPathChange
|
||||
OnBusy = DirViewBusy
|
||||
OnChangeFocus = DirViewChangeFocus
|
||||
DirViewStyle = dvsReport
|
||||
end
|
||||
object LocalTopDock: TTBXDock
|
||||
Left = 0
|
||||
@@ -1686,6 +1699,19 @@ inherited ScpCommanderForm: TScpCommanderForm
|
||||
object TBXItem164: TTBXItem
|
||||
Action = NonVisualDataModule.LocalTreeAction
|
||||
end
|
||||
object TBXSubmenuItem4: TTBXSubmenuItem
|
||||
Caption = 'Change directory view style'
|
||||
ImageIndex = 11
|
||||
Options = [tboDropdownArrow]
|
||||
object TBXItem269: TTBXItem
|
||||
Action = NonVisualDataModule.LocalReportAction
|
||||
end
|
||||
object TBXSeparatorItem75: TTBXSeparatorItem
|
||||
end
|
||||
object TBXItem268: TTBXItem
|
||||
Action = NonVisualDataModule.LocalThumbnailAction
|
||||
end
|
||||
end
|
||||
end
|
||||
object LocalPathToolbar: TTBXToolbar
|
||||
Left = 0
|
||||
@@ -1805,7 +1831,7 @@ inherited ScpCommanderForm: TScpCommanderForm
|
||||
end
|
||||
end
|
||||
object LocalSelectionToolbar: TTBXToolbar
|
||||
Left = 217
|
||||
Left = 244
|
||||
Top = 27
|
||||
Caption = 'Local Selection'
|
||||
DockPos = 217
|
||||
|
||||
@@ -468,6 +468,14 @@ __published:
|
||||
TTBXItem *TBXItem266;
|
||||
TTBXSeparatorItem *TBXSeparatorItem74;
|
||||
TTBXItem *TBXItem267;
|
||||
TTBXSubmenuItem *TBXSubmenuItem4;
|
||||
TTBXItem *TBXItem269;
|
||||
TTBXSeparatorItem *TBXSeparatorItem75;
|
||||
TTBXItem *TBXItem268;
|
||||
TTBXSubmenuItem *TBXSubmenuItem17;
|
||||
TTBXItem *TBXItem270;
|
||||
TTBXSeparatorItem *TBXSeparatorItem76;
|
||||
TTBXItem *TBXItem271;
|
||||
void __fastcall SplitterMoved(TObject *Sender);
|
||||
void __fastcall SplitterCanResize(TObject *Sender, int &NewSize,
|
||||
bool &Accept);
|
||||
@@ -592,7 +600,7 @@ protected:
|
||||
virtual void __fastcall ConfigurationChanged();
|
||||
virtual bool __fastcall GetHasDirView(TOperationSide Side);
|
||||
virtual TCustomDirView * GetCurrentLocalBrowser();
|
||||
virtual void __fastcall UpdateControls();
|
||||
virtual void UpdatePanelControls(TCustomDirView * ADirView, TCustomDriveView * ADriveView);
|
||||
virtual void __fastcall FileOperationProgress(
|
||||
TFileOperationProgressType & ProgressData);
|
||||
virtual void __fastcall DoOpenDirectoryDialog(TOpenDirectoryMode Mode,
|
||||
@@ -695,6 +703,7 @@ public:
|
||||
virtual void ResetLayoutColumns(TOperationSide Side);
|
||||
virtual void * SaveFocus();
|
||||
virtual void RestoreFocus(void * Focus);
|
||||
virtual void __fastcall UpdateControls();
|
||||
|
||||
__property double LeftPanelWidth = { read = GetLeftPanelWidth, write = SetLeftPanelWidth };
|
||||
};
|
||||
|
||||
@@ -86,7 +86,7 @@ void __fastcall TScpExplorerForm::RestoreParams()
|
||||
bool HadHandleAllocated = RemoteDirView->HandleAllocated();
|
||||
RemoteDirView->UnixColProperties->ParamsStr = WinConfiguration->ScpExplorer.DirViewParams;
|
||||
RemoteDirView->UnixColProperties->ExtVisible = false; // just to make sure
|
||||
RemoteDirView->ViewStyle = (TViewStyle)WinConfiguration->ScpExplorer.ViewStyle;
|
||||
RemoteDirView->DirViewStyle = (TDirViewStyle)WinConfiguration->ScpExplorer.ViewStyle;
|
||||
if (HadHandleAllocated)
|
||||
{
|
||||
// This is here to make our persistence checks in VerifyControl pass,
|
||||
@@ -121,7 +121,7 @@ void __fastcall TScpExplorerForm::StoreParams()
|
||||
|
||||
WinConfiguration->ScpExplorer.WindowParams = StoreForm(this);
|
||||
WinConfiguration->ScpExplorer.DirViewParams = RemoteDirView->UnixColProperties->ParamsStr;
|
||||
WinConfiguration->ScpExplorer.ViewStyle = RemoteDirView->ViewStyle;
|
||||
WinConfiguration->ScpExplorer.ViewStyle = RemoteDirView->DirViewStyle;
|
||||
WinConfiguration->ScpExplorer.DriveView = RemoteDrivePanel->Visible;
|
||||
WinConfiguration->ScpExplorer.DriveViewWidth = RemoteDrivePanel->Width;
|
||||
WinConfiguration->ScpExplorer.DriveViewWidthPixelsPerInch = GetControlPixelsPerInch(this);
|
||||
@@ -444,5 +444,5 @@ void __fastcall TScpExplorerForm::UpdateControls()
|
||||
ActiveControl = RemoteDirView;
|
||||
}
|
||||
|
||||
ColumndsSubmenuItem->Enabled = (RemoteDirView->ViewStyle == vsReport);
|
||||
ColumndsSubmenuItem->Enabled = (RemoteDirView->DirViewStyle == dvsReport);
|
||||
}
|
||||
|
||||
@@ -460,16 +460,16 @@ inherited ScpExplorerForm: TScpExplorerForm
|
||||
object TBXSeparatorItem3: TTBXSeparatorItem
|
||||
end
|
||||
object TBXItem16: TTBXItem
|
||||
Action = NonVisualDataModule.CurrentIconAction
|
||||
Action = NonVisualDataModule.RemoteIconAction
|
||||
end
|
||||
object TBXItem17: TTBXItem
|
||||
Action = NonVisualDataModule.CurrentSmallIconAction
|
||||
Action = NonVisualDataModule.RemoteSmallIconAction
|
||||
end
|
||||
object TBXItem18: TTBXItem
|
||||
Action = NonVisualDataModule.CurrentListAction
|
||||
Action = NonVisualDataModule.RemoteListAction
|
||||
end
|
||||
object TBXItem19: TTBXItem
|
||||
Action = NonVisualDataModule.CurrentReportAction
|
||||
Action = NonVisualDataModule.RemoteReportAction
|
||||
end
|
||||
object TBXSeparatorItem4: TTBXSeparatorItem
|
||||
end
|
||||
@@ -833,19 +833,19 @@ inherited ScpExplorerForm: TScpExplorerForm
|
||||
object TBXSeparatorItem36: TTBXSeparatorItem
|
||||
end
|
||||
object TBXSubmenuItem3: TTBXSubmenuItem
|
||||
Action = NonVisualDataModule.CurrentCycleStyleAction
|
||||
Action = NonVisualDataModule.RemoteCycleStyleAction
|
||||
DropdownCombo = True
|
||||
object TBXItem72: TTBXItem
|
||||
Action = NonVisualDataModule.CurrentIconAction
|
||||
Action = NonVisualDataModule.RemoteIconAction
|
||||
end
|
||||
object TBXItem73: TTBXItem
|
||||
Action = NonVisualDataModule.CurrentSmallIconAction
|
||||
Action = NonVisualDataModule.RemoteSmallIconAction
|
||||
end
|
||||
object TBXItem74: TTBXItem
|
||||
Action = NonVisualDataModule.CurrentListAction
|
||||
Action = NonVisualDataModule.RemoteListAction
|
||||
end
|
||||
object TBXItem75: TTBXItem
|
||||
Action = NonVisualDataModule.CurrentReportAction
|
||||
Action = NonVisualDataModule.RemoteReportAction
|
||||
end
|
||||
end
|
||||
object TBXSubmenuItem24: TTBXSubmenuItem
|
||||
|
||||
@@ -373,7 +373,6 @@ protected:
|
||||
virtual void __fastcall ToolbarItemResize(TTBXCustomDropDownItem * Item, int Width);
|
||||
virtual bool __fastcall UpdateToolbarDisplayMode();
|
||||
virtual void __fastcall UpdateImages();
|
||||
virtual void __fastcall UpdateControls();
|
||||
|
||||
public:
|
||||
__fastcall TScpExplorerForm(TComponent* Owner);
|
||||
@@ -386,6 +385,7 @@ public:
|
||||
virtual UnicodeString __fastcall DefaultDownloadTargetDirectory();
|
||||
virtual bool SupportedSession(TSessionData * SessionData);
|
||||
virtual void ResetLayoutColumns(TOperationSide Side);
|
||||
virtual void __fastcall UpdateControls();
|
||||
};
|
||||
//---------------------------------------------------------------------------
|
||||
#endif
|
||||
|
||||
@@ -17,6 +17,7 @@ uses
|
||||
const
|
||||
clDefaultItemColor = -(COLOR_ENDCOLORS + 1);
|
||||
WM_USER_RENAME = WM_USER + 57;
|
||||
WM_USER_INVALIDATEITEM = WM_USER + $2000 + 16;
|
||||
oiNoOverlay = $00;
|
||||
oiDirUp = $01;
|
||||
oiLink = $02;
|
||||
@@ -88,6 +89,8 @@ type
|
||||
TDVHistoryGoEvent = procedure(Sender: TCustomDirView; Index: Integer; var Cancel: Boolean) of object;
|
||||
TCompareCriteria = (ccTime, ccSize);
|
||||
TCompareCriterias = set of TCompareCriteria;
|
||||
// First four must match TViewStyle
|
||||
TDirViewStyle = (dvsIcon, dvsSmallIcon, dvsList, dvsReport, dvsThumbnail);
|
||||
|
||||
TWMXMouse = packed record
|
||||
Msg: Cardinal;
|
||||
@@ -149,6 +152,8 @@ type
|
||||
FHistoryPaths: TStrings;
|
||||
FOverlaySmallImages: TImageList;
|
||||
FOverlayLargeImages: TImageList;
|
||||
FThumbnailShellImages: TImageList;
|
||||
FThumbnailImages: TImageList;
|
||||
FMaxHistoryCount: Integer;
|
||||
FPathLabel: TCustomPathLabel;
|
||||
FOnUpdateStatusBar: TDirViewUpdateStatusBarEvent;
|
||||
@@ -173,6 +178,8 @@ type
|
||||
FDoubleBufferedScrollingWorkaround: Boolean;
|
||||
FOnBusy: TDirViewBusy;
|
||||
FOnChangeFocus: TDirViewChangeFocusEvent;
|
||||
FFallbackThumbnail: array[Boolean] of TBitmap;
|
||||
FFallbackThumbnailSize: TSize;
|
||||
|
||||
procedure CNNotify(var Message: TWMNotify); message CN_NOTIFY;
|
||||
procedure WMNotify(var Msg: TWMNotify); message WM_NOTIFY;
|
||||
@@ -190,6 +197,7 @@ type
|
||||
procedure CMDPIChanged(var Message: TMessage); message CM_DPICHANGED;
|
||||
procedure CMEnabledChanged(var Message: TMessage); message CM_ENABLEDCHANGED;
|
||||
procedure CNKeyDown(var Message: TWMKeyDown); message CN_KEYDOWN;
|
||||
procedure WMUserInvalidateItem(var Message: TMessage); message WM_USER_INVALIDATEITEM;
|
||||
|
||||
procedure DumbCustomDrawItem(Sender: TCustomListView; Item: TListItem;
|
||||
State: TCustomDrawState; var DefaultDraw: Boolean);
|
||||
@@ -201,6 +209,9 @@ type
|
||||
function GetHistoryPath(Index: Integer): string;
|
||||
function GetSelectedNamesSaved: Boolean;
|
||||
|
||||
function GetDirViewStyle: TDirViewStyle;
|
||||
procedure SetDirViewStyle(Value: TDirViewStyle);
|
||||
|
||||
function GetTargetPopupMenu: Boolean;
|
||||
function GetUseDragImages: Boolean;
|
||||
procedure SetMaxHistoryCount(Value: Integer);
|
||||
@@ -223,6 +234,7 @@ type
|
||||
FInvalidNameChars: string;
|
||||
FDragDrive: string;
|
||||
FAnnouncedState: TObject;
|
||||
FThumbnail: Boolean;
|
||||
|
||||
procedure AddToDragFileList(FileList: TFileList; Item: TListItem); virtual;
|
||||
function CanEdit(Item: TListItem): Boolean; override;
|
||||
@@ -276,6 +288,10 @@ type
|
||||
function DoItemColor(Item: TListItem): TColor;
|
||||
function ItemColor(Item: TListItem): TColor; virtual;
|
||||
function ItemImageIndex(Item: TListItem; Cache: Boolean): Integer; virtual; abstract;
|
||||
function ItemThumbnail(Item: TListItem; Size: TSize): TBitmap; virtual;
|
||||
procedure FreeThumbnails;
|
||||
function FallbackThumbnail(Dir: Boolean; Size: TSize): TBitmap;
|
||||
procedure DrawThumbnail(Item: TListItem; DC: HDC);
|
||||
// ItemIsDirectory and ItemFullFileName is in public block
|
||||
function ItemIsRecycleBin(Item: TListItem): Boolean; virtual;
|
||||
procedure KeyDown(var Key: Word; Shift: TShiftState); override;
|
||||
@@ -299,6 +315,7 @@ type
|
||||
function ItemIsFile(Item: TListItem): Boolean; virtual; abstract;
|
||||
function ItemMatchesFilter(Item: TListItem; const Filter: TFileFilter): Boolean; virtual; abstract;
|
||||
function ItemOverlayIndexes(Item: TListItem): Word; virtual;
|
||||
function IsItemVisible(Item: TListItem): Boolean;
|
||||
procedure LimitHistorySize;
|
||||
procedure Notification(AComponent: TComponent; Operation: TOperation); override;
|
||||
procedure PathChanged; virtual;
|
||||
@@ -342,6 +359,8 @@ type
|
||||
procedure DoUpdateStatusBar(Force: Boolean = False);
|
||||
procedure DoCustomDrawItem(Item: TListItem; Stage: TCustomDrawStage);
|
||||
procedure ItemCalculatedSizeUpdated(Item: TListItem; OldSize, NewSize: Int64);
|
||||
function GetThumbnail(Path: string; Size: TSize): TBitmap;
|
||||
procedure InvalidateItem(Item: TListItem);
|
||||
public
|
||||
constructor Create(AOwner: TComponent); override;
|
||||
destructor Destroy; override;
|
||||
@@ -436,6 +455,7 @@ type
|
||||
property NaturalOrderNumericalSorting: Boolean read FNaturalOrderNumericalSorting write SetNaturalOrderNumericalSorting;
|
||||
property AlwaysSortDirectoriesByName: Boolean read FAlwaysSortDirectoriesByName write SetAlwaysSortDirectoriesByName;
|
||||
property DarkMode: Boolean read FDarkMode write SetDarkMode;
|
||||
property DirViewStyle: TDirViewStyle read GetDirViewStyle write SetDirViewStyle;
|
||||
|
||||
property OnContextPopup;
|
||||
property OnStartLoading: TNotifyEvent read FOnStartLoading write FOnStartLoading;
|
||||
@@ -548,7 +568,11 @@ const
|
||||
implementation
|
||||
|
||||
uses
|
||||
Math, DirViewColProperties, UITypes, Types, OperationWithTimeout, Winapi.UxTheme, Vcl.Themes;
|
||||
Math, DirViewColProperties, UITypes, Types, OperationWithTimeout, Winapi.UxTheme, Vcl.Themes, System.IOUtils;
|
||||
|
||||
type
|
||||
PRGBQuadArray = ^TRGBQuadArray; // From graphics.pas
|
||||
TRGBQuadArray = array[Byte] of TRGBQuad; // From graphics.pas
|
||||
|
||||
const
|
||||
ResDirUp = 'DIRUP%2.2d';
|
||||
@@ -957,6 +981,47 @@ begin
|
||||
else inherited;
|
||||
end;
|
||||
|
||||
procedure TCustomDirView.DrawThumbnail(Item: TListItem; DC: HDC);
|
||||
var
|
||||
Rect: TRect;
|
||||
Thumbnail: TBitmap;
|
||||
Size: TSize;
|
||||
Left, Top: Integer;
|
||||
BlendFunction: TBlendFunction;
|
||||
ThumbnailDC: HDC;
|
||||
begin
|
||||
Rect := Item.DisplayRect(drIcon);
|
||||
|
||||
// For thumbnails: The larger side (e.g. height for portrait oriented images) is rescaled to Size.Width
|
||||
// For icons: The "generated" images is exactly as requested
|
||||
Size.Height := MulDiv(Min(Rect.Width, Rect.Height), 9, 10);
|
||||
Size.Width := Size.Height;
|
||||
|
||||
Thumbnail := ItemThumbnail(Item, Size);
|
||||
if not Assigned(Thumbnail) then
|
||||
Thumbnail := FallbackThumbnail(ItemIsDirectory(Item), Size);
|
||||
|
||||
if Assigned(Thumbnail) then
|
||||
begin
|
||||
Left := Rect.Left + ((Rect.Width - Thumbnail.Width) div 2);
|
||||
Top := Rect.Bottom - Thumbnail.Height - MulDiv(Rect.Height, 1, 20); // Bottom-aligned, as Explorer does
|
||||
|
||||
// https://stackoverflow.com/q/24595717/850848
|
||||
// https://stackoverflow.com/q/10028531/850848#10044325
|
||||
ThumbnailDC := CreateCompatibleDC(0);
|
||||
try
|
||||
SelectObject(ThumbnailDC, Thumbnail.Handle);
|
||||
BlendFunction.BlendOp := AC_SRC_OVER;
|
||||
BlendFunction.BlendFlags := 0;
|
||||
BlendFunction.SourceConstantAlpha := 255;
|
||||
BlendFunction.AlphaFormat := AC_SRC_ALPHA;
|
||||
AlphaBlend(DC, Left, Top, Thumbnail.Width, Thumbnail.Height, ThumbnailDC, 0, 0, Thumbnail.Width, Thumbnail.Height, BlendFunction);
|
||||
finally
|
||||
DeleteDC(ThumbnailDC);
|
||||
end;
|
||||
end;
|
||||
end;
|
||||
|
||||
procedure TCustomDirView.CNNotify(var Message: TWMNotify);
|
||||
|
||||
procedure DrawOverlayImage(DC: HDC; Image: Integer; Item: TListItem);
|
||||
@@ -1072,22 +1137,39 @@ begin
|
||||
begin
|
||||
Nmcd := @PNMLVCustomDraw(Message.NMHdr).nmcd;
|
||||
try
|
||||
Message.Result := Message.Result or CDRF_NOTIFYPOSTPAINT;
|
||||
if (Nmcd.dwDrawStage = CDDS_ITEMPOSTPAINT) and
|
||||
((Nmcd.dwDrawStage and CDDS_SUBITEM) = 0) then
|
||||
if (Nmcd.dwDrawStage and CDDS_SUBITEM) = 0 then
|
||||
begin
|
||||
Item := Items[Nmcd.dwItemSpec];
|
||||
Assert(Assigned(Item));
|
||||
OverlayIndexes := ItemOverlayIndexes(Item);
|
||||
OverlayIndex := 1;
|
||||
while OverlayIndexes > 0 do
|
||||
if (Nmcd.dwDrawStage and CDDS_ITEMPREPAINT) = CDDS_ITEMPREPAINT then
|
||||
begin
|
||||
if (OverlayIndex and OverlayIndexes) <> 0 then
|
||||
Message.Result := Message.Result or CDRF_NOTIFYPOSTPAINT;
|
||||
end
|
||||
else
|
||||
if ((Nmcd.dwDrawStage and CDDS_ITEMPOSTPAINT) = CDDS_ITEMPOSTPAINT) and
|
||||
(Nmcd.rc.Width > 0) then // We get called many times with empty rect while view is recreating (e.g. when switching to thumnails mode)
|
||||
begin
|
||||
Item := Items[Nmcd.dwItemSpec];
|
||||
|
||||
if IsItemVisible(Item) then // particularly the thumbnail drawing is expensive
|
||||
begin
|
||||
DrawOverlayImage(Nmcd.hdc, OverlayIndex, Item);
|
||||
Dec(OverlayIndexes, OverlayIndex);
|
||||
if FThumbnail then
|
||||
begin
|
||||
DrawThumbnail(Item, Nmcd.hdc);
|
||||
end
|
||||
else
|
||||
begin
|
||||
OverlayIndexes := ItemOverlayIndexes(Item);
|
||||
OverlayIndex := 1;
|
||||
while OverlayIndexes > 0 do
|
||||
begin
|
||||
if (OverlayIndex and OverlayIndexes) <> 0 then
|
||||
begin
|
||||
DrawOverlayImage(Nmcd.hdc, OverlayIndex, Item);
|
||||
Dec(OverlayIndexes, OverlayIndex);
|
||||
end;
|
||||
OverlayIndex := OverlayIndex shl 1;
|
||||
end;
|
||||
end;
|
||||
end;
|
||||
OverlayIndex := OverlayIndex shl 1;
|
||||
end;
|
||||
end;
|
||||
except
|
||||
@@ -1186,9 +1268,31 @@ begin
|
||||
end;
|
||||
|
||||
procedure TCustomDirView.NeedImageLists(Recreate: Boolean);
|
||||
var
|
||||
ALargeImages: TImageList;
|
||||
ThumbnailSize: Integer;
|
||||
begin
|
||||
SmallImages := NeedImageList(ilsSmall, Recreate, FOverlaySmallImages);
|
||||
LargeImages := NeedImageList(ilsLarge, Recreate, FOverlayLargeImages);
|
||||
ALargeImages := NeedImageList(ilsLarge, Recreate, FOverlayLargeImages);
|
||||
|
||||
if FThumbnail then
|
||||
begin
|
||||
ThumbnailSize := ScaleByPixelsPerInch(128, Self);
|
||||
// ShellImageListForSize would normally prefer smaller icons (for row sizing purposes).
|
||||
// But for thumbnails, we prefer larger version as will will scale it when painting.
|
||||
// The *2 is hackish way to achieve that.
|
||||
FThumbnailShellImages := ShellImageListForSize(ThumbnailSize * 2);
|
||||
if (not Assigned(FThumbnailImages)) or (FThumbnailImages.Width <> ThumbnailSize) then
|
||||
begin
|
||||
if Assigned(FThumbnailImages) then
|
||||
FreeAndNil(FThumbnailImages);
|
||||
// Dummy image list, whose sole purpose it to autosize the items in the view
|
||||
FThumbnailImages := TImageList.CreateSize(ThumbnailSize, ThumbnailSize);
|
||||
end;
|
||||
|
||||
LargeImages := FThumbnailImages
|
||||
end
|
||||
else LargeImages := ALargeImages;
|
||||
end;
|
||||
|
||||
procedure TCustomDirView.CMDPIChanged(var Message: TMessage);
|
||||
@@ -1222,6 +1326,7 @@ procedure TCustomDirView.FreeImageLists;
|
||||
begin
|
||||
FreeAndNil(FOverlaySmallImages);
|
||||
FreeAndNil(FOverlayLargeImages);
|
||||
FreeAndNil(FThumbnailImages);
|
||||
|
||||
SmallImages := nil;
|
||||
LargeImages := nil;
|
||||
@@ -1383,6 +1488,7 @@ begin
|
||||
|
||||
FreeAndNil(FDragDropFilesEx);
|
||||
FreeImageLists;
|
||||
FreeThumbnails;
|
||||
|
||||
inherited;
|
||||
end;
|
||||
@@ -1465,6 +1571,104 @@ begin
|
||||
Result := clDefaultItemColor;
|
||||
end;
|
||||
|
||||
function TCustomDirView.ItemThumbnail(Item: TListItem; Size: TSize): TBitmap;
|
||||
begin
|
||||
Result := nil;
|
||||
end;
|
||||
|
||||
function TCustomDirView.GetThumbnail(Path: string; Size: TSize): TBitmap;
|
||||
var
|
||||
ImageFactory: IShellItemImageFactory;
|
||||
X, Y: Integer;
|
||||
Row: PRGBQuadArray;
|
||||
Pixel: PRGBQuad;
|
||||
Alpha: Byte;
|
||||
Handle: HBITMAP;
|
||||
begin
|
||||
Result := nil;
|
||||
SHCreateItemFromParsingName(PChar(Path), nil, IShellItemImageFactory, ImageFactory);
|
||||
if Assigned(ImageFactory) then
|
||||
begin
|
||||
if Succeeded(ImageFactory.GetImage(Size, SIIGBF_RESIZETOFIT, Handle)) then
|
||||
begin
|
||||
Result := TBitmap.Create;
|
||||
try
|
||||
Result.Handle := Handle;
|
||||
Result.PixelFormat := pf32bit;
|
||||
|
||||
for Y := 0 to Result.Height - 1 do
|
||||
begin
|
||||
Row := Result.ScanLine[Y];
|
||||
for X := 0 to Result.Width - 1 do
|
||||
begin
|
||||
Pixel := @Row[X];
|
||||
Alpha := Pixel.rgbReserved;
|
||||
Pixel.rgbBlue := (Pixel.rgbBlue * Alpha) div 255;
|
||||
Pixel.rgbGreen := (Pixel.rgbGreen * Alpha) div 255;
|
||||
Pixel.rgbRed := (Pixel.rgbRed * Alpha) div 255;
|
||||
end;
|
||||
end;
|
||||
except
|
||||
Result.Free;
|
||||
raise;
|
||||
end;
|
||||
end;
|
||||
|
||||
ImageFactory := nil; // Redundant?
|
||||
end;
|
||||
end;
|
||||
|
||||
procedure TCustomDirView.FreeThumbnails;
|
||||
begin
|
||||
FreeAndNil(FFallbackThumbnail[True]);
|
||||
FreeAndNil(FFallbackThumbnail[False]);
|
||||
end;
|
||||
|
||||
function TCustomDirView.FallbackThumbnail(Dir: Boolean; Size: TSize): TBitmap;
|
||||
var
|
||||
FallbackPath: string;
|
||||
Existed: Boolean;
|
||||
Index: Integer;
|
||||
begin
|
||||
Result := nil;
|
||||
try
|
||||
if FFallbackThumbnailSize <> Size then
|
||||
begin
|
||||
FreeThumbnails;
|
||||
end;
|
||||
|
||||
if not Assigned(FFallbackThumbnail[Dir]) then
|
||||
begin
|
||||
Index := 1;
|
||||
repeat
|
||||
FallbackPath := TPath.Combine(TempDir, 'default.' + IntToStr(Index) + '.thumbnailimage');
|
||||
Existed := FileExists(FallbackPath) or DirectoryExists(FallbackPath);
|
||||
if not Existed then
|
||||
begin
|
||||
if Dir then
|
||||
CreateDir(FallbackPath)
|
||||
else
|
||||
TFile.WriteAllText(FallbackPath, '');
|
||||
end;
|
||||
Inc(Index);
|
||||
until not Existed;
|
||||
|
||||
FFallbackThumbnailSize := Size;
|
||||
FFallbackThumbnail[Dir] := GetThumbnail(FallbackPath, Size);
|
||||
if Existed then
|
||||
begin
|
||||
if Dir then
|
||||
RemoveDir(FallbackPath)
|
||||
else
|
||||
DeleteFile(FallbackPath);
|
||||
end;
|
||||
end;
|
||||
|
||||
Result := FFallbackThumbnail[Dir];
|
||||
except
|
||||
end;
|
||||
end;
|
||||
|
||||
function TCustomDirView.GetFilesMarkedSize: Int64;
|
||||
begin
|
||||
if SelCount > 0 then Result := FilesSelSize
|
||||
@@ -1485,6 +1689,11 @@ begin
|
||||
OnGetOverlay(Self, Item, Result);
|
||||
end;
|
||||
|
||||
function TCustomDirView.IsItemVisible(Item: TListItem): Boolean;
|
||||
begin
|
||||
Result := (ListView_IsItemVisible(Handle, Item.Index) <> 0);
|
||||
end;
|
||||
|
||||
procedure TCustomDirView.WMKeyDown(var Message: TWMKeyDown);
|
||||
begin
|
||||
if DoubleBuffered and (Message.CharCode in [VK_PRIOR, VK_NEXT]) and
|
||||
@@ -3482,6 +3691,54 @@ begin
|
||||
UpdateStatusBar;
|
||||
end;
|
||||
|
||||
function TCustomDirView.GetDirViewStyle: TDirViewStyle;
|
||||
begin
|
||||
if (ViewStyle = vsIcon) and FThumbnail then Result := dvsThumbnail
|
||||
else Result := TDirViewStyle(ViewStyle);
|
||||
end;
|
||||
|
||||
procedure TCustomDirView.SetDirViewStyle(Value: TDirViewStyle);
|
||||
var
|
||||
NewViewStyle: TViewStyle;
|
||||
begin
|
||||
if DirViewStyle <> Value then
|
||||
begin
|
||||
FThumbnail := (Value = dvsThumbnail);
|
||||
// Create thumbnail images before recreating the view
|
||||
NeedImageLists(False);
|
||||
if FThumbnail then NewViewStyle := vsIcon
|
||||
else NewViewStyle := TViewStyle(Value);
|
||||
if ViewStyle <> NewViewStyle then
|
||||
begin
|
||||
ViewStyle := NewViewStyle;
|
||||
end
|
||||
else
|
||||
begin
|
||||
// Changing ViewStyle recreates the view, we want to be consistent.
|
||||
if not (csLoading in ComponentState) then
|
||||
RecreateWnd;
|
||||
end;
|
||||
end;
|
||||
end;
|
||||
|
||||
procedure TCustomDirView.InvalidateItem(Item: TListItem);
|
||||
var
|
||||
R: TRect;
|
||||
begin
|
||||
R := Item.DisplayRect(drBounds);
|
||||
// alternative to TListItem.Update (which causes flicker)
|
||||
InvalidateRect(Handle, @R, True);
|
||||
end;
|
||||
|
||||
procedure TCustomDirView.WMUserInvalidateItem(var Message: TMessage);
|
||||
var
|
||||
Index: Integer;
|
||||
begin
|
||||
Index := Integer(Message.WParam);
|
||||
if (Index >= 0) and (Index < Items.Count) then
|
||||
InvalidateItem(Items[Index]);
|
||||
end;
|
||||
|
||||
initialization
|
||||
DropSourceControl := nil;
|
||||
|
||||
|
||||
@@ -74,6 +74,8 @@ type
|
||||
FileExt: string;
|
||||
TypeName: string;
|
||||
ImageIndex: Integer;
|
||||
Thumbnail: TBitmap;
|
||||
ThumbnailSize: TSize;
|
||||
Size: Int64;
|
||||
Attr: LongWord;
|
||||
FileTime: TFileTime;
|
||||
@@ -94,6 +96,7 @@ type
|
||||
private
|
||||
FOwner: TDirView;
|
||||
FSyncIcon: Integer;
|
||||
FSyncThumbnail: TBitmap;
|
||||
FCurrentIndex: Integer;
|
||||
FCurrentFilePath: string;
|
||||
FCurrentItemData: TFileRec;
|
||||
@@ -101,6 +104,9 @@ type
|
||||
protected
|
||||
constructor Create(Owner: TDirView);
|
||||
procedure Execute; override;
|
||||
|
||||
public
|
||||
destructor Destroy; override;
|
||||
end;
|
||||
|
||||
// WORKAROUND: TQueue<Integer>.Create fails when TDirView is created in IDE, while TQueue<TIconUpdateSchedule>.Create works
|
||||
@@ -200,6 +206,7 @@ type
|
||||
function GetIsRoot: Boolean; override;
|
||||
procedure InternalEdit(const HItem: TLVItem); override;
|
||||
function ItemColor(Item: TListItem): TColor; override;
|
||||
function ItemThumbnail(Item: TListItem; Size: TSize): TBitmap; override;
|
||||
function ItemFileExt(Item: TListItem): string;
|
||||
function ItemFileNameOnly(Item: TListItem): string;
|
||||
function ItemImageIndex(Item: TListItem; Cache: Boolean): Integer; override;
|
||||
@@ -211,9 +218,11 @@ type
|
||||
procedure LoadFiles; override;
|
||||
procedure PerformItemDragDropOperation(Item: TListItem; Effect: Integer; Paste: Boolean); override;
|
||||
procedure SortItems; override;
|
||||
function ThumbnailNeeded(ItemData: PFileRec): Boolean;
|
||||
procedure DoFetchIconUpdate;
|
||||
procedure DoUpdateIcon;
|
||||
procedure StartFileDeleteThread;
|
||||
procedure IconUpdateEnqueue(ListItem: TListItem);
|
||||
function IconUpdatePeek: Integer;
|
||||
procedure IconUpdateDequeue;
|
||||
procedure WMDestroy(var Msg: TWMDestroy); message WM_DESTROY;
|
||||
@@ -363,6 +372,7 @@ type
|
||||
property ColumnClick;
|
||||
property MultiSelect;
|
||||
property ReadOnly;
|
||||
property DirViewStyle;
|
||||
|
||||
// The only way to make Items stored automatically and survive handle recreation.
|
||||
// Though we should implement custom persisting to avoid publishing this
|
||||
@@ -395,6 +405,9 @@ uses
|
||||
ShellDialogs, IEDriveInfo,
|
||||
FileChanges, Math, PasTools, StrUtils, Types, UITypes;
|
||||
|
||||
var
|
||||
ThumbnailNotNeeded: TSize;
|
||||
|
||||
var
|
||||
DaylightHack: Boolean;
|
||||
|
||||
@@ -617,6 +630,12 @@ begin
|
||||
FOwner := Owner;
|
||||
end; {TIconUpdateThread.Create}
|
||||
|
||||
destructor TIconUpdateThread.Destroy;
|
||||
begin
|
||||
FreeAndNil(FSyncThumbnail);
|
||||
inherited;
|
||||
end;
|
||||
|
||||
procedure TIconUpdateThread.Execute;
|
||||
var
|
||||
IsSpecialExt: Boolean;
|
||||
@@ -631,19 +650,32 @@ begin
|
||||
if (FCurrentIndex >= 0) and
|
||||
(not Terminated) then
|
||||
begin
|
||||
PrevPIDL := FCurrentItemData.PIDL;
|
||||
try
|
||||
IsSpecialExt := MatchesFileExt(FCurrentItemData.FileExt, SpecialExtensions);
|
||||
FOwner.DoFetchIcon(FCurrentFilePath, IsSpecialExt, False, @FCurrentItemData, FSyncIcon, TypeName);
|
||||
except
|
||||
{Capture exceptions generated by the shell}
|
||||
FSyncIcon := UnknownFileIcon;
|
||||
end;
|
||||
if Assigned(FCurrentItemData.PIDL) and
|
||||
(PrevPIDL <> FCurrentItemData.PIDL) then
|
||||
FSyncIcon := -1;
|
||||
if Assigned(FSyncThumbnail) then
|
||||
FreeAndNil(FSyncThumbnail);
|
||||
|
||||
if FCurrentItemData.IconEmpty then
|
||||
begin
|
||||
FreePIDL(FCurrentItemData.PIDL);
|
||||
PrevPIDL := FCurrentItemData.PIDL;
|
||||
try
|
||||
IsSpecialExt := MatchesFileExt(FCurrentItemData.FileExt, SpecialExtensions);
|
||||
FOwner.DoFetchIcon(FCurrentFilePath, IsSpecialExt, False, @FCurrentItemData, FSyncIcon, TypeName);
|
||||
except
|
||||
{Capture exceptions generated by the shell}
|
||||
FSyncIcon := UnknownFileIcon;
|
||||
end;
|
||||
if Assigned(FCurrentItemData.PIDL) and
|
||||
(PrevPIDL <> FCurrentItemData.PIDL) then
|
||||
begin
|
||||
FreePIDL(FCurrentItemData.PIDL);
|
||||
end;
|
||||
end;
|
||||
|
||||
if FOwner.ThumbnailNeeded(@FCurrentItemData) then
|
||||
begin
|
||||
FSyncThumbnail := FOwner.GetThumbnail(FCurrentFilePath, FCurrentItemData.ThumbnailSize);
|
||||
end;
|
||||
|
||||
if not Terminated then
|
||||
begin
|
||||
Synchronize(FOwner.DoUpdateIcon);
|
||||
@@ -907,6 +939,8 @@ begin
|
||||
{$WARNINGS ON}
|
||||
Empty := True;
|
||||
IconEmpty := True;
|
||||
Thumbnail := nil;
|
||||
ThumbnailSize := ThumbnailNotNeeded;
|
||||
if Size > 0 then Inc(FFilesSize, Size);
|
||||
PIDL := nil;
|
||||
CalculatedSize := -1;
|
||||
@@ -955,6 +989,8 @@ begin
|
||||
{$WARNINGS ON}
|
||||
Empty := True;
|
||||
IconEmpty := False;
|
||||
Thumbnail := nil;
|
||||
ThumbnailSize := ThumbnailNotNeeded;
|
||||
PIDL := nil;
|
||||
|
||||
ImageIndex := StdDirIcon;
|
||||
@@ -1332,7 +1368,6 @@ var
|
||||
SaveCursor: TCursor;
|
||||
FSize: Int64;
|
||||
FocusedIsVisible: Boolean;
|
||||
R: TRect;
|
||||
begin
|
||||
if (not Loading) and LoadEnabled then
|
||||
begin
|
||||
@@ -1347,29 +1382,7 @@ begin
|
||||
end
|
||||
else
|
||||
begin
|
||||
if Assigned(ItemFocused) then
|
||||
begin
|
||||
R := ItemFocused.DisplayRect(drBounds);
|
||||
// btw, we use vsReport only, nothing else was tested
|
||||
// (We can use ListView_IsItemVisible here)
|
||||
Assert(ViewStyle = vsReport);
|
||||
case ViewStyle of
|
||||
vsReport:
|
||||
FocusedIsVisible := (TopItem.Index <= ItemFocused.Index) and
|
||||
(ItemFocused.Index < TopItem.Index + VisibleRowCount);
|
||||
|
||||
vsList:
|
||||
// do not know how to implement that
|
||||
FocusedIsVisible := False;
|
||||
|
||||
else // vsIcon and vsSmallIcon
|
||||
FocusedIsVisible :=
|
||||
IntersectRect(R,
|
||||
Classes.Rect(ViewOrigin, Point(ViewOrigin.X + ClientWidth, ViewOrigin.Y + ClientHeight)),
|
||||
ItemFocused.DisplayRect(drBounds));
|
||||
end;
|
||||
end
|
||||
else FocusedIsVisible := False; // shut up
|
||||
FocusedIsVisible := Assigned(ItemFocused) and IsItemVisible(ItemFocused);
|
||||
|
||||
SaveCursor := Screen.Cursor;
|
||||
Screen.Cursor := crHourGlass;
|
||||
@@ -1446,9 +1459,7 @@ begin
|
||||
FileTime := SRec.FindData.ftLastWriteTime;
|
||||
{$WARNINGS ON}
|
||||
end;
|
||||
// alternative to TListItem.Update (which causes flicker)
|
||||
R := Items[iIndex].DisplayRect(drBounds);
|
||||
InvalidateRect(Handle, @R, True);
|
||||
InvalidateItem(Items[iIndex]);
|
||||
AnyUpdate := True;
|
||||
end;
|
||||
FItems.Add(Srec.Name);
|
||||
@@ -2299,7 +2310,6 @@ var
|
||||
Value: string;
|
||||
ASize: Int64;
|
||||
FetchIcon: Boolean;
|
||||
Schedule: TIconUpdateSchedule;
|
||||
begin
|
||||
Assert(Assigned(ListItem) and Assigned(ListItem.Data));
|
||||
with PFileRec(ListItem.Data)^, DispInfo do
|
||||
@@ -2320,13 +2330,9 @@ begin
|
||||
GetDisplayData(ListItem, True);
|
||||
|
||||
{Set IconUpdatethread :}
|
||||
if IconEmpty and UseIconUpdateThread and (not FIsRecycleBin) and
|
||||
(not FIconUpdateSet.ContainsKey(ListItem.Index)) then
|
||||
if IconEmpty and UseIconUpdateThread and (not FIsRecycleBin) then
|
||||
begin
|
||||
FIconUpdateSet.Add(ListItem.Index, False);
|
||||
Schedule.Index := ListItem.Index;
|
||||
FIconUpdateQueue.Enqueue(Schedule);
|
||||
StartIconUpdateThread;
|
||||
IconUpdateEnqueue(ListItem);
|
||||
end;
|
||||
|
||||
if (DispInfo.Mask and LVIF_TEXT) <> 0 then
|
||||
@@ -2381,6 +2387,33 @@ begin
|
||||
Result := clDefaultItemColor;
|
||||
end;
|
||||
|
||||
function TDirView.ItemThumbnail(Item: TListItem; Size: TSize): TBitmap;
|
||||
var
|
||||
ItemData: PFileRec;
|
||||
begin
|
||||
if not UseIconUpdateThread then
|
||||
begin
|
||||
// not supported without update thread
|
||||
Result := nil;
|
||||
end
|
||||
else
|
||||
begin
|
||||
ItemData := PFileRec(Item.Data);
|
||||
if (not Assigned(ItemData.Thumbnail)) or
|
||||
(ItemData.ThumbnailSize <> Size) then
|
||||
begin
|
||||
FreeAndNil(ItemData.Thumbnail);
|
||||
ItemData.ThumbnailSize := Size;
|
||||
Result := nil;
|
||||
IconUpdateEnqueue(Item);
|
||||
end
|
||||
else
|
||||
begin
|
||||
Result := ItemData.Thumbnail;
|
||||
end;
|
||||
end;
|
||||
end;
|
||||
|
||||
procedure TDirView.StartFileDeleteThread;
|
||||
var
|
||||
Files: TStringList;
|
||||
@@ -2394,6 +2427,20 @@ begin
|
||||
end;
|
||||
end;
|
||||
|
||||
procedure TDirView.IconUpdateEnqueue(ListItem: TListItem);
|
||||
var
|
||||
Schedule: TIconUpdateSchedule;
|
||||
begin
|
||||
if not FIconUpdateSet.ContainsKey(ListItem.Index) then
|
||||
begin
|
||||
FIconUpdateSet.Add(ListItem.Index, False);
|
||||
Schedule.Index := ListItem.Index;
|
||||
FIconUpdateQueue.Enqueue(Schedule);
|
||||
Assert(FIconUpdateSet.Count = FIconUpdateQueue.Count + FIconUpdateQueueDeferred.Count);
|
||||
end;
|
||||
StartIconUpdateThread;
|
||||
end;
|
||||
|
||||
function TDirView.IconUpdatePeek: Integer;
|
||||
begin
|
||||
if FIconUpdateQueue.Count > 0 then
|
||||
@@ -2411,12 +2458,19 @@ begin
|
||||
else
|
||||
FIconUpdateQueueDeferred.Dequeue;
|
||||
FIconUpdateSet.Remove(FIconUpdateThread.FCurrentIndex);
|
||||
Assert(FIconUpdateSet.Count = FIconUpdateQueue.Count + FIconUpdateQueueDeferred.Count);
|
||||
end;
|
||||
|
||||
function TDirView.ThumbnailNeeded(ItemData: PFileRec): Boolean;
|
||||
begin
|
||||
Result := (not Assigned(ItemData.Thumbnail)) and (ItemData.ThumbnailSize <> ThumbnailNotNeeded);
|
||||
end;
|
||||
|
||||
procedure TDirView.DoFetchIconUpdate;
|
||||
var
|
||||
Item: TListItem;
|
||||
ItemData: PFileRec;
|
||||
Invisible: Boolean;
|
||||
begin
|
||||
FIconUpdateThread.FCurrentIndex := IconUpdatePeek;
|
||||
if FIconUpdateThread.FCurrentIndex < 0 then
|
||||
@@ -2432,27 +2486,50 @@ begin
|
||||
IconUpdateDequeue;
|
||||
end
|
||||
else
|
||||
// Deprioritizing unvisible item taken from priority queue
|
||||
if (FIconUpdateQueue.Count > 0) and
|
||||
IsVista and (ListView_IsItemVisible(Handle, FIconUpdateThread.FCurrentIndex) = 0) then
|
||||
begin
|
||||
FIconUpdateQueueDeferred.Enqueue(FIconUpdateQueue.Dequeue);
|
||||
end
|
||||
else
|
||||
begin
|
||||
Item := Items[FIconUpdateThread.FCurrentIndex];
|
||||
Assert(Assigned(Item));
|
||||
Assert(Assigned(Item.Data));
|
||||
ItemData := PFileRec(Item.Data);
|
||||
if not ItemData.IconEmpty then
|
||||
|
||||
Invisible := IsVista and (not IsItemVisible(Item));
|
||||
|
||||
if (Invisible or (not FThumbnail)) and
|
||||
(not Assigned(ItemData.Thumbnail)) then
|
||||
begin
|
||||
ItemData.ThumbnailSize := ThumbnailNotNeeded; // not needed anymore
|
||||
end;
|
||||
|
||||
// Deprioritizing unvisible item taken from priority queue.
|
||||
// As we ask Window to cache the image index (LVIF_DI_SETITEM), we won't get asked again,
|
||||
// so we have to retrieve the image eventually (but not thumbnail)
|
||||
if (FIconUpdateQueue.Count > 0) and
|
||||
Invisible then
|
||||
begin
|
||||
Assert(not ThumbnailNeeded(ItemData));
|
||||
if ItemData.IconEmpty then
|
||||
begin
|
||||
FIconUpdateQueueDeferred.Enqueue(FIconUpdateQueue.Dequeue);
|
||||
end
|
||||
else
|
||||
begin
|
||||
IconUpdateDequeue;
|
||||
end;
|
||||
FIconUpdateThread.FCurrentIndex := -1;
|
||||
IconUpdateDequeue;
|
||||
end
|
||||
else
|
||||
begin
|
||||
FIconUpdateThread.FCurrentFilePath := ItemFullFileName(Item);
|
||||
FIconUpdateThread.FCurrentItemData := ItemData^;
|
||||
if ItemData.IconEmpty or
|
||||
ThumbnailNeeded(ItemData) then
|
||||
begin
|
||||
FIconUpdateThread.FCurrentFilePath := ItemFullFileName(Item);
|
||||
FIconUpdateThread.FCurrentItemData := ItemData^;
|
||||
end
|
||||
else
|
||||
begin
|
||||
IconUpdateDequeue;
|
||||
FIconUpdateThread.FCurrentIndex := -1;
|
||||
end;
|
||||
end;
|
||||
end;
|
||||
end;
|
||||
@@ -2498,6 +2575,16 @@ begin
|
||||
end;
|
||||
end;
|
||||
ItemData^.IconEmpty := False;
|
||||
|
||||
if Assigned(FIconUpdateThread.FSyncThumbnail) then
|
||||
begin
|
||||
ItemData^.Thumbnail := FIconUpdateThread.FSyncThumbnail;
|
||||
FIconUpdateThread.FSyncThumbnail := nil;
|
||||
// It can happen that this is called while the very item is being painted,
|
||||
// (particularly ImageFactory.GetImage pumps the queue).
|
||||
// Calling InvalidateRect directly would get ignored then.
|
||||
PostMessage(WindowHandle, WM_USER_INVALIDATEITEM, Item.Index, 0);
|
||||
end;
|
||||
end;
|
||||
end;
|
||||
end;
|
||||
@@ -2801,6 +2888,7 @@ begin
|
||||
SetLength(TypeName, 0);
|
||||
SetLength(DisplayName, 0);
|
||||
if Assigned(PIDL) then FreePIDL(PIDL);
|
||||
FreeAndNil(Thumbnail);
|
||||
Dispose(PFileRec(Item.Data));
|
||||
Item.Data := nil;
|
||||
end;
|
||||
|
||||
@@ -147,7 +147,6 @@ type
|
||||
property ShowHint;
|
||||
property TabOrder;
|
||||
property TabStop default True;
|
||||
property ViewStyle;
|
||||
property Visible;
|
||||
property OnChange;
|
||||
property OnChanging;
|
||||
|
||||
@@ -64,6 +64,7 @@ type
|
||||
TImageListSize = (ilsSmall, ilsLarge);
|
||||
|
||||
procedure NeedShellImageLists;
|
||||
function ShellImageListForSize(Width: Integer): TImageList;
|
||||
function ShellImageListForControl(Control: TControl; Size: TImageListSize): TImageList;
|
||||
|
||||
function ControlHasRecreationPersistenceData(Control: TControl): Boolean;
|
||||
@@ -504,6 +505,7 @@ end;
|
||||
var
|
||||
ShellImageLists: TDictionary<Integer, TImageList> = nil;
|
||||
|
||||
// This should be replaced with IShellItemImageFactory, as already used for thumbnails
|
||||
procedure InitializeShellImageLists;
|
||||
type
|
||||
TSHGetImageList = function (iImageList: integer; const riid: TGUID; var ppv: Pointer): hResult; stdcall;
|
||||
@@ -551,23 +553,15 @@ begin
|
||||
end;
|
||||
end;
|
||||
|
||||
function ShellImageListForControl(Control: TControl; Size: TImageListSize): TImageList;
|
||||
function ShellImageListForSize(Width: Integer): TImageList;
|
||||
var
|
||||
ImageListPair: TPair<Integer, TImageList>;
|
||||
Width, ImageListWidth: Integer;
|
||||
ImageListWidth: Integer;
|
||||
Diff, BestDiff: Integer;
|
||||
begin
|
||||
// Delay load image lists, not to waste resources in console/scripting mode
|
||||
NeedShellImageLists;
|
||||
|
||||
case Size of
|
||||
ilsSmall: Width := 16;
|
||||
ilsLarge: Width := 32;
|
||||
else Width := 0; Assert(False);
|
||||
end;
|
||||
|
||||
Width := ScaleByPixelsPerInch(Width, Control);
|
||||
|
||||
Result := nil;
|
||||
BestDiff := -1;
|
||||
for ImageListPair in ShellImageLists do
|
||||
@@ -580,6 +574,7 @@ begin
|
||||
else
|
||||
begin
|
||||
// Prefer smaller images over larger, so for 150%, we use 100% images, not 200%
|
||||
// (a larger icon would make the item row higher)
|
||||
Diff := ImageListWidth - Width + 1;
|
||||
end;
|
||||
|
||||
@@ -591,6 +586,22 @@ begin
|
||||
end;
|
||||
end;
|
||||
|
||||
function ShellImageListForControl(Control: TControl; Size: TImageListSize): TImageList;
|
||||
var
|
||||
Width: Integer;
|
||||
begin
|
||||
case Size of
|
||||
ilsSmall: Width := 16;
|
||||
ilsLarge: Width := 32;
|
||||
else Width := 0; Assert(False);
|
||||
end;
|
||||
|
||||
Width := ScaleByPixelsPerInch(Width, Control);
|
||||
|
||||
Result := ShellImageListForSize(Width);
|
||||
|
||||
end;
|
||||
|
||||
type
|
||||
TListViewHelper = class helper for TCustomListView
|
||||
public
|
||||
|
||||
@@ -18,6 +18,7 @@
|
||||
// WM_USER_SHCHANGENOTIFY + 13 (packages/filemng/DriveView.pas)
|
||||
// WM_PASTE_FILES + 14 (forms/CustomScpExplorer.cpp)
|
||||
#define WM_IS_HIDDEN (WM_WINSCP_USER + 15)
|
||||
// WM_USER_INVALIDATEITEM + 16 (packages/filemng/DirView.pas)
|
||||
//---------------------------------------------------------------------------
|
||||
#define C(Property) (Property != rhc.Property) ||
|
||||
struct TSynchronizeChecklistConfiguration
|
||||
|
||||
@@ -723,7 +723,7 @@ void __fastcall TWinConfiguration::Default()
|
||||
FScpExplorer.SessionsTabs = true;
|
||||
FScpExplorer.StatusBar = true;
|
||||
FScpExplorer.LastLocalTargetDirectory = GetPersonalFolder();
|
||||
FScpExplorer.ViewStyle = 0; /* vsIcon */
|
||||
FScpExplorer.ViewStyle = dvsIcon;
|
||||
FScpExplorer.ShowFullAddress = true;
|
||||
FScpExplorer.DriveView = true;
|
||||
FScpExplorer.DriveViewWidth = 180;
|
||||
@@ -771,6 +771,7 @@ void __fastcall TWinConfiguration::Default()
|
||||
FScpCommander.ExplorerKeyboardShortcuts = false;
|
||||
FScpCommander.SystemContextMenu = false;
|
||||
FScpCommander.RemotePanel.DirViewParams = ScpCommanderRemotePanelDirViewParamsDefault;
|
||||
FScpCommander.RemotePanel.ViewStyle = dvsReport;
|
||||
FScpCommander.RemotePanel.StatusBar = true;
|
||||
FScpCommander.RemotePanel.DriveView = false;
|
||||
FScpCommander.RemotePanel.DriveViewHeight = 100;
|
||||
@@ -779,6 +780,7 @@ void __fastcall TWinConfiguration::Default()
|
||||
FScpCommander.RemotePanel.DriveViewWidthPixelsPerInch = USER_DEFAULT_SCREEN_DPI;
|
||||
FScpCommander.RemotePanel.LastPath = UnicodeString();
|
||||
FScpCommander.LocalPanel.DirViewParams = ScpCommanderLocalPanelDirViewParamsDefault;
|
||||
FScpCommander.LocalPanel.ViewStyle = dvsReport;
|
||||
FScpCommander.LocalPanel.StatusBar = true;
|
||||
FScpCommander.LocalPanel.DriveView = false;
|
||||
FScpCommander.LocalPanel.DriveViewHeight = 100;
|
||||
@@ -787,6 +789,7 @@ void __fastcall TWinConfiguration::Default()
|
||||
FScpCommander.LocalPanel.DriveViewWidthPixelsPerInch = USER_DEFAULT_SCREEN_DPI;
|
||||
FScpCommander.LocalPanel.LastPath = UnicodeString();
|
||||
FScpCommander.OtherLocalPanelDirViewParams = FScpCommander.LocalPanel.DirViewParams;
|
||||
FScpCommander.OtherLocalPanelViewStyle = FScpCommander.LocalPanel.ViewStyle;
|
||||
FScpCommander.OtherLocalPanelLastPath = UnicodeString();
|
||||
|
||||
FBookmarks->Clear();
|
||||
@@ -1229,6 +1232,7 @@ THierarchicalStorage * TWinConfiguration::CreateScpStorage(bool & SessionList)
|
||||
); \
|
||||
BLOCK(L"Interface\\Commander\\LocalPanel", CANCREATE, \
|
||||
KEY(String, ScpCommander.LocalPanel.DirViewParams); \
|
||||
KEY(Integer, ScpCommander.LocalPanel.ViewStyle); \
|
||||
KEY(Bool, ScpCommander.LocalPanel.StatusBar); \
|
||||
KEY(Bool, ScpCommander.LocalPanel.DriveView); \
|
||||
KEY(Integer, ScpCommander.LocalPanel.DriveViewHeight); \
|
||||
@@ -1239,6 +1243,7 @@ THierarchicalStorage * TWinConfiguration::CreateScpStorage(bool & SessionList)
|
||||
); \
|
||||
BLOCK(L"Interface\\Commander\\RemotePanel", CANCREATE, \
|
||||
KEY(String, ScpCommander.RemotePanel.DirViewParams); \
|
||||
KEY(Integer, ScpCommander.RemotePanel.ViewStyle); \
|
||||
KEY(Bool, ScpCommander.RemotePanel.StatusBar); \
|
||||
KEY(Bool, ScpCommander.RemotePanel.DriveView); \
|
||||
KEY(Integer, ScpCommander.RemotePanel.DriveViewHeight); \
|
||||
@@ -1248,8 +1253,9 @@ THierarchicalStorage * TWinConfiguration::CreateScpStorage(bool & SessionList)
|
||||
KEY(String, ScpCommander.RemotePanel.LastPath); \
|
||||
); \
|
||||
BLOCK(L"Interface\\Commander\\OtherLocalPanel", CANCREATE, \
|
||||
KEYEX(String, ScpCommander.OtherLocalPanelDirViewParams, L"DirViewParams"); \
|
||||
KEYEX(String, ScpCommander.OtherLocalPanelLastPath, L"LastPath"); \
|
||||
KEYEX(String, ScpCommander.OtherLocalPanelDirViewParams, L"DirViewParams"); \
|
||||
KEYEX(Integer, ScpCommander.OtherLocalPanelViewStyle, L"ViewStyle"); \
|
||||
KEYEX(String, ScpCommander.OtherLocalPanelLastPath, L"LastPath"); \
|
||||
); \
|
||||
BLOCK(L"Security", CANCREATE, \
|
||||
KEY(Bool, FUseMasterPassword); \
|
||||
|
||||
@@ -35,6 +35,7 @@ struct TScpExplorerConfiguration {
|
||||
//---------------------------------------------------------------------------
|
||||
struct TScpCommanderPanelConfiguration {
|
||||
UnicodeString DirViewParams;
|
||||
int ViewStyle;
|
||||
bool StatusBar;
|
||||
bool DriveView;
|
||||
int DriveViewHeight;
|
||||
@@ -43,7 +44,7 @@ struct TScpCommanderPanelConfiguration {
|
||||
int DriveViewWidthPixelsPerInch;
|
||||
UnicodeString LastPath;
|
||||
bool __fastcall operator !=(TScpCommanderPanelConfiguration & rhc)
|
||||
{ return C(DirViewParams) C(StatusBar)
|
||||
{ return C(DirViewParams) C(ViewStyle) C(StatusBar)
|
||||
C(DriveView) C(DriveViewHeight) C(DriveViewHeightPixelsPerInch)
|
||||
C(DriveViewWidth) C(DriveViewWidthPixelsPerInch) C(LastPath) 0; };
|
||||
};
|
||||
@@ -67,6 +68,7 @@ struct TScpCommanderConfiguration {
|
||||
bool ExplorerKeyboardShortcuts;
|
||||
bool SystemContextMenu;
|
||||
UnicodeString OtherLocalPanelDirViewParams;
|
||||
int OtherLocalPanelViewStyle;
|
||||
UnicodeString OtherLocalPanelLastPath;
|
||||
bool __fastcall operator !=(TScpCommanderConfiguration & rhc)
|
||||
{ return C(WindowParams) C(LocalPanelWidth) C(ToolbarsLayout) C(ToolbarsButtons)
|
||||
@@ -75,7 +77,7 @@ struct TScpCommanderConfiguration {
|
||||
C(NortonLikeMode) C(PreserveLocalDirectory)
|
||||
C(CompareBySize) C(CompareByTime) C(SwappedPanels)
|
||||
C(TreeOnLeft) C(ExplorerKeyboardShortcuts) C(SystemContextMenu)
|
||||
C(OtherLocalPanelDirViewParams) C(OtherLocalPanelLastPath) 0; };
|
||||
C(OtherLocalPanelDirViewParams) C(OtherLocalPanelViewStyle) C(OtherLocalPanelLastPath) 0; };
|
||||
|
||||
TCompareCriterias __fastcall CompareCriterias()
|
||||
{
|
||||
|
||||
Reference in New Issue
Block a user