Sign in Join

Live chat for Free Pascal, Lazarus, Delphi and every Pascal programmer.

Mailing lists / lazarus / 2015-08

help needed making an ide extension

5 messages · 2 people ·

Reply by email Subscribe to this list Your subscription

Read-only archive. Use j and k to move between messages.

Marc Santhoff

Hi,

I'd like to try building an extension to Lazarus. After reading a lot of

http://wiki.lazarus.freepascal.org/Extending_the_IDE#See_also

I think I'm starting to understand how this can be done. But some questions are left open:

1. Is it correct that to make an extension basically all I have to do is write the code that
- adds a menu entry for starting the code
- save it as a lazarus package and check "register in ide" (or the like ;)
and that's the basis for doing something useful?

2. When I want the user to select a form for the ide expert to work on, a list of available forms is needed. Is iterating over all the projects files and getting the form of a file the right way to go? Additionally if yes:

The code there:

http://wiki.lazarus.freepascal.org/Extending_the_IDE#Get_unit.2C_designer.2C_form_of_a_file

looks OK, but doesn't it open all the files of a project? And does

// get form
aForm:=aDesigner.Form;

give NIL if the file has no form?

3. How do I create a new component on a form?
For doing so one would need at least a reference to the active form and second a reference to the active component to use as parent.

Afterwards, will the new component created and have owner, parent and essential properties set and then added, like I would do in any other program creating components in code at runtime or is there another way (sth. like "IDEDoCreateComponetntAndAdd(newcomponent.class)")?

If there is an example doing all of this stuff, please point me there. After browsing some intresting names in lazarus/examples I haven't found what's missing.

TIA,
Marc

Marc Santhoff

Reply by email

Mattias Gaertner
to Marc Santhoff
Show quoted text 7 lines
[...] 1. Is it correct that to make an extension basically all I have to do is write the code that - adds a menu entry for starting the code - save it as a lazarus package and check "register in ide" (or the like ;) and that's the basis for doing something useful?

Yes, see for example examples/exploremenu.

2. When I want the user to select a form for the ide expert to work on, a list of available forms is needed. Is iterating over all the projects files and getting the form of a file the right way to go?

It depends on what you mean with "available".
For example a project can also access the forms of packages.

Show quoted text 7 lines
Additionally if yes: The code there: http://wiki.lazarus.freepascal.org/Extending_the_IDE#Get_unit.2C_designer.2C_form_of_a_file looks OK, but doesn't it open all the files of a project?

It opens all forms of the project.

Show quoted text 6 lines
And does // get form aForm:=aDesigner.Form; give NIL if the file has no form?

aDesigner will be nil.

3. How do I create a new component on a form? For doing so one would need at least a reference to the active form and second a reference to the active component to use as parent.

Adding a component can be complex.
See designer/designer.pp TDesigner.MouseUpOnControl AddComponent.

Afterwards, will the new component created and have owner, parent and essential properties set and then added, like I would do in any other program creating components in code at runtime or is there another way (sth. like "IDEDoCreateComponetntAndAdd(newcomponent.class)")?

Maybe such a function can be added to the IDEIntf. Can you give some more details what you are trying to achieve?

If there is an example doing all of this stuff, please point me there. After browsing some intresting names in lazarus/examples I haven't found what's missing.

Mattias

Reply by email

Marc Santhoff
to Mattias Gaertner
Mattias Gaertner wrote 12 lines
On Wed, 12 Aug 2015 21:16:22 +0200 Marc Santhoff wrote: >[...] > 1. Is it correct that to make an extension basically all I have to do is > write the code that > - adds a menu entry for starting the code > - save it as a lazarus package and check "register in ide" (or the > like ;) > and that's the basis for doing something useful? Yes, see for example examples/exploremenu.

Good example.

I do not fully understand the creation mechanism. I see an extra register procedure in "frmexploremenu.pas" that actually sets the menu entry. I thought a constructor of the extension class would be called. But since it is a modal form that is done by execution of the menu code.

Instead there is a notify event "FormCreate()", where is that one called? Is it done that way by convention? Did I miss some piece of documentation?

Show quoted text 6 lines
> 2. When I want the user to select a form for the ide expert to work on, > a list of available forms is needed. Is iterating over all the projects > files and getting the form of a file the right way to go? It depends on what you mean with "available". For example a project can also access the forms of packages.

Available means all forms the user has created in his own lazarus project. He will want to place components there and forms from foreign packages are r/o, me thinks. Except when actively working on an opened package.

Hmm, you're right, not easy to distinguish which is which.

Show quoted text 9 lines
> Additionally if yes: > > The code there: > > http://wiki.lazarus.freepascal.org/Extending_the_IDE#Get_unit.2C_designer.2C_form_of_a_file > > looks OK, but doesn't it open all the files of a project? It opens all forms of the project.

OK, not what I want. What strategy can be used to get a list of forms in the users project without having to open them all?

Show quoted text 8 lines
> And does > > // get form > aForm:=aDesigner.Form; > > give NIL if the file has no form? aDesigner will be nil.

OK.

