Jetpack Compose ejecuta modificadores en distintas fases. En el siguiente desglose, se muestra a qué fase pertenecen los modificadores comunes y cuándo se evalúan sus argumentos o lambdas.
Fase 1: Fase de composición
Estos modificadores evalúan los argumentos de forma síncrona dentro del @Composable cuerpo. Cualquier estado que se lea aquí registra una dependencia con el alcance de reinicio de Composable y activa una recomposición completa cuando cambia.
- Modificadores de tamaño y dimensión estáticos:
Modifier.size(dp),Modifier.width(dp),Modifier.height(dp)Modifier.fillMaxSize(),Modifier.fillMaxWidth(),Modifier.fillMaxHeight()Modifier.wrapContentSize(),Modifier.wrapContentWidth(),Modifier.wrapContentHeight()Modifier.requiredSize(),Modifier.defaultMinSize()Modifier.aspectRatio(ratio)Modifier.weight(weight)(enRowScopeoColumnScope)Modifier.width(IntrinsicSize.Min / Max)Modifier.height(IntrinsicSize.Min / Max)
- Espaciado y ajustes estáticos:
Modifier.padding(all = dp),Modifier.padding(start, top, end, bottom)Modifier.windowInsetsPadding(insets),Modifier.statusBarsPadding()
- Modificadores visuales de valor directo:
Modifier.alpha(float)(lee el estado durante la composición)Modifier.rotate(degrees)(lee el estado durante la composición)Modifier.scale(scaleX, scaleY)(lee el estado durante la composición)Modifier.background(color = Color, shape = Shape)Modifier.border(width, color, shape)Modifier.shadow(elevation, shape)Modifier.clip(shape)Modifier.blur(radius)
- Modificadores de posición estáticos:
Modifier.offset(x = dp, y = dp)(sobrecarga de valor directo)Modifier.absoluteOffset(x = dp, y = dp)
- Modificadores dinámicos componibles:
Modifier.composed { ... }(ejecuta el cuerpo de la fábrica durante la composición)
Fase 2: Fase de diseño
La fase de diseño se divide en dos subpasos distintos con diferentes alcances de invalidación:
Paso 2A: Medición
Determina el tamaño (width, height) y las restricciones. La lectura de estado aquí activa la nueva medición y la reubicación:
Modifier.layout { measurable, constraints -> ... }: Código anterior a la ejecución delayout(w, h)durante la medición.
Paso 2B: Devoluciones de llamada de posición y diseño
Determina la posición de la coordenada (x, y). El estado que se lee aquí solo activa la reubicación (se omiten la medición y la composición):
Modifier.offset { IntOffset(x, y) }(sobrecarga de lambda)Modifier.absoluteOffset { IntOffset(x, y) }(sobrecarga de lambda)Modifier.layout { ... layout(w, h) { placeable.place(x, y) } }: Código dentro del bloquelayout(w, h) { ... }.Modifier.onPlaced { layoutCoordinates -> ... }: Se invoca después de que se determinan las coordenadas principales durante la colocación.Modifier.onSizeChanged { intSize -> ... }: Se invoca después de que se completa la medición del diseño si cambió el tamaño.Modifier.onGloballyPositioned { layoutCoordinates -> ... }: Se invoca después de que finaliza todo el pase de diseño de la ventana.
Fase 3: Fase de dibujo
Estos modificadores se ejecutan durante el dibujo del lienzo. La lectura de estado dentro de estos bloques omite tanto la composición como el diseño y solo ejecuta el paso de dibujo:
Modifier.graphicsLayer { ... }:- Propiedades actualizadas en la función lambda:
alpha,translationX,translationY,scaleX,scaleY,rotationX,rotationY,rotationZ,shadowElevation,shape,clip,renderEffect,transformOrigin.
- Propiedades actualizadas en la función lambda:
Modifier.drawBehind { ... }:- Dibuja comandos de lienzo detrás del contenido componible.
Modifier.drawWithContent { ... }:- Controla el orden de dibujo con
drawContent().
- Controla el orden de dibujo con
Modifier.drawWithCache { ... }:- El bloque externo se ejecuta en los cambios de tamaño o diseño para almacenar en caché los objetos
Path,PaintoBrush;onDrawBehindoonDrawWithContentse ejecuta en cada dibujo de fotograma.
- El bloque externo se ejecuta en los cambios de tamaño o diseño para almacenar en caché los objetos
Fuera del bucle de recomposición: modificadores de observación
Algunos modificadores operan fuera de las tres fases de fotogramas para controlar la accesibilidad, la entrada del usuario y las observaciones del ciclo de vida.
Semántica y accesibilidad
Procesa propiedades semánticas para servicios de accesibilidad (TalkBack) y pruebas:
Modifier.semantics { ... }Modifier.clearAndSetSemantics { ... }
Entrada, gestos y eventos
Funciona fuera de la canalización de renderización de fotogramas de tres fases, ya que recibe eventos de movimiento del SO y las interacciones del usuario:
Modifier.pointerInput(key) { detectTapGestures { ... } }/detectDragGestures/awaitPointerEventScopeModifier.clickable(enabled, onClickLabel) { ... }Modifier.combinedClickable { ... }Modifier.toggleable { ... }Modifier.selectable { ... }Modifier.draggable(...)/Modifier.scrollable(...)/Modifier.draggable2D(...)Modifier.onFocusChanged { focusState -> ... }Modifier.onKeyEvent { keyEvent -> ... }Modifier.onVisibilityChanged { isVisible -> ... }: Se invoca la devolución de llamada cuando cambia la visibilidad de un elemento componible después del retraso configurado, en una corrutina.
Referencia rápida: Fase de valor versus fase de lambda
Leer un valor de estado en una lambda difiere la lectura a una fase posterior, lo que omite las fases anteriores cuando cambia ese estado:
| Modificador / patrón | Valor directo (composición) | Lambda Variant (fase aplazada) | Cuándo cambian los estados |
|---|---|---|---|
| Desplazamiento | Modifier.offset(x, y) |
Modifier.offset { IntOffset(x, y) } |
Diseño (posición) (omite la composición) |
| Alfa / Opacidad | Modifier.alpha(alpha) |
Modifier.graphicsLayer { this.alpha = alpha } |
Dibujo (se omite Composición y diseño) |
| Rotación | Modifier.rotate(degrees) |
Modifier.graphicsLayer { rotationZ = degrees } |
Dibujo (se omite Composición y diseño) |
| Escala | Modifier.scale(scale) |
Modifier.graphicsLayer { scaleX = s; scaleY = s } |
Dibujo (se omite Composición y diseño) |
| Traducción | Modifier.padding(...) |
Modifier.graphicsLayer { translationX = ... } |
Dibujo (se omite Composición y diseño) |
| Color de fondo | Modifier.background(color) |
Modifier.drawBehind { drawRect(color) } |
Dibujo (se omite Composición y diseño) |
| Desplazamiento / Paralaje | Modifier.offset(scroll.dp) |
Modifier.offset { IntOffset(0, scroll) } |
Diseño (posición) (omite la composición) |
Asignación de la interfaz Modifier.Node
En el caso de los modificadores personalizados que usan la API de Modifier.Node de alto rendimiento, las fases se asignan directamente a las interfaces de capacidad de los nodos:
| Fase | Interfaz de Modifier.Node |
Métodos principales |
|---|---|---|
| Diseño (Medir y colocar) | LayoutModifierNode |
measure(measurable, constraints) |
| Diseño (coordenadas globales) | GlobalPositionAwareModifierNode |
onGloballyPositioned(coordinates) |
| Diseño (posición) | LayoutAwareModifierNode |
onRemeasured(size), onPlaced(coordinates) |
| Dibujo | DrawModifierNode |
draw(ContentDrawScope) |
| Entrada / Puntero | PointerInputModifierNode |
onPointerEvent(...), onCancelPointerInput() |
| Semántica | SemanticsModifierNode |
applySemantics(SemanticsPropertyReceiver) |
| Enfoque | FocusEventModifierNode |
onFocusEvent(focusState) |