Index: src/fileviews/ucolumnsfileview.pas
===================================================================
--- src/fileviews/ucolumnsfileview.pas	(revision 8064)
+++ src/fileviews/ucolumnsfileview.pas	(working copy)
@@ -164,7 +164,7 @@
     procedure RedrawFile(FileIndex: PtrInt); override;
     procedure RedrawFile(DisplayFile: TDisplayFile); override;
     procedure RedrawFiles; override;
-    procedure SetActiveFile(FileIndex: PtrInt; ScrollTo: Boolean); override;
+    procedure SetActiveFile(FileIndex: PtrInt; ScrollTo: Boolean; aLastTopRowIndex: PtrInt = -1); override;
     procedure SetSorting(const NewSortings: TFileSortings); override;
     procedure ShowRenameFileEdit(aFile: TFile); override;
     procedure UpdateRenameFileEditPosition; override;
@@ -416,11 +416,12 @@
 {$IF lcl_fullversion >= 093100}
   dgPanel.Options := dgPanel.Options - [goDontScrollPartCell];
 {$ENDIF}
-  DoFileIndexChanged(aRow - dgPanel.FixedRows);
+  DoFileIndexChanged(aRow - dgPanel.FixedRows, dgPanel.TopRow);
 end;
 
 procedure TColumnsFileView.dgPanelTopLeftChanged(Sender: TObject);
 begin
+  if not FUpdatingActiveFile then DoFileIndexChanged(dgPanel.Row - dgPanel.FixedRows, dgPanel.TopRow);
   Notify([fvnVisibleFilePropertiesChanged]);
 end;
 
@@ -679,7 +680,7 @@
   begin
     AVisibleRows := GetFullVisibleRows;
     if iRow < AVisibleRows.First then
-      TopRow := AVisibleRows.First;
+     TopRow := iRow;
     if iRow > AVisibleRows.Last then
       TopRow := iRow - (AVisibleRows.Last - AVisibleRows.First);
   end;
@@ -691,12 +692,13 @@
     MakeVisible(dgPanel.Row);
 end;
 
-procedure TColumnsFileView.SetActiveFile(FileIndex: PtrInt; ScrollTo: Boolean);
+procedure TColumnsFileView.SetActiveFile(FileIndex: PtrInt; ScrollTo: Boolean; aLastTopRowIndex: PtrInt = -1);
 begin
   if not ScrollTo then
     dgPanel.SetColRow(dgPanel.Col, FileIndex + dgPanel.FixedRows)
   else begin
     dgPanel.Row := FileIndex + dgPanel.FixedRows;
+    if (aLastTopRowIndex <> -1) then dgPanel.TopRow := aLastTopRowIndex;
     MakeVisible(dgPanel.Row);
   end;
 end;
@@ -905,10 +907,10 @@
   SetFilesDisplayItems;
   RedrawFiles;
 
-  if SetActiveFileNow(RequestedActiveFile) then
+  if SetActiveFileNow(RequestedActiveFile, FLastTopRowIndex) then
     RequestedActiveFile := ''
   // Requested file was not found, restore position to last active file.
-  else if not SetActiveFileNow(LastActiveFile) then
+  else if not SetActiveFileNow(LastActiveFile, FLastTopRowIndex) then
   // Make sure at least that the previously active file is still visible after displaying file list.
     MakeActiveVisible;
 
Index: src/fileviews/ufileviewwithgrid.pas
===================================================================
--- src/fileviews/ufileviewwithgrid.pas	(revision 8064)
+++ src/fileviews/ufileviewwithgrid.pas	(working copy)
@@ -83,7 +83,7 @@
     procedure RedrawFile(FileIndex: PtrInt); override;
     procedure RedrawFile(DisplayFile: TDisplayFile); override;
     procedure RedrawFiles; override;
-    procedure SetActiveFile(FileIndex: PtrInt; ScrollTo: Boolean); override;
+    procedure SetActiveFile(FileIndex: PtrInt; ScrollTo: Boolean; aLastTopRowIndex: PtrInt = -1); override;
     procedure DoFileUpdated(AFile: TDisplayFile; UpdatedProperties: TFilePropertiesTypes = []); override;
     procedure DoHandleKeyDown(var Key: Word; Shift: TShiftState); override;
     procedure UpdateFlatFileName; override;
@@ -524,11 +524,11 @@
   dgPanel.CalculateColumnWidth;
   SetFilesDisplayItems;
 
-  if SetActiveFileNow(RequestedActiveFile) then
+  if SetActiveFileNow(RequestedActiveFile, FLastTopRowIndex) then
     RequestedActiveFile := ''
   else
     // Requested file was not found, restore position to last active file.
-    SetActiveFileNow(LastActiveFile);
+    SetActiveFileNow(LastActiveFile, FLastTopRowIndex);
 
   Notify([fvnVisibleFilePropertiesChanged]);
 
@@ -703,7 +703,7 @@
   TabHeader.UpdateSorting(Sorting);
 end;
 
-procedure TFileViewWithGrid.SetActiveFile(FileIndex: PtrInt; ScrollTo: Boolean);
+procedure TFileViewWithGrid.SetActiveFile(FileIndex: PtrInt; ScrollTo: Boolean; aLastTopRowIndex: PtrInt = -1);
 var
   ACol, ARow: Integer;
 begin
@@ -756,7 +756,7 @@
 
 procedure TFileViewWithGrid.dgPanelSelection(Sender: TObject; aCol, aRow: Integer);
 begin
-  DoFileIndexChanged(dgPanel.CellToIndex(aCol, aRow));
+  DoFileIndexChanged(dgPanel.CellToIndex(aCol, aRow), dgPanel.TopRow);
   UpdateFooterDetails;
 end;
 
