How to define events

Hi

Currently I’m playing around with modules, trying to find a reason why, when and how to use them.

I defined a form with a navigation bar in a module and want to use this bar in another solution. Is it possible to define an event on that form in the module (e.g. onNavigationItemSelected) and how could it be done? I then would like to “listen” to this event in the other solution and react to that event.

This question is not limited to modules. I imagine same behavior for forms in the same solution.

The only way I currently found how a module can share its information (state, not events) are globals. Which actually is not my favorite way of programming.

Thanks for any help and kind regards
Birgit

When I understand what you ask for I would say use application.getMethodTriggerElementName(). That will give you the last element that fired an on action event.

birgit:
The only way I currently found how a module can share its information (state, not events) are globals. Which actually is not my favorite way of programming.

I agree. There are at least 2 ways around this issue;

  1. Form-level variables. Omit the ‘var’. Just use variables without declaring them. I use these now and then.
  2. Virtual table columns. Create calulated fields in a table with calculation ‘;’ – in other words the calc returns nothing. These fields can be used just like any other fields, but their values are local to the current user, and are lost when the user exits Servoy. I use these a lot.

Hello

Thank you for your responses. I read your answers several times. I think they did not answer my question. So I ask again and try to explain better what I’m looking for:

I would like to define (program) an event on a form. Lets say I name the event “onDomainItemSelected”. And I raise this event, whenever an item in the list of domains is selcted. By raising the event, I notify whoever is interested in this event. In my case all forms, using the navigation form, are interested. They need to listen to this event (hook). And react appropriate.

Can I define events and raise them? Can I listen to events? And how can it be done?

Thanks and kind regards
Birgit

I think not. You would have to build a plugin for this that listens to the selection as you call it.

You can fire a method based on, for instance, onRecordSelect (I think that is what you want when you talk about selection in a list). And you can ofcourse fire whatever you want in that method. But really listening to events can not be done just like that (as far as I know).

Hi Marcel

Thank you. That was (again) a fast response.

I’m a little confused . I thought, it MUST be possible. How else can I build a serious program? To me it looks as if I cannot build a HIERARCHY of forms (which means I’d like to build basic forms which can be used in many other forms) because they all need to interact with each other: FormA calls a method in FormB, FormB calls a method in FormA, since all events must be handled in the form where they occur. Which also means that basic forms need to know where they are used. Which breaks all my effort building a hierarchy.

So, I guess, the strength of servoy is showing table contents and there relations. And not programming. Provocative?

Thanks and best regards
Birgit

Yep, but imho that’s something else than you ask for. You ask for forms that LISTEN. That’s not possible.

What is possible is what I described. Attach a method to whatever event is available under the properties.

