lazarus/ide/editorfilemanager.pas
ondrej a914eaa29d IDE: use TLCLGlyphs for IDE buttons
git-svn-id: trunk@57857 -
2018-05-08 23:10:58 +00:00

433 lines
14 KiB
ObjectPascal

unit EditorFileManager;
{$mode objfpc}{$H+}
interface
uses
Classes, sysutils, Forms, Controls, CheckLst, ButtonPanel, StdCtrls, Buttons,
ExtCtrls, Menus, LCLProc, LCLType, IDEImagesIntf, LazIDEIntf, IDEHelpIntf,
SrcEditorIntf, IDEWindowIntf, SourceEditor, LazarusIDEStrConsts,
ListFilterEdit, IDEOptionDefs;
type
{ TEditorFileManagerForm }
TEditorFileManagerForm = class(TForm)
ActivateMenuItem: TMenuItem;
FileCountLabel: TLabel;
MoveDownBtn: TSpeedButton;
MoveUpBtn: TSpeedButton;
FilterPanel: TPanel;
OpenButton: TSpeedButton;
SaveCheckedButton: TBitBtn;
ButtonPanel1: TButtonPanel;
CloseCheckedButton: TBitBtn;
CloseMenuItem: TMenuItem;
Panel1: TPanel;
PopupMenu1: TPopupMenu;
CheckAllCheckBox: TCheckBox;
CheckListBox1: TCheckListBox;
FilterEdit: TListFilterEdit;
SortAlphabeticallyButton: TSpeedButton;
procedure ActivateMenuItemClick(Sender: TObject);
procedure CheckListBox1DblClick(Sender: TObject);
procedure CheckListBox1KeyDown(Sender: TObject; var Key: Word;
Shift: TShiftState);
procedure CheckListBox1KeyPress(Sender: TObject; var Key: char);
procedure CloseButtonClick(Sender: TObject);
procedure DoEditorsChanged(Sender: TObject);
procedure FormKeyDown(Sender: TObject; var Key: Word; Shift: TShiftState);
procedure HelpButtonClick(Sender: TObject);
procedure MoveDownBtnClick(Sender: TObject);
procedure MoveUpBtnClick(Sender: TObject);
procedure CheckListBox1Click(Sender: TObject);
procedure CheckListBox1ItemClick(Sender: TObject; Index: integer);
procedure CloseCheckedButtonClick(Sender: TObject);
procedure PopupMenu1Popup(Sender: TObject);
procedure SaveCheckedButtonClick(Sender: TObject);
procedure CloseMenuItemClick(Sender: TObject);
procedure FormCreate(Sender: TObject);
procedure ActivateButtonClick(Sender: TObject);
procedure CheckAllCheckBoxClick(Sender: TObject);
procedure SortAlphabeticallyButtonClick(Sender: TObject);
private
FSortAlphabetically: boolean;
procedure CloseListItem(ListIndex: integer);
procedure PopulateList;
function SrcEditorByListItem(ListIndex: integer): TSourceEditor;
procedure SetSortAlphabetically(AValue: boolean);
procedure UpdateCheckAllCaption;
procedure UpdateButtons;
procedure UpdateMoveButtons(ListIndex: integer);
public
destructor Destroy; override;
property SortAlphabetically: boolean read FSortAlphabetically write SetSortAlphabetically;
end;
var
EditorFileManagerForm: TEditorFileManagerForm;
procedure ShowEditorFileManagerForm(State: TIWGetFormState = iwgfShowOnTop);
implementation
{$R *.lfm}
procedure ShowEditorFileManagerForm(State: TIWGetFormState);
begin
if EditorFileManagerForm = Nil then
IDEWindowCreators.CreateForm(EditorFileManagerForm,TEditorFileManagerForm,
State=iwgfDisabled,LazarusIDE.OwningComponent)
else if State=iwgfDisabled then
EditorFileManagerForm.DisableAlign;
if State>=iwgfShow then
IDEWindowCreators.ShowForm(EditorFileManagerForm,State=iwgfShowOnTop);
end;
{ TEditorFileManagerForm }
procedure TEditorFileManagerForm.FormCreate(Sender: TObject);
begin
Name := NonModalIDEWindowNames[nmiwEditorFileManager];
SourceEditorManager.RegisterChangeEvent(semEditorCreate, @DoEditorsChanged);
SourceEditorManager.RegisterChangeEvent(semEditorDestroy, @DoEditorsChanged);
PopulateList; // Populate the list with all open editor file names
// Captions
Caption:=lisSourceEditorWindowManager;
ActivateMenuItem.Caption:=lisActivate;
CloseMenuItem.Caption:=lisClose;
CheckAllCheckBox.Caption:=lisCheckAll;
SaveCheckedButton.Caption:=lisSaveAllChecked;
CloseCheckedButton.Caption:=lisCloseAllChecked;
MoveUpBtn.Hint:=lisMoveSelectedUp;
MoveDownBtn.Hint:=lisMoveSelectedDown;
// Icons
PopupMenu1.Images:=IDEImages.Images_16;
ActivateMenuItem.ImageIndex:=IDEImages.LoadImage('laz_open');
CloseMenuItem.ImageIndex:=IDEImages.LoadImage('menu_close');
IDEImages.AssignImage(CloseCheckedButton, 'menu_close_all');
IDEImages.AssignImage(SaveCheckedButton, 'menu_save_all');
IDEImages.AssignImage(MoveUpBtn, 'arrow_up');
IDEImages.AssignImage(MoveDownBtn, 'arrow_down');
// Buttons on FilterPanel
IDEImages.AssignImage(OpenButton, 'laz_open');
OpenButton.Hint:=lisActivateSelected;
SortAlphabeticallyButton.Hint:=lisPESortFilesAlphabetically;
IDEImages.AssignImage(SortAlphabeticallyButton, 'pkg_sortalphabetically');
end;
procedure TEditorFileManagerForm.CheckListBox1Click(Sender: TObject);
var
clb: TCheckListBox;
begin
clb:=Sender as TCheckListBox;
// Enable Activate when there is a selected item.
OpenButton.Enabled:=clb.SelCount>0;
UpdateMoveButtons(clb.ItemIndex);
end;
procedure TEditorFileManagerForm.CheckListBox1ItemClick(Sender: TObject; Index: integer);
var
clb: TCheckListBox;
i: Integer;
HasChecked: Boolean;
begin
clb:=Sender as TCheckListBox;
// Notify the filter edit that item's checked state has changed.
if Index>-1 then
FilterEdit.ItemWasClicked(clb.Items[Index], clb.Checked[Index]);
// Enable save and close buttons when there are checked items.
HasChecked:=False;
for i:=clb.Count-1 downto 0 do
if clb.Checked[i] then begin
HasChecked:=True;
Break;
end;
SaveCheckedButton.Enabled:=HasChecked;
CloseCheckedButton.Enabled:=HasChecked;
CloseMenuItem.Enabled:=HasChecked;
CheckAllCheckBox.Enabled:=clb.Count>0;
// If all items were unchecked, change CheckAllCheckBox state.
if CheckAllCheckBox.Checked and not HasChecked then begin
CheckAllCheckBox.Checked:=HasChecked;
UpdateCheckAllCaption;
end;
CheckListBox1Click(CheckListBox1); // Call also OnClick handler for other controls.
end;
procedure TEditorFileManagerForm.CheckAllCheckBoxClick(Sender: TObject);
var
cb: TCheckBox;
i: Integer;
begin
cb:=Sender as TCheckBox;
UpdateCheckAllCaption;
// Set / reset all CheckListBox1 items.
for i:=0 to CheckListBox1.Count-1 do begin
if CheckListBox1.Checked[i]<>cb.Checked then begin
CheckListBox1.Checked[i]:=cb.Checked;
FilterEdit.ItemWasClicked(CheckListBox1.Items[i], cb.Checked); // Notify the filter
end;
end;
CheckListBox1ItemClick(CheckListBox1, CheckListBox1.Count-1);
end;
procedure TEditorFileManagerForm.SortAlphabeticallyButtonClick(Sender: TObject);
begin
SortAlphabetically:=SortAlphabeticallyButton.Down;
end;
procedure TEditorFileManagerForm.SaveCheckedButtonClick(Sender: TObject);
var
i: Integer;
SrcEdit: TSourceEditor;
begin
for i:=CheckListBox1.Count-1 downto 0 do
if CheckListBox1.Checked[i] then begin
SrcEdit:=SrcEditorByListItem(i);
Assert(Assigned(SrcEdit), 'TEditorFileManagerForm.SaveCheckedButtonClick: SrcEdit is not assigned.');
if (not SrcEdit.CodeBuffer.IsVirtual) and (LazarusIDE.DoSaveEditorFile(SrcEdit, []) <> mrOk) then
DebugLn(['TSourceNotebook.EncodingClicked LazarusIDE.DoSaveEditorFile failed']);
end;
end;
procedure TEditorFileManagerForm.CloseCheckedButtonClick(Sender: TObject);
var
i: Integer;
begin
for i:=CheckListBox1.Count-1 downto 0 do
if CheckListBox1.Checked[i] then
CloseListItem(i);
PopulateList;
UpdateButtons;
end;
procedure TEditorFileManagerForm.PopupMenu1Popup(Sender: TObject);
var
HasSelected: Boolean;
begin
HasSelected:=CheckListBox1.SelCount>0;
ActivateMenuItem.Enabled:=HasSelected;
CloseMenuItem.Enabled:=HasSelected;
end;
procedure TEditorFileManagerForm.CloseMenuItemClick(Sender: TObject);
begin
CloseListItem(CheckListBox1.ItemIndex);
PopulateList;
UpdateButtons;
end;
procedure TEditorFileManagerForm.ActivateMenuItemClick(Sender: TObject);
begin
ActivateButtonClick(nil);
end;
procedure TEditorFileManagerForm.CheckListBox1DblClick(Sender: TObject);
begin
ActivateButtonClick(nil);
end;
procedure TEditorFileManagerForm.CheckListBox1KeyDown(Sender: TObject;
var Key: Word; Shift: TShiftState);
begin
if (ssCtrl in Shift ) and ((Key = VK_UP) or (Key = VK_DOWN)) then begin
if Key = VK_UP then
MoveUpBtnClick(nil)
else
MoveDownBtnClick(nil);
Key:=VK_UNKNOWN;
end;
end;
procedure TEditorFileManagerForm.CheckListBox1KeyPress(Sender: TObject; var Key: char);
begin
if Key = char(VK_RETURN) then
ActivateButtonClick(nil);
end;
procedure TEditorFileManagerForm.CloseButtonClick(Sender: TObject);
begin
Close;
end;
procedure TEditorFileManagerForm.DoEditorsChanged(Sender: TObject);
begin
PopulateList;
end;
procedure TEditorFileManagerForm.FormKeyDown(Sender: TObject; var Key: Word; Shift: TShiftState);
begin
if (Key = VK_ESCAPE) and (Shift = []) then
Close;
end;
procedure TEditorFileManagerForm.HelpButtonClick(Sender: TObject);
begin
LazarusHelp.ShowHelpForIDEControl(Self);
end;
procedure TEditorFileManagerForm.MoveDownBtnClick(Sender: TObject);
var
SrcEdit: TSourceEditor;
i: Integer;
begin
i:=CheckListBox1.ItemIndex;
if (i>-1) and (i<CheckListBox1.Items.Count-1)
and (FilterEdit.Filter='') and not SortAlphabetically then begin
SrcEdit:=SrcEditorByListItem(i);
Assert(Assigned(SrcEdit), 'TEditorFileManagerForm.MoveDownBtnClick: SrcEdit is not assigned.');
if SrcEdit.PageIndex < SrcEdit.SourceNotebook.PageCount-1 then begin
// First move the source editor tab
SrcEdit.SourceNotebook.MoveEditor(SrcEdit.PageIndex, SrcEdit.PageIndex+1);
// Then switch the list items
FilterEdit.Items.Exchange(i, i+1);
FilterEdit.InvalidateFilter;
UpdateMoveButtons(i+1);
end;
end;
end;
procedure TEditorFileManagerForm.MoveUpBtnClick(Sender: TObject);
var
SrcEdit: TSourceEditor;
i: Integer;
begin
i := CheckListBox1.ItemIndex;
if (i > 0) and (FilterEdit.Filter='') and not SortAlphabetically then begin
SrcEdit:=SrcEditorByListItem(i);
Assert(Assigned(SrcEdit), 'TEditorFileManagerForm.MoveUpBtnClick: SrcEdit is not assigned.');
if SrcEdit.PageIndex > 0 then begin
// First move the source editor tab
SrcEdit.SourceNotebook.MoveEditor(SrcEdit.PageIndex, SrcEdit.PageIndex-1);
// Then switch the list items
FilterEdit.Items.Exchange(i, i-1);
FilterEdit.InvalidateFilter;
UpdateMoveButtons(i-1);
end;
end;
end;
procedure TEditorFileManagerForm.ActivateButtonClick(Sender: TObject);
var
i: Integer;
SrcEdit: TSourceEditor;
begin
for i:=0 to CheckListBox1.Count-1 do
if CheckListBox1.Selected[i] then begin // Find first selected.
SrcEdit:=SrcEditorByListItem(CheckListBox1.ItemIndex);
Assert(Assigned(SrcEdit), 'TEditorFileManagerForm.ActivateButtonClick: SrcEdit is not assigned.');
SrcEdit.Activate;
Break;
end;
end;
// Private methods
procedure TEditorFileManagerForm.CloseListItem(ListIndex: integer);
var
SrcEdit: TSourceEditor;
begin
SrcEdit:=SrcEditorByListItem(ListIndex);
Assert(Assigned(SrcEdit), 'TEditorFileManagerForm.CloseListItem: SrcEdit is not assigned.');
LazarusIDE.DoCloseEditorFile(SrcEdit, [cfSaveFirst]);
end;
procedure TEditorFileManagerForm.PopulateList;
// Populate the list with all open editor file names
var
SrcEdit: TSourceEditor;
i, j: Integer;
sw: TSourceNotebook;
Modi: String;
begin
FilterEdit.Items.Clear;
with SourceEditorManager do
for i:=0 to SourceWindowCount-1 do begin
sw:=SourceWindows[i];
Assert(sw.PageCount=sw.EditorCount, 'sw.PageCount<>sw.EditorCount');
for j:=0 to sw.EditorCount-1 do begin
SrcEdit:=sw.FindSourceEditorWithPageIndex(j);
if SrcEdit.Modified then
Modi:='* '
else
Modi:='';
FilterEdit.Items.Add(Modi+SrcEdit.FileName);
end;
end;
FilterEdit.InvalidateFilter;
FileCountLabel.Caption:=Format(dlgFiles,[IntToStr(SourceEditorManager.SourceEditorCount)]);
end;
function TEditorFileManagerForm.SrcEditorByListItem(ListIndex: integer): TSourceEditor;
var
s: String;
begin
s:=CheckListBox1.Items[ListIndex];
if (s<>'') and (s[1]='*') then // Modified indicator
delete(s, 1, 2);
Result:=SourceEditorManager.SourceEditorIntfWithFilename(s);
end;
procedure TEditorFileManagerForm.SetSortAlphabetically(AValue: boolean);
begin
if FSortAlphabetically=AValue then exit;
FSortAlphabetically:=AValue;
SortAlphabeticallyButton.Down:=FSortAlphabetically;
FilterEdit.SortData:=FSortAlphabetically;
FilterEdit.InvalidateFilter;
end;
procedure TEditorFileManagerForm.UpdateCheckAllCaption;
// Caption text: check all / uncheck all
begin
if CheckAllCheckBox.Checked then
CheckAllCheckBox.Caption:=lisUncheckAll
else
CheckAllCheckBox.Caption:=lisCheckAll;
end;
procedure TEditorFileManagerForm.UpdateButtons;
// Update the filter and buttons. Reuse event handlers for it.
begin
FilterEdit.InvalidateFilter;
CheckListBox1ItemClick(CheckListBox1, CheckListBox1.Count-1);
end;
procedure TEditorFileManagerForm.UpdateMoveButtons(ListIndex: integer);
var
SrcEdit: TSourceEditor;
UpEnabled, DownEnabled: Boolean;
begin
UpEnabled:=False;
DownEnabled:=False;
if (ListIndex>-1) and (ListIndex<CheckListBox1.Items.Count)
and (FilterEdit.Filter='') and not SortAlphabetically then begin
//DebugLn(['TEditorFileManagerForm.UpdateMoveButtons: Filename', CheckListBox1.Items[ListIndex], ', ListIndex:', ListIndex]);
SrcEdit:=SrcEditorByListItem(ListIndex);
if Assigned(SrcEdit) then begin
DownEnabled:=(ListIndex<CheckListBox1.Items.Count-1)
and (SrcEdit.PageIndex<SrcEdit.SourceNotebook.PageCount-1);
UpEnabled:=(ListIndex>0) and (SrcEdit.PageIndex>0);
end;
end;
MoveUpBtn.Enabled:=UpEnabled;
MoveDownBtn.Enabled:=DownEnabled;
end;
destructor TEditorFileManagerForm.Destroy;
begin
if SourceEditorManager <> nil then begin
SourceEditorManager.UnRegisterChangeEvent(semEditorCreate, @DoEditorsChanged);
SourceEditorManager.UnRegisterChangeEvent(semEditorDestroy, @DoEditorsChanged);
end;
inherited Destroy;
end;
end.