Communitygithub.com

axewhyzed/agentic-skills

Guía completa y marco operativo para ingeniería nativa de Android y UI/UX móvil. Útil al diseñar, auditar, construir o refactorizar aplicaciones Android (Jetpack Compose, Material 3), ergonomía móvil, patrones offline-first outbox, caché stale-while-revalidate, acciones inteligentes de un solo toque, integraciones con el marco de almacenamiento, hápticas táctiles, transiciones de elementos compartidos, gestos de retroceso predictivos y autenticación móvil sin fricciones.

¿Qué es agentic-skills?

Esta skill proporciona un marco operativo probado en producción para diseñar y construir aplicaciones Android nativas con Jetpack Compose y Material 3, enfocándose en la ergonomía móvil, el rendimiento percibido, la resiliencia offline y la accesibilidad. Cubre desde la jerarquía de alcance del pulgar hasta patrones avanzados como stale-while-revalidate, outbox para offline-first, transiciones de elementos compartidos y hápticas táctiles. La skill está diseñada para ingenieros de Android que deseen construir aplicaciones que se sientan nativas, rápidas y accesibles, cumpliendo con los estándares WCAG 2.2. Incluye ejemplos concretos de código Kotlin, configuraciones de manifiesto y referencias a repositorios open source de referencia como `nowinandroid` y `Signal-Android`. Es útil para auditar, rediseñar o construir desde cero aplicaciones Android modernas.

Compatible con~Claude Code~Codex CLI~Cursor✓Antigravity
npx skills add https://github.com/axewhyzed/agentic-skills/tree/HEAD/.agents/skills/android-mobile-ui-ux

Preguntar en tu IA favorita

Abre un nuevo chat con esta habilidad de agente ya precargada.

Documentación

Guía de Ingeniería de Android y UI/UX Móvil

Un marco operativo práctico y probado en producción para diseñar y construir aplicaciones Android nativas con Jetpack Compose, Material 3, resiliencia offline-first y ergonomía móvil centrada en el ser humano.


1. Ergonomía Móvil Central y Zona del Pulgar

Los dispositivos móviles se sostienen con una sola mano más del 70% del tiempo. Diseña las interfaces en torno a la alcanzabilidad del pulgar, la retroalimentación táctil y la mínima fricción física.

1.1 Jerarquía de Alcanzabilidad Ergonómica

+---------------------------+  <- Parte superior de la pantalla (Solo visualización)
|  Estado y Encabezados     |     Más difícil de alcanzar. Reserva para estado
|  Título, Medidor de cuota |     pasivo, barras de búsqueda y medidores en vivo.
+---------------------------+
|                           |  <- Zona de Alcance Medio
|  Contenido Desplazable    |     Ideal para elementos de lista, detalles y
|  Tarjetas de Bandeja      |     tarjetas de contenido navegable.
|  de Entrada, Fragmentos   |
|                           |
+---------------------------+
|  Objetivos de Acción      |  <- Zona Principal del Pulgar (40% inferior)
|  Principal                |     Más fácil de tocar. Mantén la navegación, CTAs,
|  Botones de Envío,        |     paneles inferiores, filtros y controles
|  Pestañas, Hojas          |     interactivos aquí.
|  Inferiores, Filtros      |
+---------------------------+

1.2 Estándares No Negociables de Objetivos Táctiles

  • Objetivo Interactivo Mínimo: Cada elemento cliqueable debe cumplir o superar $48 \times 48\text{dp}$ (Modifier.sizeIn(minWidth = 48.dp, minHeight = 48.dp)), incluso si el icono visual es de $24\text{dp}$.
  • Inserciones de Borde y Áreas Seguras: Siempre envuelve los diseños raíz de Compose en Scaffold o aplica Modifier.windowInsetsPadding(WindowInsets.safeDrawing) para tener en cuenta los recortes de la cámara, los gestos y las barras de navegación.
  • Controles de Formulario en la Parte Inferior: Coloca las entradas de texto, los botones de envío y los diálogos de confirmación en ModalBottomSheet o tarjetas ancladas en la parte inferior para que el teclado del software (imePadding()) no oculte el campo activo.

2. Velocidad y Rendimiento Percibido

Los usuarios móviles perciben la demora de inmediato. Nunca bloquees la navegación ni muestres estados de carga vacíos cuando haya datos previamente obtenidos disponibles.

2.1 La Regla de Cero Esqueletos (Stale-While-Revalidate)

  • El Problema: Mostrar un cargador de esqueleto de página completa o un spinner circular cada vez que el usuario toca la pestaña de la bandeja de entrada se siente lento, discordante y poco pulido.
  • La Solución: Implementa un patrón de caché Stale-While-Revalidate (SWR):
    1. Almacena los elementos obtenidos en almacenamiento local cifrado (EncryptedSharedPreferences o SQLite/Room).
    2. Al entrar en la pantalla, muestra los elementos en caché inmediatamente (sin demora).
    3. Revalida en segundo plano si la caché tiene más de 5 a 10 minutos.
    4. Cuando lleguen los datos actualizados, agrega/actualiza los elementos suavemente sin borrar la lista ni mostrar marcadores de posición vacíos.
    5. Solo muestra indicadores sutiles (por ejemplo, un spinner de pull-to-refresh o una pequeña barra de progreso superior) durante las actualizaciones en segundo plano.

2.2 Patrón de Buzón de Salida Offline-First

Nunca falles una acción del usuario porque el dispositivo móvil tenga una conexión celular intermitente o esté temporalmente en modo avión.

flowchart TD
    UserAction["El usuario comparte un archivo / escribe una nota"] --> LocalDraft["1. Guardar en borradores locales del buzón de salida"]
    LocalDraft --> RenderOutbox["2. Renderizar en la tarjeta de la cola del buzón de salida inmediatamente"]
    RenderOutbox --> CheckNet{"¿Conectado a la red?"}
    CheckNet -- Sí --> DirectUpload["3. Subir directamente"]
    CheckNet -- No --> EnqueueWork["3. Encolar trabajo de WorkManager (NetworkType.CONNECTED)"]
    EnqueueWork --> WaitConn["4. Esperar por Wi-Fi / Celular"]
    WaitConn --> AutoDispatch["5. Subida en segundo plano con retroceso exponencial"]
    DirectUpload --> Success["6. Actualizar estado de la IU y notificar Toast"]
    AutoDispatch --> Success

Estados de la IU del Buzón de Salida:

  • Pendiente: "Esperando red…" con un icono de nube en pausa.
  • Subiendo: "Enviando 42%…" con un indicador de progreso lineal.
  • Fallido / Reintentando: Indicador de estado claro con botones explícitos de Reintentar y Descartar.

3. Movimiento, Transiciones y Hápticas Táctiles

El diseño moderno de Android (Android 14/15+) requiere movimiento dinámico basado en física y retroalimentación sensorial táctil para sentirse nativo y receptivo.

3.1 Manejo de Borde a Borde y Barras del Sistema

Siempre dibuja detrás de las barras del sistema globalmente en MainActivity.kt:

enableEdgeToEdge()
setContent {
    VaultTheme {
        Scaffold(
            contentWindowInsets = WindowInsets.safeDrawing
        ) { innerPadding ->
            AppNavHost(Modifier.padding(innerPadding))
        }
    }
}

3.2 Gestos de Retroceso Predictivos

Habilita el retroceso predictivo en AndroidManifest.xml (android:enableOnBackInvokedCallback="true") y usa PredictiveBackHandler para hojas inferiores y paneles de detalle:

PredictiveBackHandler(enabled = isDetailOpen) { progressFlow ->
    try {
        progressFlow.collect { backEvent ->
            // Escalar o desplazar la hoja de detalle proporcionalmente a backEvent.progress (0f a 1f)
            detailScale = 1f - (backEvent.progress * 0.1f)
        }
        // El usuario confirmó el gesto de retroceso
        closeDetail()
    } catch (e: CancellationException) {
        // El usuario abortó el gesto de retroceso, volver a 1f con rebote
        detailScale = 1f
    }
}

