Change theme
Help
Press space for more information.
Show links for this issue (Shortcut: i, l)
Copy issue ID
Previous Issue (Shortcut: k)
Next Issue (Shortcut: j)
Sign in to use full features.
Vote: I am impacted
Notification menu
Refresh (Shortcut: Shift+r)
Go home (Shortcut: u)
Pending code changes (auto-populated)
View issue level access limits(Press Alt + Right arrow for more information)
Unintended behavior
View staffing
Description
Component used: Androidx Lint
Not sure if this is the best component for this issue. This might be a bug somewhere else, and the correct thing to do is fix the bug, instead of issue a lint warning.
I've just fixed an unexpected race-condition-y bug setting a view's layout params using Kotlin scope functions.
tl;dr
Setting a view's layout params using
with
and other scope functions like so:can silently not set the params, resulting in visual bugs at run time. This might be worth a lint check.
I suspect this is an unintended interaction between Kotlin's scope functions and Kotlin's Java interoperability with class fields that havehttps://kotlinlang.org/docs/java-interop.html#getters-and-setters ).
get
andset
methods (The problem
I have a custom view that displays a preview image and some metadata.
Depending on the aspect ratio of the image the overall layout looks like this (text in
[...]
is the view IDs) for landscape images:and this for portrait images:
preview_card_wrapper
is aConstraintLayout
. At run time I check the aspect ratio of the image and call this if the image is portrait.There's a similar function if the image's aspect ratio is landscape.
Sometimes, this doesn't work. Specifically, the
card_info
view behaves as though thestartToEnd
constraint is not updated. Thecard_info
view's starting edge matches the parent, so thecard_image
andcard_info
end up overlapping.In normal use of the app this happens rarely, but frequently enough for users to report the problem. I was eventually able to engineer a situation in my app where I can reproduce this 100%.
Adding the following to the end of that function resolves the issue 100 % of the time:
As does re-writing the second
with
block to the following that doesn't use scope functions:Other attempts to fix this (e.g., calling
cardInfo.requestLayout()
after thewith
block in the original code) do not work.