Cómo tomar fotografías
Capture y guarde una imagen
Cómo tomar fotografías es una lección gratuita de Android Academy en CoddyKit. Esta es la lección 3 de 4. Puedes leer la lección completa abajo gratuitamente — luego la practicas en el navegador con un editor de código integrado y un tutor de IA 24/7. Forma parte de la ruta de aprendizaje de Android Academy, y tu progreso se sincroniza en la web y la app de CoddyKit. El curso de Android Academy incluye 4 lecciones en total.
Captura de una foto
Con la vista previa en pantalla, el siguiente paso es tomar una foto. CameRX se encarga de ello mediante el caso de uso ImageCapture.
Vinculará ImageCapture junto con la vista previa y, después, llamará a takePicture() cuando el usuario pulse el botón del obturador para guardar el resultado en la galería del dispositivo.
Creación del caso de uso ImageCapture
ImageCapture se configura mediante un builder. Una opción útil es el modo de captura, que establece un equilibrio entre latencia y calidad:
CAPTURE_MODE_MINIMIZE_LATENCY: obturador rápido.CAPTURE_MODE_MAXIMIZE_QUALITY: máxima calidad de imagen, con una ligera reducción de velocidad.
val imageCapture = ImageCapture.Builder()
.setCaptureMode(ImageCapture.CAPTURE_MODE_MINIMIZE_LATENCY)
.build()Vinculación de Preview + ImageCapture
Puede vincular varios casos de uso a la vez. Pase tanto preview como imageCapture a bindToLifecycle para que la cámara proporcione la imagen en directo y esté lista para tomar una foto.
cameraProvider.unbindAll()
cameraProvider.bindToLifecycle(
lifecycleOwner,
CameraSelector.DEFAULT_BACK_CAMERA,
preview,
imageCapture
)Dónde guardar: MediaStore
La forma moderna y compatible con el almacenamiento de ámbito restringido de guardar una foto es utilizar MediaStore. Describa el archivo (nombre, tipo MIME y carpeta) con ContentValues y deje que el sistema lo coloque en la colección compartida Pictures.
Esto funciona sin el permiso heredado WRITE_EXTERNAL_STORAGE en Android 10 y versiones posteriores.
val name = "photo_${System.currentTimeMillis()}"
val contentValues = ContentValues().apply {
put(MediaStore.MediaColumns.DISPLAY_NAME, name)
put(MediaStore.MediaColumns.MIME_TYPE, "image/jpeg")
put(MediaStore.Images.Media.RELATIVE_PATH, "Pictures/MyApp")
}Opciones de salida
Para indicar a CameraX dónde escribir el archivo JPEG, cree un OutputFileOptions a partir del content resolver, el URI de la colección de destino y sus ContentValues.
val outputOptions = ImageCapture.OutputFileOptions
.Builder(
context.contentResolver,
MediaStore.Images.Media.EXTERNAL_CONTENT_URI,
contentValues
)
.build()Llamada a takePicture()
Ahora active la captura. takePicture() recibe las opciones de salida, un Executor y un callback. CameRX informa del resultado correcto o del error de forma asíncrona.
Use ContextCompat.getMainExecutor(context) para que el callback se ejecute en el hilo principal.
imageCapture.takePicture(
outputOptions,
ContextCompat.getMainExecutor(context),
object : ImageCapture.OnImageSavedCallback {
override fun onImageSaved(output: ImageCapture.OutputFileResults) {
val savedUri = output.savedUri
// Photo saved! Show a confirmation.
}
override fun onError(exc: ImageCaptureException) {
// Handle the failure.
}
}
)Gestionar el resultado
Si la operación se realiza correctamente, OutputFileResults.savedUri proporciona el URI de la imagen guardada. Puede mostrarla (con Coil), compartirla o mostrar un Snackbar para confirmar que se ha guardado.
Si se produce un error, ImageCaptureException indica qué ha ocurrido; regístrelo e informe al usuario.
override fun onImageSaved(output: ImageCapture.OutputFileResults) {
val uri = output.savedUri ?: return
Toast.makeText(context, "Saved: $uri", Toast.LENGTH_SHORT).show()
}Conectar un botón de obturación
En Compose, superponga un botón de obturación sobre la vista previa mediante un Box. Eleve la referencia de ImageCapture para que el onClick del botón pueda llamar a takePhoto.
Box(modifier = Modifier.fillMaxSize()) {
CameraPreview(imageCapture = imageCapture)
IconButton(
onClick = { takePhoto(context, imageCapture) },
modifier = Modifier
.align(Alignment.BottomCenter)
.padding(32.dp)
) {
Icon(Icons.Default.PhotoCamera, contentDescription = "Take photo")
}
}Extraer takePhoto()
Mantenga limpio el composable trasladando la lógica de captura a una función auxiliar. Esta recibe el contexto y el caso de uso ImageCapture, crea las opciones de salida y llama a takePicture.
fun takePhoto(context: Context, imageCapture: ImageCapture) {
val values = ContentValues().apply {
put(MediaStore.MediaColumns.DISPLAY_NAME, "IMG_${System.currentTimeMillis()}")
put(MediaStore.MediaColumns.MIME_TYPE, "image/jpeg")
}
val options = ImageCapture.OutputFileOptions.Builder(
context.contentResolver,
MediaStore.Images.Media.EXTERNAL_CONTENT_URI,
values
).build()
imageCapture.takePicture(
options,
ContextCompat.getMainExecutor(context),
object : ImageCapture.OnImageSavedCallback {
override fun onImageSaved(o: ImageCapture.OutputFileResults) {}
override fun onError(e: ImageCaptureException) {}
}
)
}Flash y rotación
Dos últimos ajustes:
- Flash: establezca
imageCapture.flashModeenFLASH_MODE_ON,OFFoAUTO. - Rotación: CameRX utiliza la rotación objetivo para orientar correctamente el JPEG guardado; manténgala actualizada para obtener una orientación precisa.
imageCapture.flashMode = ImageCapture.FLASH_MODE_AUTO
// Update target rotation when the device rotates:
imageCapture.targetRotation = display.rotationUnirlo todo
El flujo completo para tomar una foto es: crear ImageCapture → vincularlo con la vista previa → al pulsar el obturador, crear OutputFileOptions y llamar a takePicture → gestionar onImageSaved / onError.
Con solo unas pocas líneas, ya dispone de una cámara completa que guarda las fotos en la galería.
Comprobación rápida
Confirme que comprende el flujo de captura de fotos.
Resumen
Ya puede tomar y guardar fotos con CameRX:
- Cree un caso de uso
ImageCapturey vincúlelo con la vista previa. - Describa la salida con
ContentValuesyMediaStorepara utilizar el almacenamiento específico de la aplicación. - Llame a
takePicture()conOutputFileOptions, un executor y unOnImageSavedCallback. - Lea
savedUrisi la operación se realiza correctamente; gestioneImageCaptureExceptionsi se produce un error.
A continuación, grabará vídeo con el caso de uso VideoCapture.
Preguntas frecuentes
¿La lección «Cómo tomar fotografías» es gratis?
Sí — el texto completo de «Cómo tomar fotografías» es gratis para leer aquí en la web. Para practicarla de forma interactiva (editor de código integrado y tutor de IA 24/7) y desbloquear el resto del curso de Android Academy, actualiza a CoddyKit PRO. El curso de Android Academy incluye 4 lecciones en total.
¿Qué aprenderé en «Cómo tomar fotografías»?
Capture y guarde una imagen Practicas Android Academy con código real que ejecutas directamente en el navegador, y un tutor de IA 24/7 responde tus preguntas mientras trabajas en la lección.
¿Necesito experiencia previa para empezar Android Academy?
No se requiere experiencia previa. Android Academy en CoddyKit está estructurado para principiantes hasta estudiantes avanzados, así que puedes empezar aquí o desde el inicio y avanzar a tu ritmo. Esta es la lección 3 de 4.
¿Cuánto tiempo toma la lección «Cómo tomar fotografías»?
La mayoría de las lecciones de CoddyKit toman alrededor de 5–10 minutos. Cada una es compacta e interactiva, así que avanzas constantemente y retomas exactamente por donde dejaste en la web y la app.
¿Puedo escribir y ejecutar código en esta lección de Android Academy?
Sí. Cada lección de Android Academy incluye un editor de código integrado, así que escribes y ejecutas código real directamente en tu navegador y obtienes retroalimentación instantánea de IA — sin configuración local necesaria.
Todas las lecciones de este curso
- Descripción general de CameraX
- Cómo mostrar una vista previa de la cámara
- Cómo tomar fotografías
- Grabación de vídeo