On Wed, 1 Oct 2025 16:55:00 GMT, John Hendrikx <[email protected]> wrote:

>>> When a situation like this happens in reality, we might see a momentary 
>>> flicker due to the layout spanning several pulses, correct?
>> 
>> Well, if layout runs (due to a significant change), you'll see components be 
>> re-arranged, and if a 2nd pulse is needed, you would probably not notice as 
>> things were moved around a lot anyway.  But on top of that, there is a good 
>> chance the 2nd pass is just recalculating everything without actually 
>> changing anything because it is often triggered without a good reason.  For 
>> example:
>> 
>> Take an HBox for example.  During layoutChildren, it will position its 
>> children.  If this involves moving a child to the right or left because an 
>> earlier child has shrunk/grown then layout X is changed and triggers the 
>> logic in Node (without good reason I might add).  This is in part because 
>> HBox does not update or set the "current layout child" at all (none of the 
>> containers do this, except Parent's layoutChildren which is almost always 
>> overridden).  So this code below in Node will trigger and force another 
>> layout pass:
>> 
>>                     if (p != null && !p.isCurrentLayoutChild(Node.this)) {
>>                         if (isManaged()) {
>>                             // Force its parent to fix the layout since it 
>> is a managed child.
>>                             p.requestLayout(true);
>>                         } else {
>>                             // Parent size changed, parent's parent might 
>> need to re-layout
>>                             p.clearSizeCache();
>>                             p.requestParentLayout();
>>                         }
>>                     }
>>                     
>> All the ingredients match:
>> - LayoutX was modified on a child
>> - Its parent is not `null` (it's the HBox)
>> - It is not the current layout child (HBox doesn't update this before 
>> modifying a position on a child)
>> - The child in question is managed (all children in an HBox generally are)
>> 
>> End result: schedule another layout pass
>> 
>> Now, if in the 2nd pass none of the X (or Y) positions change again, then 
>> this 2nd pass will end up doing nothing.  Quite wasteful.
>> 
>>> The platform itself can't really do anything, except for the application 
>>> code to call the layout() explicitly to avoid flicker, right?
>> 
>> Calling `layout` won't do much when the flags are bad, as layout basically 
>> operates based on those flags.  So if you call layout at the root, and the 
>> flags say that it is `CLEAN` then it stops right there.  
>> 
>> However there are many thi...
>
>> Or maybe even make it more generic: detect when (a small number of) 
>> additional layout passes are needed and do them right away instead of 
>> waiting for another pulse?
> 
> But also avoid passes that are not needed... I mean HBox almost always 
> triggering a redundant 2nd pass makes the logic in `Node` suspect IMHO.
> 
> I get why the logic is **really** there; a user may modify layoutX randomly 
> on some managed control outside a layout pass; in that case you do want the 
> Parent that is managing those nodes to take control and "fix" what the user 
> broke, but it is triggering much more often than needed.

that was a good, informative discussion, thank you all!

-------------

PR Review Comment: https://git.openjdk.org/jfx/pull/1879#discussion_r2395291017

Reply via email to