3.3 Transiciones de Elementos Compartidos

Al hacer la transición entre una fila de la lista de la bandeja de entrada y una vista de detalle del elemento, envuelve las pantallas en SharedTransitionLayout:

SharedTransitionLayout {
    NavHost(...) {
        composable("inbox") {
            InboxScreen(
                sharedTransitionScope = this@SharedTransitionLayout,
                animatedVisibilityScope = this
            )
        }
        composable("detail/{id}") {
            DetailScreen(
                sharedTransitionScope = this@SharedTransitionLayout,
                animatedVisibilityScope = this
            )
        }
    }
}

Usa .sharedElement() o .sharedBounds() en tarjetas de miniatura, iconos de avatar y títulos para crear transiciones sin interrupciones.

3.4 Hápticas Táctiles

Nunca dejes las acciones del usuario en silencio cuando ocurra un hito físico:

  • Deslizamientos de Umbral (Swipe-to-Dismiss): Activa HapticFeedbackConstantsCompat.GESTURE_START cuando el deslizamiento cruce el umbral de acción.
  • Copiar al Portapapeles / Envío Completado: Activa HapticFeedbackConstantsCompat.CONFIRM.
  • Fallo de Validación / Error de Red: Activa HapticFeedbackConstantsCompat.REJECT.
val view = LocalView.current
fun triggerHaptic(feedbackConstant: Int) {
    view.performHapticFeedback(feedbackConstant)
}

3.5 Física de Resorte sobre Easing Lineal

Evita las animaciones lineales rígidas. Usa siempre física de resorte para gestos, hojas y descartes:

val offsetAnim by animateFloatAsState(
    targetValue = targetOffset,
    animationSpec = spring(
        dampingRatio = Spring.DampingRatioMediumBouncy,
        stiffness = Spring.StiffnessLow
    )
)

4. Acciones Inteligentes de un Solo Toque e Integración con el Sistema

Las interfaces móviles deben minimizar la carga cognitiva reconociendo el tipo de carga útil y ofreciendo la acción nativa del sistema más relevante.

4.1 Matriz de Acciones Sensibles al Contexto

Tipo de Carga ÚtilAcción PrincipalAcción SecundariaIntegración con el Sistema
URL / Enlace WebAbrir en el Navegador (Intent.ACTION_VIEW)Copiar EnlaceChrome Custom Tabs o navegador predeterminado del sistema
Texto / FragmentoCopiar TextoCompartir (Intent.ACTION_SEND)ClipboardManager de Android con Toast / Snackbar instantáneo
Archivo / MultimediaDescargar a CarpetaAbrir ArchivoMarco de Acceso al Almacenamiento (SAF) + FileProvider

4.2 Descargas Directas de Archivos con Directorio Predeterminado Personalizado

Solicitar al usuario el selector de archivos del sistema cada vez que descarga un archivo crea fricción innecesaria.

  1. Permite al usuario seleccionar una Carpeta de Descarga Predeterminada una vez en Ajustes/Centro usando ActivityResultContracts.OpenDocumentTree().
  2. Persiste el permiso permanentemente:
    context.contentResolver.takePersistableUriPermission(
        treeUri,
        Intent.FLAG_GRANT_READ_URI_PERMISSION or Intent.FLAG_GRANT_WRITE_URI_PERMISSION
    )
    
  3. Al tocar Descargar:
    • Si hay un directorio predeterminado establecido: Transmite bytes directamente usando DocumentFile.createFile(), muestra el progreso de bytes en vivo y dispara un Toast de finalización nativo ("Descargado documento.pdf en Vault").
    • Si no hay un predeterminado: Recurre a ActivityResultContracts.CreateDocument().

4.3 Apertura Segura de Archivos con FileProvider

Nunca uses URIs inseguras de file:// en bruto. Siempre delega la visualización de archivos a aplicaciones nativas de Android usando FileProvider:

<!-- res/xml/file_paths.xml -->
<paths xmlns:android="http://schemas.android.com/apk/res/android">
    <cache-path name="cached_files" path="." />
</paths>
val contentUri = FileProvider.getUriForFile(
    context,
    "${context.packageName}.fileprovider",
    tempFile
)
val intent = Intent(Intent.ACTION_VIEW).apply {
    setDataAndType(contentUri, mimeType)
    addFlags(Intent.FLAG_GRANT_READ_URI_PERMISSION)
}
context.startActivity(Intent.createChooser(intent, "Abrir con..."))

5. Autenticación Móvil Sin Fricciones

Escribir URLs de servidor y contraseñas largas en pantallas táctiles móviles es propenso a errores tipográficos.

5.1 Jerarquía de Prioridad de Inicio de Sesión

  1. Prioridad 1: Escaneo de Código QR con Cámara (Emparejamiento de 1 Segundo)
    • Muestra un código QR de emparejamiento firmado temporal en la aplicación web de escritorio.
    • El usuario móvil abre la aplicación, toca Escanear Código QR, apunta la cámara a la pantalla.
    • La aplicación analiza el origen, el token y el nombre del dispositivo en una sola pasada: autenticado al instante.
  2. Prioridad 2: Nombre de Usuario y Contraseña con URL de Servidor Plegable
    • El 99% de los inicios de sesión usan el host configurado por defecto.
    • Presenta solo los campos Nombre de Usuario y Contraseña por defecto.
    • Oculta la URL del servidor detrás de un conmutador plegable sutil: "Configuración del servidor (avanzado)".

5.2 Persistencia de Sesión Deslizante de 14 Días

  • Almacena los tokens de acceso (va1_) y actualización (vr1_) en EncryptedSharedPreferences de Android.
  • Desliza/rota automáticamente el token de actualización con el uso activo.
  • Mientras el usuario abra la aplicación dentro de los 14 días, permanecerá conectado sin necesidad de reautenticarse.

6. Diseños Adaptativos (Plegables y Tablets)

Construye pantallas que escalen suavemente entre clases de tamaño de ventana usando WindowSizeClass:

  • Compacto (<600dp): Una sola columna, barra de navegación inferior, hojas inferiores modales.
  • Medio (600dp - 840dp): Riel de navegación, cuadrícula de dos columnas.
  • Expandido (>840dp): Diseño persistente de dos paneles maestro-detalle lado a lado (Lista a la izquierda, inspector a la derecha).

7. Contraste de Color de Material 3 y Accesibilidad de Estados (WCAG 2.2 AA / AAA)

Los dispositivos móviles son particularmente propensos a fallos de contraste debido a la iluminación ambiental variable (luz solar directa, deslumbramiento exterior, atenuación de la batería OLED). Busca un contraste de texto WCAG 2.2 AAA ($\ge 7:1$) y cumple estrictamente con WCAG 1.4.11 (contraste de límites no textuales $\ge 3:1$) y WCAG 1.4.1 (uso del color).

