-
Notifications
You must be signed in to change notification settings - Fork 188
[Win32] Fix control bounds exceeding parent size #2849
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
[Win32] Fix control bounds exceeding parent size #2849
Conversation
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
There is no test that is ensuring, that making the child explicitly bigger, e.g. 2 pt that the parent is working, right? Wouldn't that make sense as some kind of sanity check?
| Rectangle parentBounds = parent.getBoundsInPixels(); | ||
| if (parentBounds.width < boundsInPixels.x + boundsInPixels.width | ||
| && parentBounds.width >= boundsInPixels.x + boundsInPixels.width - Win32DPIUtils.pointToPixel(1.0f, zoom)) { | ||
| boundsInPixels.width = parentBounds.width - boundsInPixels.x; | ||
| } | ||
| if (parentBounds.height < boundsInPixels.y + boundsInPixels.height && parentBounds.height >= boundsInPixels.y | ||
| + boundsInPixels.height - Win32DPIUtils.pointToPixel(1.0f, zoom)) { | ||
| boundsInPixels.height = parentBounds.height - boundsInPixels.y; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think a short comment about the if conditions would be helpful either here or in the javadoc above. what you are testing is that is would only be 1 point bigger - that should be stated somewhere here, I think
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
It would indeed help to have more explanation here. I have added a comment with a short explanation and also refactored the code to extract the conditions into variable, so that the variable names hopefully support comprehensibility of the semantics. Please have a look if you think that the changes help.
The invertibility of point/pixel conversions is limited as point values are int-based and with lower resolution than pixel values. In consequence, values need to be rounded when converted between the two, which inevitably leads to rounded values that do not fit for every use case. This adds test cases that demonstrate such use cases, including simple parent/child scenarios, in which the child is supposed to fill the parent, and including layouting scenarios incorporating the client area of a composite, and how the current implementation is not capable of producing proper results for them. This change also adapts the methods for setting bounds/size of controls to deal with the limited invertibility. They shrink the calculated pixel values by at most the maximum error that can be made when transforming from point to pixel values, such that rounding errors due to layouts that calculated control bounds based on a composites client area are evened out. Without that, layouted controls may be up to one point too large to fit into the composite.
eb2f91a to
cbdcdcb
Compare
Valid point. I have extended the tests to cover this case. And I have added a unit test (setting bounds with defined values) for the fit-into-parent scenario in addition to the existing (rather integration-like) test case (setting bounds with values depending on the parent's client area). I also extended the tests to also use |
akoch-yatta
left a comment
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
LGTM, the explanation makes sense to limit the effect of the rounding issues. I tested with different configuration with the IDE and found the mentioned improvements and no regressions
The invertibility of point/pixel conversions is limited as point values are int-based and with lower resolution than pixel values. In consequence, values need to be rounded when converted between the two, which inevitably leads to rounded values that do not fit for every use case. This adds test cases that demonstrate such use cases, including simple parent/child scenarios, in which the child is supposed to fill the parent, and including layouting scenarios incorporating the client area of a composite, and how the current implementation is not capable of producing proper results for them.
This change also adapts the methods for setting bounds/size of controls to deal with the limited invertibility. They shrink the calculated pixel values by at most the maximum error that can be made when transforming from point to pixel values, such that rounding errors due to layouts that calculated control bounds based on a composites client area are evened out. Without that, layouted controls may be up to one point too large to fit into the composite.
This is an extract of:
which would, in its current state, introduce a regression that needs to be further analyzed.
How to reproduce
The different issues are demonstrated with the following snippet (conforms to the test cases and same as in #2782)):
All scenarios except for the one with third composite (becoming too small to fit its parent) are fixed with this change.
Before at 125%:

After at 125%:

Further examples
This change improves layouting behavior and can, e.g., be seen in the Forms UI, such as used in the Manifest editor.
Before at 125%:

After at 125%:
