1
votes

I successfully installed my menu item inside Delphi using INTAServices40 but the problem is - menu is missing the next time Delphi starts?! Actually, two menu items are installed; One under Help menu which is ALWAYS shown (IOTAWizardMenu), but the one under Tools menu (TEST menu item) is missing the next time Delphi starts. How to fix this?

unit TESTMENU;

interface    
uses
   ToolsAPI, Classes, Windows, vcl.Menus, vcl.dialogs;    
type
   TCustomMenuItem = class(TNotifierObject, IOTAWizard, IOTAMenuWizard)
     function GetIDString: string;
     function GetName: string;
     function GetState: TWizardState;
     // Launch the AddIn
     procedure Execute;
     function GetMenuText: string;
   end;

   TCustomMenuHandler = class(TObject)
    // Handle custom menu
     procedure HandleClick(Sender: TObject);
   end;

procedure Register;

implementation    
var
  mnuitem: TMenuItem;
  CustomMenuHandler: TCustomMenuHandler;

procedure TCustomMenuItem.Execute;
begin
  ShowMessage('IOTAWizardMenu based menu item');
end;

function TCustomMenuItem.GetIDString: string;
begin
  Result := 'TMS.MenuSample';
end;

function TCustomMenuItem.GetMenuText: string;
begin
  Result := 'IOTAWizardMenu';
end;

function TCustomMenuItem.GetName: string;
begin
  Result := 'TMSMenuSample';
end;

function TCustomMenuItem.GetState: TWizardState;
begin
  Result := [wsEnabled];
end;

procedure TCustomMenuHandler.HandleClick(Sender: TObject);
begin
  ShowMessage('INTAServices40.MainMenu based menu item');
end;   

procedure AddIDEMenu;
var
  NTAServices: INTAServices40;    
begin
  NTAServices := BorlandIDEServices as INTAServices40;

  // avoid inserting twice
  if NTAServices.MainMenu.Items[9].Find('TEST') = nil then
  begin
    CustomMenuHandler := TCustomMenuHandler.Create;

    mnuitem := TMenuItem.Create(nil);
    mnuitem.Caption := 'TEST';
    mnuitem.OnClick := CustomMenuHandler.HandleClick;
    NTAServices.MainMenu.Items[9].Add(mnuitem)
  end;
end;

procedure RemoveIDEMenu;
var
  NTAServices: INTAServices40;
begin
  if Assigned(mnuitem) then
  begin
    NTAServices := BorlandIDEServices as INTAServices40;
    NTAServices.MainMenu.Items[9].Remove(mnuitem);
    mnuitem.Free;
    if Assigned(CustomMenuHandler) then
      CustomMenuHandler.Free;
  end;
end;

procedure Register;
begin
  AddIDEMenu;
  RegisterPackageWizard(TCustomMenuItem.Create);
end;

initialization
  mnuitem := nil;    
  CustomMenuHandler := nil;    
finalization
  RemoveIDEMenu;
end.

So, my first problem is how to get menu item TEST shown each time Delphi starts.. Also, I would like to add icon next to the menu item TEST. Any directions?

Thank you

EDIT: I just found out my package is delayed loading. Reading the Internet people say ForceDemandLoadState(dlDisable) should be called. But, this is not helping me also....

1
OTA plugins have to be implemented as Packages that are installed into the IDE and loaded each time the IDE is run. Assuming you did create a Package, did you verify that the Package is being loaded on the next IDE restart? - Remy Lebeau
I did check it and it's loading. The problem is - menu item is not showing even if I manually add a package (bpl). Only when I recompile the package the menu item is shown. - Tracer
Which version of Delphi is this? - Ondrej Kelle

1 Answers

1
votes

NTAServices.MainMenu.Items[9] may return different things at different times as the IDE is loading its packages, also there are menu items whose sub-items are managed by the IDE at runtime (e.g. the Window menu).

You could look up the Help menu item component by name:

procedure AddIDEMenu;
var
  HelpMenu: TComponent;
begin
  HelpMenu := Application.MainForm.FindComponent('HelpMenu');
  if (HelpMenu is TMenuItem) and (TMenuItem(HelpMenu).Find('TEST') = nil) then
  begin
    CustomMenuHandler := TCustomMenuHandler.Create;

    mnuitem := TMenuItem.Create(nil);
    mnuitem.Caption := 'TEST';
    mnuitem.OnClick := CustomMenuHandler.HandleClick;

    TMenuItem(HelpMenu).Add(mnuitem);
  end;
end;

procedure RemoveIDEMenu;
var
  HelpMenu: TComponent;
begin
  if Assigned(mnuitem) then
  begin
    HelpMenu := Application.MainForm.FindComponent('HelpMenu');
    if HelpMenu is TMenuItem then
      TMenuItem(HelpMenu).Remove(mnuitem);
    mnuitem.Free;
    CustomMenuHandler.Free;
  end;
end;