7.1 La Trampa del FilterChip en Modo Oscuro de Material 3

  • El Defecto: Por defecto, el FilterChip de Material 3 en modo oscuro usa secondaryContainer (#37474F) para su fondo seleccionado contra la surface oscura (#14181E). Esto produce una relación de contraste inaceptable de 1.83:1. Con poca luz o deslumbramiento, los usuarios no pueden distinguir qué chip está activo.
  • La Solución:
    1. Aplica una definición de límite de alto contraste con selectedBorderColor = MaterialTheme.colorScheme.primary (que produce una relación de contraste de 9.88:1 en modo oscuro).
    2. Establece selectedBorderWidth = 1.5.dp.
    3. Cumple con WCAG 1.4.1 (estados que no dependen solo del color) proporcionando un icono de marca de verificación inicial:
      FilterChip(
          selected = isSelected,
          onClick = { onSelect() },
          label = { Text(label) },
          leadingIcon = if (isSelected) {
              { Icon(Icons.Filled.Done, contentDescription = null, Modifier.size(16.dp)) }
          } else null,
          border = FilterChipDefaults.filterChipBorder(
              enabled = true,
              selected = isSelected,
              selectedBorderColor = MaterialTheme.colorScheme.primary,
              selectedBorderWidth = 1.5.dp
          )
      )
      

7.2 Estándares de Legibilidad con Luz Solar y Deslumbramiento

  1. Texto Primario vs Superficie: Estandariza el modo oscuro con texto de alto contraste (onSurface #E1E2E8 o #F8FAFC sobre #14181E), logrando $\ge 13:1$ de contraste (superando WCAG AAA).
  2. Contornos de Controles de Formulario: OutlinedTextField y los bordes de botones de opción / casillas de verificación deben usar tokens outline que mantengan al menos $3:1$ de contraste contra las tarjetas contenedoras (Color(0xFF8D9199) o rgba(255, 255, 255, 0.20) explícito).
  3. Filas de Presets Compactos: Al organizar filas de chips compactos (por ejemplo, presets de retención 1h, 4h, 12h, 1d), preserva los tamaños objetivo y aplica maxLines = 1 con selectedBorderColor para que los chips nunca se envuelvan o se vean ambiguos.

8. Repositorios de Referencia de Código Abierto

Inspecciona estos proyectos de código abierto líderes en la industria de Android para obtener inspiración en diseño e implementación:

  • android/nowinandroid: Muestra emblemática de Compose con Material 3 de Google que demuestra tematización dinámica, diseños adaptativos y arquitectura limpia.
  • skydoves/Pokedex-Compose: Transiciones de elementos compartidos de nivel de producción (.sharedBounds / .sharedElement) y gestos suaves de hojas de detalle.
  • plainhub/plain-app: Implementación excepcional de gestión local del teléfono, tematización Material You y sincronización cliente-servidor receptiva.
  • Gurupreet/ComposeCookBook: Catálogo exhaustivo de animaciones de Compose de producción, barras inferiores y micro-interacciones de lienzo personalizadas.
  • signalapp/Signal-Android: Estándar de oro para almacenamiento local cifrado, trabajadores de buzón de salida en segundo plano y resiliencia de red.

Individual skills in this repo

This repo contains 4 individual skills — each has its own dedicated page.

axewhyzed/agentic-skills

>- Operational framework for high-density, zero-waste modern web applications, tool dashboards, and productive workspaces. Use when designing, building, or refactoring web interfaces (React, TypeScript), two-pane master-detail layouts, unified compose hubs, keyboard-driven navigation, command palettes (cmdk), live telemetry indicators, and granular authentication ergonomics.

axewhyzed/agentic-skills

>- Comprehensive guide and operational framework for engineering world-class, human-grade GitHub READMEs and technical repository documentation. Use whenever creating, auditing, or refactoring a README for open-source tools, self-hosted services, developer utilities, or client-server applications. Enforces clear documentation guidelines, the 30-second rule, dual-audience narrative balance, copy-pasteable quickstarts, and high-signal visual showcases.

axewhyzed/agentic-skills

>- Comprehensive guide and operational framework for software engineering standards, clean code, low-level design (LLD), high-level architecture (HLD), distributed systems, API contracts, database indexing, capacity planning, and architecture decision records (ADRs). Use this skill whenever designing, evaluating, refactoring, reviewing, or scaling software architectures, backend services, database schemas, APIs, or performance-critical systems.

axewhyzed/agentic-skills

>- Comprehensive operational framework and design intelligence for modern UI/UX design, design systems, visual hierarchy, design tokens, component architecture, high-density financial terminal aesthetics, accessibility (WCAG 2.2 AAA/AA), mobile ergonomics, data visualization, and complete interface revamps. Use this skill whenever auditing, designing, refactoring, building, or restyling user interfaces, dashboards, design systems, layouts, forms, data tables, animations, and micro-interactions.

Skills relacionados