Show quoted text 6 lines
> 3. How do I create a new component on a form? > For doing so one would need at least a reference to the active form and > second a reference to the active component to use as parent. Adding a component can be complex. See designer/designer.pp TDesigner.MouseUpOnControl AddComponent.

Uff. Lots of safety belts, some tricky looking code for calculating bounds, but in general it answers my question.

Seems to be necessary to inform the IDE about changing the form.

Show quoted text 6 lines
> Afterwards, will the new component created and have owner, parent and > essential properties set and then added, like I would do in any other > program creating components in code at runtime or is there another way > (sth. like "IDEDoCreateComponetntAndAdd(newcomponent.class)")? Maybe such a function can be added to the IDEIntf.

In principle making something like "designer/designer.pp TDesigner.MouseUpOnControl AddComponent" publicly available would suffice.

Can you give some more details what you are trying to achieve?

I'm only learning how to do basic actions. Playing around, that is.

Currently it is planned to show a list of available forms and let the user select one. Then he would select the parent component for one or more new components to insert. All done from a modal form, and if feasible it will evolve to some sort of multi step "wizard" or "assistant" dialog triggering complex actions.

Many thanks,
Marc

Marc Santhoff

Reply by email

Mattias Gaertner
to Marc Santhoff
Show quoted text 11 lines
[...] Good example. I do not fully understand the creation mechanism. I see an extra register procedure in "frmexploremenu.pas" that actually sets the menu entry. I thought a constructor of the extension class would be called. But since it is a modal form that is done by execution of the menu code. Instead there is a notify event "FormCreate()", where is that one called? Is it done that way by convention? Did I miss some piece of documentation?

It is set by the lfm, which is parsed in the forms constructor.

Show quoted text 5 lines
[...] > It opens all forms of the project. OK, not what I want. What strategy can be used to get a list of forms in the users project without having to open them all?

If you need the list of all units with designer, you can simply search for lfm files.
If you want only specific classes, you have to check each lfm.

Show quoted text 11 lines
[...] > > Afterwards, will the new component created and have owner, parent and > > essential properties set and then added, like I would do in any other > > program creating components in code at runtime or is there another way > > (sth. like "IDEDoCreateComponetntAndAdd(newcomponent.class)")? > > Maybe such a function can be added to the IDEIntf. In principle making something like "designer/designer.pp TDesigner.MouseUpOnControl AddComponent" publicly available would suffice.

It needs various parameters:
ComponentClass
ParentComponent
Left,Top,
Optional: Width,Height
Optional: Name

Would that suffice?

Show quoted text 7 lines
> Can you give some more details what you are trying to achieve? I'm only learning how to do basic actions. Playing around, that is. Currently it is planned to show a list of available forms and let the user select one. Then he would select the parent component for one or more new components to insert.

Just an idea: Why not select the form and parent component, by right clicking on the parent component and start the wizard via a menu item in the popup menu?

All done from a modal form, and if feasible it will evolve to some sort of multi step "wizard" or "assistant" dialog triggering complex actions.

Mattias

Reply by email

Marc Santhoff
to Mattias Gaertner
Mattias Gaertner wrote 16 lines
On Thu, 13 Aug 2015 00:06:34 +0200 Marc Santhoff wrote: >[...] > Good example. > > I do not fully understand the creation mechanism. I see an extra > register procedure in "frmexploremenu.pas" that actually sets the menu > entry. I thought a constructor of the extension class would be called. > But since it is a modal form that is done by execution of the menu code. > > Instead there is a notify event "FormCreate()", where is that one > called? Is it done that way by convention? Did I miss some piece of > documentation? It is set by the lfm, which is parsed in the forms constructor.

I see, time to activate some code in the IDE instead of only reading it.

Show quoted text 9 lines
>[...] > > It opens all forms of the project. > > OK, not what I want. What strategy can be used to get a list of forms in > the users project without having to open them all? If you need the list of all units with designer, you can simply search for lfm files. If you want only specific classes, you have to check each lfm.

Simple and effective. Beautiful.

Show quoted text 22 lines
>[...] > > > Afterwards, will the new component created and have owner, parent and > > > essential properties set and then added, like I would do in any other > > > program creating components in code at runtime or is there another way > > > (sth. like "IDEDoCreateComponetntAndAdd(newcomponent.class)")? > > > > Maybe such a function can be added to the IDEIntf. > > In principle making something like "designer/designer.pp > TDesigner.MouseUpOnControl AddComponent" publicly available would > suffice. It needs various parameters: ComponentClass ParentComponent Left,Top, Optional: Width,Height Optional: Name Would that suffice? From my POV it would, although I'm not the most experienced extension

developer. ;)

Show quoted text 11 lines
> > Can you give some more details what you are trying to achieve? > > I'm only learning how to do basic actions. Playing around, that is. > > Currently it is planned to show a list of available forms and let the > user select one. Then he would select the parent component for one or > more new components to insert. Just an idea: Why not select the form and parent component, by right clicking on the parent component and start the wizard via a menu item in the popup menu?

Neat, would save some dialog space and maybe one step. For usability there should be a menu item at the standard location, but that's another question.

Thanks again,
Marc

Marc Santhoff

Reply by email