In THAT method you can call methods on other forms of course. And you can also do so by passing variables to that method. You can do this with the following syntax form.formname.method(var1,var2,var3) in that method you can set```
var1 = arguments[0] etc.

This is dealt with many times on the forum and I am pretty sure it is in the documentation too...

Yes, I know how to call a method. And how to pass arguments.

You said, a form cannot listen to events of another form. Again, this implies to me that you cannot encapsulate your forms. They will all interact with each other. Is this the case in your solution(s)? What are modules worth in this case?

Thanks and best regards
Birgit

Modules are the first attempt of Servoy to make it easier for more developers to work ‘together’.

You can re-use forms and the way I do that is by passing the parent form name to the next/child form or using getMethodTriggerFormName. Whichever one is appropriate. By knowing the name I know what task I want accomplished.

I don’t really see the relation between ‘serious programming’ and the fact that you can’t ‘listen’ to other forms. Even when you would be able to listen you define the listener on the form you come from and not on the form that you go to imho. That listener then calls other methods, forms or sets variables like you can with Servoy.

When I misinterpreted you again I am afraid I am going to rest my case :) I run out of ideas.

Thanks for all your time. I hope we’ll soon come to an end, where either I convince you that there is a problem and you tell me if it can be solved or not. Or you convince me that I don’t have this problem and everything is fine and you show me how to do it. :)

First: Maybe we have problems understanding each other since we use other terminology: I use “basic form” you use “parent” and “child form” and the form “you come from” and the form “you go to”.

I guess parent is the form which uses an other form. The child form is probably the form I call basic form. And the form “you come from” is the parent form, the form “you go to” is the child form. Right?

I don’t see where and when I should use application.getMethodTriggerFormName:

I have a form (child form) with a list of domains. In this form I call the method “domainSelected” whenever an item is selected. In this method I call a method in a parent form:

domainSelected
forms.main.domainInDomainFormSelected(xyDomain);

Now my child form knows where it is used. Which is not what I want. What I would like is something like:

domainSelected
  this.raise(Event.new("domainSelected"));

And in the parent form the registering on the event like:

domainForm.onEvent("domainSeleted", domainInDomainFormSelected());

And then the code in the parent form:

domainInDomainFormSelected
  /* react to the fact that an other domain is selected */

How can this be done? Why and where does application.getMethodTriggerFormName help? How can I avoid that the child form calls a method in the parent form?

Best regards
Birgit

guess parent is the form which uses an other form. The child form is probably the form I call basic form. And the form “you come from” is the parent form, the form “you go to” is the child form. Right?

Agree :)

don’t see where and when I should use application.getMethodTriggerFormName

In your example probably never :(

Birgit, I just don’t understand these quotes:

Now my child form knows where it is used. Which is not what I want

Why not? What is going wrong when you do this?

How can I avoid that the child form calls a method in the parent form?

Again, why do you want to avoid that?
This is exactly what I do, Tell the child who the parent is and then let the child execute a method on the parent on whatever event.

Hi again, it looks as if we finally found each other. Thanks for trying to understand my thoughts!

So, why do I call this a problem? It’s because of the program structure. Modern program languages offer the possibility of building modules (or reusable components or basic classes or frameworks or whatever). Modules (not servoy modules) usually define a public interface, guarantee data encapsulation and don’t know anything about its use.

From Servoy Forms I expected the same. I was looking for an interface I could define and which could be used in a parent form.

Whenever you start calling methods arbitrarily between all available forms this will be at the expense of structure, control, overview and extensibility. You’d deny all the advantages of the evolution of program languages. This is why I’d call servoy week in this aspect. It may be strong in an other.

Best regards
Birgit

Ok, yes I think we understand each other now. In other words this is about expectations and also definition.

I would not call Servoy a programming language. It is a RAD tool. Enabling fast development. Enabling strong stuff, sometimes disabling too ‘complicated’ stuff delaying development.

While working with Servoy/JavaScript and Java I would say Java is very flexible and strong when it comes to doing many many tasks. Its weakness is ‘fast development’. While I really like Java there is (virtually) nothing that can beat the speed of development that Servoy offers me. My solution was brought to the client within 4 months with 120 forms and was completed nearly half a year later. There were not many tools I missed…

Are you always online? I sometimes need some rest. :wink:

Thanks for the patience and the whole discussion.

Best regards
Birgit

Hi Birgit,

Another idea. You can create your own ‘callback’ methods on forms.
These methods need to use some kind of naming convention.
The module method can check for the existence of these methods and call them when neccessary.

 var callback = 'forms.aformname.amethodname';
//check if method exists before calling it.
if(eval(callback)) {
    callback += '();'
    //You can pass parameters too...
    //callback += '(1,"test");'
    //call the method. 
    eval(callback);
}

This helps keep your modules generic and reusable.

Hello Christian

Thank you for your post. Actually, this “callback” solution is still not quite what I’m looking for. It’ s closer to my ideas since the coupling is weaker: The method called will be more general (protocol like). But: Whenever I use the module (or the child form) in an other context, I need to change the module. That should not be neccessary.

So, what I’m currently looking for is an event handler registration: Can you tell me, if and how I could register an event handler in a parent form on a child form? I play with code like

onShow()
  //this method is in a parent form. It registers for events in a used
  //module or a used form
  forms.childFormInModuleA.elements.anElement.onClick = clickHandler();

  //or:
  forms.childFormInModuleA.elements.anElement.addEventListener("click", clickHandler(), false);

But nothing works so far.

And: Could you please tell me more about these form-level variables? I didn’t find them in the documentation. Can they be accessed by other forms? And within other methods of the same form?

Thanks a lot and best regards
Birgit

Birgit,

Besides the events (onAction, onRecordSelections, onSHow, OnHide) that Servoy provides on various objects (forms, buttons, portals, labels etc), Servoy doesn’t provide to register your own listeners.

So, you got two options:
1- Use the events provided by Servoy to accomplish what you want (various examples allready provided in this Topic)
2- Build yourself a (Java) plugin that allows you to register additional listeners on elements.

If you would go for the latter, take the following into consideration:

  • This will only work in the rich/webstart client, not in de WebClient (introduced in Servoy 3.0)
  • Adding additional listeners on objects might interferre with Servoy’s standard listeners.

Paul

birgit:
And: Could you please tell me more about these form-level variables? I didn’t find them in the documentation. Can they be accessed by other forms? And within other methods of the same form?

If you use a variable without declaring it, it becomes available to all methods on the form.

var x = 1; //normal variable declaration
y = 2; //not declared, so becomes a form-level variable.

As far as I know they are only available to the methods of the form.

Code:

var x = 1; //normal variable declaration
y = 2; //not declared, so becomes a form-level variable.

As far as I know they are only available to the methods of the form.

By heart, as far as I know they are globally available…

Hi

Events: I see the downside of creating my own events. Besides the fact that I don’t have the knowledge to build the plugins. If I go with the servoy events: Can the registration for an event be done in a script (editor)? So far, I only did it from the designer, by setting the property field. Now I try to write something like

forms.domains.onRecordSelection....

Form variables: Thank you, I’m just playing around with them. They really seem to be visible within the whole solution. So, what is there advantage to global variables?

Thanks to all and best regards
Birgit