I have the following piece of logic: ```@Composab...
# compose-desktop
y
I have the following piece of logic:
Copy code
@Composable
fun EditPartUI(part: Part, onDismiss: () -> Unit) { /* */ }

@Composable
fun PartXX() { 
    var pendingPartCreate by remember { mutableStateOf<Part?>(null) }
    
    if(pendingPartCreate == null) {
        ScrollableTab(
            onFabAction = { pendingPartCreate = Part() }) {
            // ....
        }
    } else {
        EditPartUI(pendingPartCreate!!, onDismiss = { pendingPartCreate = null} )
    }
}
The
else
branch does not compile unless I use
pendingPartCreate!!
(smart cast does not work). So is the compiler not smart enough to detect the fact that it cannot change? Or is the compiler rightfully wants to prevent me from shooting myself in the foot?
t
The second case your variable is of type var and could be change in the meanwhile from another thread / coroutine
y
but how exactly can another thread change it? It is defined inside the composable function, no other code has access to it
t
Maybe someone can explain it in more detail but one requirement for smart cast is that the variable is immutable (for example a val or a parameter) So if you would use an extra variable as 'snapshot' of the value of pendingPartCreate it would work. something like this
Copy code
[...] 
val currentPendingPart = pendingPartCreate
if (currentPendingPart == null) {
    // casted to null
} else {
    // casted to notnullable Part
} 
[...]
j
There is no way of knowing when
EditPartUI
might invoke the
onDismiss
lambda. By convention, Compose widgets typically only invoke such callbacks on the main thread in response to a UI event, but this is not guaranteed by any system that the compiler can depend upon. In particular, the
EditPartUI
widget might launch a thread and invoke that lambda between the null check and the usage.
y
I am not launching any thread but I guess I get the point, I need to copy the variable to be certain
a
I am not launching any thread
You know it. The compiler doesn’t. So it goes for a conservative approach. In the end,
!!
operator is just that, you telling the compiler that it’s OK to use a nullable var without any check because you know that it won’t be null
👍 1