Re: Are you a subform guru? Test your knowledge with a quiz. Also, a listing of all 4D documents on subforms

2018-04-07 Thread Keisuke Miyako via 4D_Tech
I am not a guru, just a follower :)

> 3) When will the On Bound Variable Change event not happen when the Subform 
> Container variable changes?

When the widget does not exist (i.e. it is not on the current form).

> 4) When will OBJECT GET SUBFORM not return the form name set by OBJECT SET 
> SUBFORM?

In the same code sequence that you called O. SET SUBFORM, because the subform 
is only set at the end of the event cycle.
Events are executed in sequence for the same process, so you can not fire a new 
event before you complete the current event.
Setting a subform triggers a sequence of events, so by definition it is 
deferred until you complete the current event.

> 5) Which form events will be triggered by redisplaying a page with a subform?

On Load.

> 6) What happens when a subform is resized? How to manage it?

The resizing of a container subform "object" is equivalent to the resizing of 
the widget "form". So you need to follow 2 rules:

If you want automatic resize (grow, resize) to work inside your widget, your 
widget form's width/height must be the same as the container object's 
width/height.

If you want automatic resize (grow, resize) to work inside your widget, your 
widget must be on page 0 or 1. This is because the container object is part of 
the parent form and resized on all pages, but your widget can only process 
resize events on the current page because it only exists on the current page.

If you can't do either of the above, you should resize your widget by code.

> 7) Is the timer in SET TIMER associated with the process or the form?

No. Each form (parent, widget) has its own timer. I know a developer who has a 
subform inside a subform inside a subform and each have running timers. When 
the form is running, he can hardly type any text in the method editor. Bad idea.

> 8) When will On Activate not be triggered when a subform becomes active?

when the subform does not have focus on the parent form. On Activate for a 
widget is equivalent to On Getting Focus for its container in the parent form. 
Same relation between On Deactivate and On Losing Focus.

> 9) Besides using process variables (including sets and Named selections), how 
> can the subform interact in the parent form context?

I think a widget should never you process variables or anything with a scope 
wider than the current form.
The bound variable should be the only connection.
If you need to process complex information, consider using an object as the 
bound variable.
Using process variables in a widget is like using process variables in a 
subroutine.
It is bad practice, you should pass parameters.
The parameter of a widget is its bound variable.

> 3) A third issue is clarifying that OBJECT SET SUBFORM does not trigger an On 
> Load event in the subform: a) if you are on another page, or, b) it is 
> already being displayed.
> The Subform will NOT get an On Load if it is already being displayed, even if 
> OBJECT SET SUBFORM is called again.
> The Subform will get an On Bound Variable Change only if the subform 
> container variable changes while the subform is already being displayed.

I prefer to understand it like this: a widget (not the subform container, but 
the child form inside the container) only exists on the current page. and a 
form that does not exist can not run any events or execute any code.

Likewise, if you exit that page, the widget is destroyed, so you it will be 
recreated when you revisit that page and an On Load event would fire again. But 
the subform container is part of the parent form, which means the bound 
variable belongs to the parent form survives the page transition. So your 
widget's On Load code needs to differentiate the 1st On Load and subsequent On 
Loads, because you don't want to reinitialise the bound variable from inside 
every time you switch pages.

I struggle to understand why you would call O. SET SUBFORM when the subform is 
already set and expect an On Load event. On Load is fired when a widget is 
loaded, i.e. created, in other words when it comes into existence. That can be 
when the parent form is loaded and the  widget is on page 0 or 1, or every time 
the parent form switches to the page on which the subform is placed, or when O. 
SET SUBFORM is called for it to replace another widget (or no widget).




**
4D Internet Users Group (4D iNUG)
FAQ:  http://lists.4d.com/faqnug.html
Archive:  http://lists.4d.com/archives.html
Options: https://lists.4d.com/mailman/options/4d_tech
Unsub:  mailto:4d_tech-unsubscr...@lists.4d.com
**

Are you a subform guru? Test your knowledge with a quiz. Also, a listing of all 4D documents on subforms

