1 {
2 Copyright (C) 2007 Graeme Geldenhuys (graemeg@gmail.com)
3
4 This library is free software; you can redistribute it and/or modify it
5 under the terms of the GNU Library General Public License as published by
6 the Free Software Foundation; either version 2 of the License, or (at your
7 option) any later version.
8
9 This program is distributed in the hope that it will be useful, but WITHOUT
10 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11 FITNESS FOR A PARTICULAR PURPOSE. See the GNU Library General Public License
12 for more details.
13
14 You should have received a copy of the GNU Library General Public License
15 along with this library; if not, write to the Free Software Foundation,
16 Inc., 51 Franklin Street - Fifth Floor, Boston, MA 02110-1335, USA.
17 }
18
19 unit ToolbarConfig;
20
21 {$mode objfpc}{$H+}
22
23 interface
24
25 uses
26 Classes, SysUtils,
27 // LCL
28 LCLProc, LclIntf, Controls, Forms, Graphics, ExtCtrls, Buttons, StdCtrls,
29 ComCtrls, Menus, ButtonPanel,
30 // LazControls
31 TreeFilterEdit,
32 // LazUtils
33 Laz2_XMLCfg, LazUTF8,
34 // IdeIntf
35 ToolBarIntf, IDEImagesIntf, IDEWindowIntf,
36 // IDE
37 LazarusIDEStrConsts;
38
39 const
40 IDEToolBarConfigVersion = 1; // File version in configuration.
41
42 type
43 { TToolBarConfig }
44
45 TToolBarConfig = class(TForm)
46 btnAdd: TSpeedButton;
47 btnAddDivider: TSpeedButton;
48 btnCancel: TButton;
49 btnHelp: TBitBtn;
50 btnMoveDown: TSpeedButton;
51 btnMoveUp: TSpeedButton;
52 btnOK: TButton;
53 btnRemove: TSpeedButton;
54 FilterEdit: TTreeFilterEdit;
55 lblMenuTree: TLabel;
56 lblToolbar: TLabel;
57 lvToolbar: TListView;
58 miAll: TMenuItem;
59 miCustom: TMenuItem;
60 miDebug: TMenuItem;
61 miDesign: TMenuItem;
62 miHTML: TMenuItem;
63 pnlButtons: TButtonPanel;
64 Splitter1: TSplitter;
65 TV: TTreeView;
66 procedure btnHelpClick(Sender: TObject);
67 procedure FormClose(Sender: TObject; var {%H-}CloseAction: TCloseAction);
68 procedure FormCreate(Sender: TObject);
69 procedure FormDestroy(Sender: TObject);
70 procedure lvToolbarDblClick(Sender: TObject);
71 procedure lvToolbarEnterExit(Sender: TObject);
72 procedure TVDblClick(Sender: TObject);
73 procedure UpdateButtonsState;
74 procedure btnAddClick(Sender: TObject);
75 procedure btnAddDividerClick(Sender: TObject);
76 procedure btnMoveDownClick(Sender: TObject);
77 procedure btnMoveUpClick(Sender: TObject);
78 procedure btnRemoveClick(Sender: TObject);
79 procedure lvToolbarSelectItem(Sender: TObject; {%H-}Item: TListItem;
80 {%H-}Selected: Boolean);
81 procedure TVSelectionChanged(Sender: TObject);
82 private
83 Image: TBitMap;
84 defImageIndex: integer;
85 procedure AddCommand;
86 procedure AddDivider;
87 procedure AddTailItem;
88 procedure AddToolBarItem(CmdItem: TIDEButtonCommand);
89 procedure InsertItem(Item: TListItem);
90 procedure MoveUpDown(aOffset: integer);
NewLvItemnull91 function NewLvItem(aCaption: string): TListItem;
92 procedure RemoveCommand;
93 procedure SetupCaptions;
94 procedure LoadCategories;
95 procedure SortCategories(ACtgList: TStrings);
96 procedure AddMenuItem(ParentNode: TTreeNode; CmdItem: TIDEButtonCommand);
RootNodeCaptionnull97 function RootNodeCaption(CmdItem: TIDEButtonCommand): string;
98 public
99 procedure LoadSettings(SL: TStringList);
100 procedure SaveSettings(SL: TStringList);
101 end;
102
103 { TIDEToolBarOptionsBase }
104
105 TIDEToolBarOptionsBase = class
106 private
107 FButtonNames: TStringList;
108 protected
109 procedure LoadButtonNames(XMLConfig: TXMLConfig; SubPath: String);
110 procedure SaveButtonNames(XMLConfig: TXMLConfig; SubPath: String);
111 public
112 constructor Create;
113 destructor Destroy; override;
114 procedure Clear;
Equalsnull115 function Equals(Opts: TIDEToolBarOptionsBase): boolean; overload;
116 procedure Assign(Source: TIDEToolBarOptionsBase);
117 //procedure Load(XMLConfig: TXMLConfig; Path: String);
118 //procedure Save(XMLConfig: TXMLConfig; Path: String);
119 published
120 property ButtonNames: TStringList read FButtonNames; // write FButtonNames;
121 end;
122
123 { TIDEToolbarBase }
124
125 TIDEToolbarBase = class(TComponent)
126 private
127 protected
128 FToolBar: TToolBar;
129 procedure AddButton(ACommand: TIDEButtonCommand);
130 procedure AddDivider;
131 procedure CopyFromOptions(Options: TIDEToolBarOptionsBase);
132 procedure PositionAtEnd(AToolBar: TToolBar; AButton: TToolButton);
133 procedure PostCopyOptions; virtual;
134 public
135 //constructor Create(AOwner: TComponent); override;
136 //destructor Destroy; override;
137 property ToolBar: TToolBar read FToolBar;
138 end;
139
140 const
141 cIDEToolbarDivider = '---------------';
142 cTailItemCaption = ' ';
143
ShowToolBarConfignull144 function ShowToolBarConfig(aNames: TStringList): TModalResult;
145
146
147 implementation
148
149 {$R *.lfm}
150
ShowToolBarConfignull151 function ShowToolBarConfig(aNames: TStringList): TModalResult;
152 var
153 Conf: TToolBarConfig;
154 begin
155 Conf := TToolBarConfig.Create(Nil);
156 try
157 if Assigned(aNames) then
158 Conf.LoadSettings(aNames);
159 Result := Conf.ShowModal;
160 if (Result = mrOK) and Assigned(aNames) then
161 Conf.SaveSettings(aNames);
162 finally
163 Conf.Free;
164 end;
165 end;
166
167 { TToolBarConfig }
168
169 procedure TToolBarConfig.FormCreate(Sender: TObject);
170 begin
171 inherited;
172 pnlButtons.Color := clBtnFace;
173 // load button images
174 IDEImages.AssignImage(btnAdd, 'arrow__darkgreen_right');
175 IDEImages.AssignImage(btnRemove, 'arrow__darkred_left');
176 IDEImages.AssignImage(btnMoveUp, 'arrow__darkgreen_up');
177 IDEImages.AssignImage(btnMoveDown, 'arrow__darkgreen_down');
178 //IDEImages.AssignImage(btnAddDivider, 'menu_divider16'); // uncomment if 'menu_divider16' exists (currently not)
179
180 btnAddDivider.Caption := '---';
181 btnAdd.Hint := lisCoolBarAddSelected;
182 btnRemove.Hint := lisCoolBarRemoveSelected;
183 btnMoveUp.Hint := lisCoolBarMoveSelectedUp;
184 btnMoveDown.Hint := lisCoolBarMoveSelectedDown;
185 btnAddDivider.Hint:= lisCoolBarAddDivider;
186
187 TV.Images := IDEImages.Images_16;
188 lvToolbar.SmallImages := IDEImages.Images_16;
189 // default image to be used when none is available
190 defImageIndex := IDEImages.LoadImage('execute');
191
192 Image := TBitmap.Create;
193 SetupCaptions;
194 LoadCategories;
195 IDEDialogLayoutList.ApplyLayout(Self);
196 end;
197
198 procedure TToolBarConfig.FormClose(Sender: TObject; var CloseAction: TCloseAction);
199 begin
200 IDEDialogLayoutList.SaveLayout(Self);
201 end;
202
203 procedure TToolBarConfig.FormDestroy(Sender: TObject);
204 begin
205 Image.Free;
206 end;
207
208 procedure TToolBarConfig.lvToolbarDblClick(Sender: TObject);
209 begin
210 RemoveCommand;
211 end;
212
213 procedure TToolBarConfig.lvToolbarEnterExit(Sender: TObject);
214 begin
215 UpdateButtonsState;
216 end;
217
218 procedure TToolBarConfig.TVDblClick(Sender: TObject);
219 begin
220 AddCommand;
221 end;
222
223 procedure TToolBarConfig.btnHelpClick(Sender: TObject);
224 begin
225 OpenUrl('http://wiki.freepascal.org/IDE_Window:_Toolbar_Config');
226 end;
227
228 procedure TToolBarConfig.UpdateButtonsState;
229 var
230 I: Integer;
231 begin
232 I := lvToolbar.ItemIndex;
233 btnAdd.Enabled := Assigned(TV.Selected) and Assigned(TV.Selected.Data);
234 btnRemove.Enabled := (I>-1) and (I<lvToolbar.Items.Count-1);
235 btnMoveUp.Enabled := (I>0) and (I<lvToolbar.Items.Count-1);
236 btnMoveDown.Enabled := (I>-1) and (I<lvToolbar.Items.Count-2);
237 btnAddDivider.Enabled := True;
238 end;
239
240 procedure TToolBarConfig.TVSelectionChanged(Sender: TObject);
241 begin
242 UpdateButtonsState;
243 end;
244
245 procedure TToolBarConfig.InsertItem(Item: TListItem);
246 begin
247 lvToolbar.ItemIndex := -1;
248 lvToolbar.Selected := nil;
249 if Item.Index < lvToolbar.Items.Count then
250 lvToolbar.ItemIndex := Item.Index+1
251 else
252 lvToolbar.ItemIndex := Item.Index;
253 end;
254
255 procedure TToolBarConfig.btnAddClick(Sender: TObject);
256 begin
257 AddCommand;
258 end;
259
NewLvItemnull260 function TToolBarConfig.NewLvItem(aCaption: string): TListItem;
261 var
262 I: Integer;
263 begin
264 I := lvToolbar.ItemIndex;
265 if I = -1 then
266 I := lvToolbar.Items.Count-1; // Add before the last empty item.
267 Result := lvToolbar.Items.Insert(I);
268 Result.Caption := aCaption;
269 end;
270
271 procedure TToolBarConfig.AddCommand;
272 var
273 Node: TTreeNode;
274 CmdCaption: string;
275 lvItem: TListItem;
276 begin
277 Node := TV.Selected;
278 if (Node = Nil) or (Node.Data = Nil) then
279 Exit;
280 CmdCaption := TIDEButtonCommand(Node.Data).Caption;
281 DeleteAmpersands(CmdCaption);
282 lvItem := NewLvItem(CmdCaption);
283 lvItem.Data := Node.Data;
284 if Node.ImageIndex > -1 then
285 lvItem.ImageIndex := Node.ImageIndex
286 else
287 lvItem.ImageIndex := defImageIndex;
288 InsertItem(lvItem); // Add the newly created item to ListView.
289 // Update selection in TreeView.
290 Node := TV.Selected.GetNext;
291 TV.Selected.Visible := False;
292 if Node <> nil then
293 TV.Selected := Node;
294 UpdateButtonsState;
295 end;
296
297 procedure TToolBarConfig.RemoveCommand;
298 Var
299 Cmd: TIDEButtonCommand;
300 Node: TTreeNode;
301 I: Integer;
302 begin
303 I := lvToolbar.ItemIndex;
304 if (I<0) or (I>=lvToolbar.Items.Count-1) then Exit;
305 Cmd := TIDEButtonCommand(lvToolbar.Items[I].Data);
306 lvToolbar.Items.Delete(I);
307 {$IF DEFINED(LCLQt) or DEFINED(LCLQt5)}
308 lvToolbar.ItemIndex := -1; // Try to make LCLQt behave.
309 lvToolbar.ItemIndex := I;
310 {$ENDIF}
311 lvToolbar.Selected := lvToolbar.Items[I];
312 // Show the command as available again in TreeView.
313 if Assigned(Cmd) then
314 begin
315 Node:= TV.Items.FindNodeWithData(Cmd);
316 if Node<>nil then
317 Node.Visible:= True;
318 end;
319 UpdateButtonsState;
320 end;
321
322 procedure TToolBarConfig.btnAddDividerClick(Sender: TObject);
323 var
324 lvItem: TListItem;
325 begin
326 lvItem := NewLvItem(cIDEToolbarDivider);
327 lvItem.ImageIndex := -1;
328 InsertItem(lvItem);
329 UpdateButtonsState;
330 end;
331
332 procedure TToolBarConfig.btnRemoveClick(Sender: TObject);
333 begin
334 RemoveCommand;
335 end;
336
337 procedure TToolBarConfig.lvToolbarSelectItem(Sender: TObject;
338 Item: TListItem; Selected: Boolean);
339 begin
340 UpdateButtonsState;
341 end;
342
343 procedure TToolBarConfig.MoveUpDown(aOffset: integer);
344 var
345 Index1,Index2: Integer;
346 begin
347 Index1 := lvToolbar.ItemIndex;
348 Index2 := Index1 + aOffset;
349 lvToolbar.Items.Exchange(Index1,Index2);
350 lvToolbar.Items[Index1].Selected := False;
351 lvToolbar.Items[Index2].Selected := False;
352 lvToolbar.ItemIndex:= -1;
353 lvToolbar.Selected := Nil;
354 lvToolbar.ItemIndex:= Index2;
355 lvToolbar.Selected := lvToolbar.Items[Index2];
356 end;
357
358 procedure TToolBarConfig.btnMoveDownClick(Sender: TObject);
359 begin
360 if (lvToolbar.ItemIndex<0) or (lvToolbar.ItemIndex>=lvToolbar.Items.Count-2) then
361 Exit;
362 MoveUpDown(1);
363 end;
364
365 procedure TToolBarConfig.btnMoveUpClick(Sender: TObject);
366 begin
367 if (lvToolbar.ItemIndex<1) or (lvToolbar.ItemIndex>=lvToolbar.Items.Count-1) then
368 Exit;
369 MoveUpDown(-1);
370 end;
371
372 procedure TToolBarConfig.SetupCaptions;
373 begin
374 Caption := lisToolbarConfiguration;
375 lblMenuTree.Caption := lisCoolbarAvailableCommands;
376 lblToolbar.Caption := lisCoolbarToolbarCommands;
377 end;
378
379 procedure TToolBarConfig.LoadCategories;
380 var
381 i, l: integer;
382 xCategory: TIDEToolButtonCategory;
383 xCaption: string;
384 Node: TTreeNode;
385 SortedCtgList: TStringListUTF8Fast;
386 begin
387 TV.Items.BeginUpdate;
388 SortedCtgList := TStringListUTF8Fast.Create;
389 try
390 SortedCtgList.OwnsObjects := False;
391 for i := 0 to IDEToolButtonCategories.Count-1 do
392 begin
393 xCategory := IDEToolButtonCategories[i];
394 SortedCtgList.AddObject(xCategory.Description, xCategory);
395 end;
396 SortCategories(SortedCtgList);
397
398 TV.Items.Clear;
399 for i := 0 to SortedCtgList.Count-1 do
400 begin
401 xCaption := SortedCtgList[i];
402 xCategory := SortedCtgList.Objects[i] as TIDEToolButtonCategory;
403 DeleteAmpersands(xCaption);
404 Node := TV.Items.AddChild(nil, Format('%s', [xCaption]));
405 for l := 0 to xCategory.ButtonCount-1 do
406 AddMenuItem(Node, xCategory.Buttons[l]);
407 end;
408 finally
409 SortedCtgList.Free;
410 TV.Items.EndUpdate;
411 end;
412 end;
413
414 procedure TToolBarConfig.SortCategories(ACtgList: TStrings);
415 var
416 NewIndex: Integer;
417
418 procedure MoveItem(s: String);
419 var
420 OldIndex: Integer;
421 begin
422 OldIndex := ACtgList.IndexOf(s);
423 if (OldIndex<0) or (NewIndex>=ACtgList.Count) then Exit;
424 ACtgList.Move(OldIndex, NewIndex);
425 Inc(NewIndex);
426 end;
427
428 begin
429 NewIndex := 0;
430 MoveItem(srkmCatFileMenu);
431 MoveItem(srkmCatCmdCmd);
432 MoveItem(srkmCatSelection);
433 MoveItem(srkmCatMacroRecording);
434 MoveItem(srkmCatSearchReplace);
435 MoveItem(srkmCatMarker);
436 MoveItem(srkmCatViewMenu);
437 MoveItem(srkmCatCodeTools);
438 MoveItem(srkmCatEditing);
439 MoveItem(srkmCatProjectMenu);
440 MoveItem(srkmCatRunMenu);
441 MoveItem(srkmCatPackageMenu);
442 MoveItem(srkmCatToolMenu);
443 MoveItem(srkmCatSrcNoteBook);
444 MoveItem(srkmCarHelpMenu);
445 end;
446
447 procedure TToolBarConfig.AddMenuItem(ParentNode: TTreeNode; CmdItem: TIDEButtonCommand);
448 var
449 Node: TTreeNode;
450 begin
451 if CmdItem.Caption = '-' then Exit; // divider
452 Node := TV.Items.AddChild(ParentNode, Format('%s', [CmdItem.GetCaptionWithShortCut]));
453 Node.ImageIndex := CmdItem.ImageIndex;
454 Node.SelectedIndex := CmdItem.ImageIndex;
455 Node.Data := CmdItem;
456 end;
457
TToolBarConfig.RootNodeCaptionnull458 function TToolBarConfig.RootNodeCaption(CmdItem: TIDEButtonCommand): string;
459 begin
460 case CmdItem.Caption of
461 'IDEMainMenu': Result := lisCoolbarIDEMainMenu; // mnuMain
462 'SourceTab': Result := lisCoolbarSourceTab; // SourceTabMenuRootName
463 'SourceEditor': Result := lisCoolbarSourceEditor; // SourceEditorMenuRootName
464 'Messages': Result := lisCoolbarMessages; // MessagesMenuRootName
465 'Code Explorer': Result := lisCoolbarCodeExplorer; // CodeExplorerMenuRootName
466 'CodeTemplates': Result := lisCoolbarCodeTemplates; // CodeTemplatesMenuRootName
467 'Designer': Result := lisCoolbarDesigner; // DesignerMenuRootName
468 'PackageEditor': Result := lisCoolbarPackageEditor; // PackageEditorMenuRootName
469 'PackageEditorFiles': Result := lisCoolbarPackageEditorFiles // PackageEditorMenuFilesRootName
470 else Result := CmdItem.Caption;
471 end;
472 end;
473
474 procedure TToolBarConfig.AddToolBarItem(CmdItem: TIDEButtonCommand);
475 Var
476 Node: TTreeNode;
477 lvItem: TListItem;
478 begin
479 if CmdItem=Nil then Exit;
480 lvItem := lvToolbar.Items.Add;
481 lvItem.Caption := CmdItem.GetCaptionWithShortCut;
482 lvItem.Data := CmdItem;
483 if CmdItem.ImageIndex > -1 then
484 lvItem.ImageIndex := CmdItem.ImageIndex
485 else
486 lvItem.ImageIndex := defImageIndex;
487 Node := TV.Items.FindNodeWithData(CmdItem);
488 if Node<>nil then
489 Node.Visible := False;
490 end;
491
492 procedure TToolBarConfig.AddDivider;
493 var
494 lvItem: TListItem;
495 begin
496 lvItem := lvToolbar.Items.Add;
497 lvItem.Caption := cIDEToolbarDivider;
498 lvItem.ImageIndex := -1;
499 end;
500
501 procedure TToolBarConfig.AddTailItem;
502 // An extra item at the end of list so that new command can be inserted there.
503 // TToolBarConfig.SaveSettings excludes this item from saving.
504 // In lvToolbar this item may only be selected, any actions with it are prohibited.
505 var
506 lvItem: TListItem;
507 begin
508 lvItem := lvToolbar.Items.Add;
509 lvItem.Caption := cTailItemCaption;
510 end;
511
512 procedure TToolBarConfig.LoadSettings(SL: TStringList);
513 var
514 I: Integer;
515 Value: string;
516 Cmd: TIDEButtonCommand;
517 begin
518 for I := 0 to SL.Count - 1 do
519 begin
520 Value := SL[I];
521 if Value = '' then Continue;
522 if Value = cIDEToolbarDivider then
523 AddDivider // Add divider.
524 else
525 begin
526 Cmd := IDEToolButtonCategories.FindItemByMenuPathOrName(Value);
527 AddToolBarItem(Cmd); // Add command.
528 if Value <> SL[I] then
529 DebugLn(['TToolBarConfig.LoadSettings: SL[I]=', SL[I], ', Value=', Value]);
530 SL[I] := Value;
531 end;
532 end;
533 AddTailItem; // Add tail item at the end.
534 lvToolbar.ItemIndex:=lvToolbar.Items.Count-1;
535 end;
536
537 procedure TToolBarConfig.SaveSettings(SL: TStringList);
538 var
539 lvItem: TListItem;
540 Cmd: TIDEButtonCommand;
541 I: Integer;
542 begin
543 SL.Clear;
544 for I := 0 to lvToolbar.Items.Count - 2 do // excluding tail item
545 begin
546 lvItem := lvToolbar.Items[I];
547 Cmd := TIDEButtonCommand(lvItem.Data);
548 if lvItem.Caption = cIDEToolbarDivider then
549 SL.Add(cIDEToolbarDivider)
550 else begin
551 Assert(Assigned(Cmd), 'TToolBarConfig.SaveSettings: Cmd = Nil.');
552 SL.Add(Cmd.Name);
553 end;
554 end;
555 end;
556
557 { TIDEToolBarOptionsBase }
558
559 constructor TIDEToolBarOptionsBase.Create;
560 begin
561 FButtonNames := TStringList.Create;
562 end;
563
564 destructor TIDEToolBarOptionsBase.Destroy;
565 begin
566 FButtonNames.Free;
567 inherited Destroy;
568 end;
569
570 procedure TIDEToolBarOptionsBase.Clear;
571 begin
572 FButtonNames.Clear;
573 end;
574
Equalsnull575 function TIDEToolBarOptionsBase.Equals(Opts: TIDEToolBarOptionsBase): boolean;
576 begin
577 Result := FButtonNames.Equals(Opts.FButtonNames);
578 end;
579
580 procedure TIDEToolBarOptionsBase.Assign(Source: TIDEToolBarOptionsBase);
581 begin
582 FButtonNames.Assign(Source.FButtonNames);
583 end;
584
585 procedure TIDEToolBarOptionsBase.LoadButtonNames(XMLConfig: TXMLConfig; SubPath: String);
586 var
587 ButtonCount: Integer;
588 ButtonName: string;
589 I, FileVersion: Integer;
590 begin
591 FileVersion := XMLConfig.GetValue(SubPath + 'Version', 0);
592 ButtonCount := XMLConfig.GetValue(SubPath + 'Count', 0);
593 if (FileVersion < 1) and (ButtonCount = 0) then // Old format
594 ButtonCount := XMLConfig.GetValue(SubPath + 'ButtonCount/Value', 0);
595 for I := 1 to ButtonCount do
596 begin
597 ButtonName := XMLConfig.GetValue(SubPath + 'Button' + IntToStr(I) + '/Name', '');
598 if (FileVersion < 1) and (ButtonName = '') then // Old format
599 ButtonName := XMLConfig.GetValue(SubPath + 'Buttons/Name' + IntToStr(I) + '/Value', '');
600 if ButtonName <> '' then
601 ButtonNames.Add(ButtonName);
602 end;
603 end;
604
605 procedure TIDEToolBarOptionsBase.SaveButtonNames(XMLConfig: TXMLConfig; SubPath: String);
606 var
607 I: Integer;
608 begin
609 XMLConfig.SetValue(SubPath + 'Version', IDEToolBarConfigVersion);
610 XMLConfig.SetDeleteValue(SubPath + 'Count', ButtonNames.Count, 0);
611 for I := 0 to ButtonNames.Count-1 do
612 XMLConfig.SetDeleteValue(SubPath + 'Button' + IntToStr(I+1) + '/Name', ButtonNames[I], '');
613 end;
614
615 { TIDEToolbarBase }
616
617 procedure TIDEToolbarBase.AddButton(ACommand: TIDEButtonCommand);
618 var
619 B: TIDEToolButton;
620 begin
621 B := ACommand.ToolButtonClass.Create(FToolBar);
622 B.Hint := ACommand.GetHintOrCaptionWithShortCut;
623 B.Enabled := ACommand.Enabled;
624 // If we have a image, use it. Otherwise supply a default.
625 if ACommand.ImageIndex <> -1 then
626 B.ImageIndex := ACommand.ImageIndex
627 else
628 B.ImageIndex := IDEImages.LoadImage('execute');
629 B.Style := tbsButton;
630 B.Item := ACommand;
631 PositionAtEnd(FToolBar, B);
632 ACommand.ToolButtonAdded(B);
633 end;
634
635 procedure TIDEToolbarBase.AddDivider;
636 var
637 B: TToolButton;
638 begin
639 B := TToolButton.Create(FToolBar);
640 B.Style := tbsDivider;
641 PositionAtEnd(FToolBar, B);
642 end;
643
644 procedure TIDEToolbarBase.CopyFromOptions(Options: TIDEToolBarOptionsBase);
645 var
646 Cmd: TIDEButtonCommand;
647 ButtonName: string;
648 i: Integer;
649 begin
650 FToolBar.BeginUpdate;
651 try
652 for i := 0 to Options.ButtonNames.Count-1 do
653 begin
654 ButtonName := Options.ButtonNames[i];
655 if ButtonName = cIDEToolbarDivider then
656 AddDivider
657 else
658 begin
659 Cmd := IDEToolButtonCategories.FindItemByMenuPathOrName(ButtonName);
660 Options.ButtonNames[i] := ButtonName;
661 if Assigned(Cmd) then
662 AddButton(Cmd);
663 end;
664 end;
665 PostCopyOptions;
666 finally
667 FToolBar.EndUpdate;
668 end;
669 end;
670
671 procedure TIDEToolbarBase.PositionAtEnd(AToolBar: TToolBar; AButton: TToolButton);
672 // position the button next to the last button
673 var
674 SiblingButton: TToolButton;
675 begin
676 if AToolBar.ButtonCount > 0 then
677 begin
678 SiblingButton := AToolBar.Buttons[AToolBar.ButtonCount-1];
679 AButton.SetBounds(SiblingButton.Left + SiblingButton.Width,
680 SiblingButton.Top, AButton.Width, AButton.Height);
681 end;
682 AButton.Parent := AToolBar;
683 end;
684
685 procedure TIDEToolbarBase.PostCopyOptions;
686 begin
687 // Can be overridden.
688 end;
689
690 end.
691
692