Index: src/fileviews/uorderedfileview.pas
===================================================================
--- src/fileviews/uorderedfileview.pas	(revision 8064)
+++ src/fileviews/uorderedfileview.pas	(working copy)
@@ -54,7 +54,8 @@
   protected
     lblFilter: TLabel;
     quickSearch: TfrmQuickSearch;
-    FLastActiveFileIndex: Integer;
+    FLastActiveFileIndex: PtrInt;
+    FLastTopRowIndex: PtrInt;
     FRangeSelecting: Boolean;
     FRangeSelectionStartIndex: Integer;
     FRangeSelectionEndIndex: Integer;
@@ -63,7 +64,7 @@
     procedure InvertActiveFile;
     procedure AfterChangePath; override;
     procedure CreateDefault(AOwner: TWinControl); override;
-    procedure DoFileIndexChanged(NewFileIndex: PtrInt);
+    procedure DoFileIndexChanged(NewFileIndex, TopRowIndex: PtrInt);
     procedure DoHandleKeyDown(var Key: Word; Shift: TShiftState); override;
     procedure DoHandleKeyDownWhenLoading(var Key: Word; Shift: TShiftState); override;
     procedure DoSelectionChanged; override; overload;
@@ -87,13 +88,13 @@
     procedure SearchFile(SearchTerm,SeparatorCharset: String; SearchOptions: TQuickSearchOptions; InvertSelection: Boolean = False);
     procedure Selection(Key: Word; CurIndex: PtrInt);
     procedure SelectRange(FileIndex: PtrInt);
-    procedure SetActiveFile(FileIndex: PtrInt; ScrollTo: Boolean = True); overload; virtual; abstract;
-    procedure SetLastActiveFile(FileIndex: PtrInt);
+    procedure SetActiveFile(FileIndex: PtrInt; ScrollTo: Boolean = True; aLastTopRowIndex: PtrInt = -1); overload; virtual; abstract;
+    procedure SetLastActiveFile(FileIndex, TopRowIndex: PtrInt);
     {en
        Sets a file as active if the file currently exists.
        @returns(@true if the file was found and selected.)
     }
-    function SetActiveFileNow(aFilePath: String): Boolean;
+    function SetActiveFileNow(aFilePath: String; aLastTopRowIndex: PtrInt = -1): Boolean;
 
   public
     procedure CloneTo(AFileView: TFileView); override;
@@ -210,9 +211,9 @@
   pmOperationsCancel.Parent := Self;
 end;
 
-procedure TOrderedFileView.DoFileIndexChanged(NewFileIndex: PtrInt);
+procedure TOrderedFileView.DoFileIndexChanged(NewFileIndex, TopRowIndex: PtrInt);
 begin
-  if IsFileIndexInRange(NewFileIndex) and (FLastActiveFileIndex <> NewFileIndex) then
+  if IsFileIndexInRange(NewFileIndex) and ( (FLastActiveFileIndex <> NewFileIndex) or (FLastTopRowIndex <> TopRowIndex) ) then
   begin
     if not FRangeSelecting then
     begin
@@ -224,8 +225,7 @@
 
     if not FUpdatingActiveFile then
     begin
-      SetLastActiveFile(NewFileIndex);
-
+      SetLastActiveFile(NewFileIndex, TopRowIndex);
       if Assigned(OnChangeActiveFile) then
         OnChangeActiveFile(Self, FFiles[NewFileIndex].FSFile);
     end;
@@ -780,54 +780,45 @@
   end;
 end;
 
-
-function TOrderedFileView.SetActiveFileNow(aFilePath: String): Boolean;
-
+function TOrderedFileView.SetActiveFileNow(aFilePath: String; aLastTopRowIndex: PtrInt = -1): Boolean;
   procedure SetUpdate(Index: PtrInt);
   begin
     FUpdatingActiveFile := True;
-    SetActiveFile(Index);
+    SetActiveFile(Index, True, aLastTopRowIndex);
     FUpdatingActiveFile := False;
-    SetLastActiveFile(Index);
+    SetLastActiveFile(Index, aLastTopRowIndex);
   end;
 
 var
   Index: PtrInt;
+  PathIsAbsolute: Boolean;
 begin
   if aFilePath <> '' then // find correct cursor position in Panel (drawgrid)
   begin
-    if FileSource.GetPathType(aFilePath) = ptAbsolute then
-    begin
-      for Index := 0 to FFiles.Count - 1 do
-      begin
-        if FFiles[Index].FSFile.FullPath = aFilePath then
-        begin
-          SetUpdate(Index);
-          Exit(True);
-        end;
-      end;
-    end
-    else
+    PathIsAbsolute := FileSource.GetPathType(aFilePath) = ptAbsolute;
+    for Index := 0 to FFiles.Count - 1 do
     begin
-      for Index := 0 to FFiles.Count - 1 do
+      if PathIsAbsolute then
+        Result := (FFiles[Index].FSFile.FullPath = aFilePath)
+      else
+        Result := (FFiles[Index].FSFile.Name = aFilePath);
+      if Result then
       begin
-        if FFiles[Index].FSFile.Name = aFilePath then
-        begin
           SetUpdate(Index);
           Exit(True);
-        end;
       end;
     end;
   end;
   Result := False;
 end;
 
-procedure TOrderedFileView.SetLastActiveFile(FileIndex: PtrInt);
+procedure TOrderedFileView.SetLastActiveFile(FileIndex, TopRowIndex: PtrInt);
 begin
   if IsFileIndexInRange(FileIndex) then
   begin
     LastActiveFile := FFiles[FileIndex].FSFile.FullPath;
     FLastActiveFileIndex := FileIndex;
+    FLastTopRowIndex := TopRowIndex;
   end;
 end;
 