2018-04-06 Thread LEONARD SOLONIUK via 4D_Tech
Following is a David-Adams-length summary about subforms



A self-quiz:

1) All 4D commands and functions in a subform are executed in the context of 
the subform. Except for a few. What are the exceptions?

2) How can a method check if it is running in a form or subform?

3) When will the On Bound Variable Change event not happen when the Subform 
Container variable changes?

4) When will OBJECT GET SUBFORM not return the form name set by OBJECT SET 
SUBFORM?

5) Which form events will be triggered by redisplaying a page with a subform?

6) What happens when a subform is resized? How to manage it?

7) Is the timer in SET TIMER associated with the process or the form?

8) When will On Activate not be triggered when a subform becomes active?

9) Besides using process variables (including sets and Named selections), how 
can the subform interact in the parent form context?

If the answers are not apparent from the references below, let me know.



When the information documented below you can answer the questions and predict 
what will happen when working with subforms.

The 4D documents describe (almost) completely all the details regarding the use 
of forms and subforms (widgets). However, this knowledge is scattered through 
many different areas of the 4D Design Reference and 4D Language reference and 
the Knowledgebase. I have tried to list them below. You also should check the 
iNug for almost anything that Keisuke Miyako has written.



Some of the older 4d documents recommend use of SET TIMER in the communication 
between Parent form and subform because of the issues of when the subform and 
objects are instantiated. There are several alternatives.

Some of the recommendations for the use of timers (as opposed to alternatives) 
is related to the use of Open window instead of the recommended Open form 
window. This is discussed by Keisuke Miyako on the iNug: Re: Resizable subforms.

Another old-fashioned way of communicating is POST KEY. No longer needed.



1) One area that I don’t think 4D does a good job of documenting is the issue 
of resizing in subforms. I am confident of the following:
The On Resize event is never triggered in the subform.

When the subform is first displayed, either by being already on the form or 
through OBJECT SET SUBFORM, 4D does not resize the objects on the subform. 
However if the parent form is subsequently resized, 4D will resize the objects 
on the subform according to the Resizing Options properties.

The standard way to handle this issue is either a) never resize the subform, or 
b) somewhere in the loading process (discussed below) the subform uses OBJECT 
GET SUBFORM CONTAINER SIZE to get its own size and resizes itself.

This issue is also discussed in the note below copied from Keisuke Miyako.

2) A second issue not discussed in the 4D documents is the issue of what 
happens to subforms when you leave the page is also missing from official 4D 
documentation but it is discussed below definitively Keisuke Miyako. 

To add to what he is saying on this: if you are on page 2 displaying a subform, 
then go to another page and change the page 2 subform variable, if you return 
to page 2, you get an On Load event in the subform, not an On Bound Variable 
Changed event.

3) A third issue is clarifying that OBJECT SET SUBFORM does not trigger an On 
Load event in the subform: a) if you are on another page, or, b) it is already 
being displayed.



The Subform will NOT get an On Load if it is already being displayed, even if 
OBJECT SET SUBFORM is called again.



The Subform will get an On Bound Variable Change only if the subform container 
variable changes while the subform is already being displayed.



The commands and functions that can be executed in the parent form context from 
a subform are GOTO OBJECT and FORM GOTO PAGE and FORM Get current page. Am I 
missing anything? Of course, process variables, sets, selections, etc, are 
shared with all forms and subforms in a process.



I did not expect this but it’s rational: A click in the subform will trigger an 
On Clicked in the Container Form as well.



Here’s the list of 4D documents, Knowledgebase, and (some) inug messages 
describing subforms (let me know if I’m missing something):

4D Design Reference: Subforms and Widgets: Overview
4D Design Reference: Subforms and Widgets: Page subforms

4D Language Reference: Form Events
Form event
CALL SUBFORM CONTAINER 
SET TIMER
Remember: When the SET TIMER command is executed in the context of a subform 
(form method of the subform), the On Timer event is generated in the subform 
and not at the parent form level.
FORM GOTO PAGE

4D Language