El selector de fotos insertado: una forma más fluida de solicitar fotos y vídeos de forma privada en tu aplicación
Prepárate para mejorar la experiencia de usuario de tu aplicación con una nueva forma de usar el selector de fotos de Android. El nuevo selector de fotos insertado ofrece a los usuarios una forma cómoda y centrada en la privacidad de seleccionar fotos y vídeos directamente en la interfaz de tu aplicación. Ahora tu aplicación puede disfrutar de todas las ventajas del selector de fotos, incluido el acceso al contenido en la nube, integrado directamente en la experiencia de tu aplicación.
¿Por qué usar la función de inserción?
Somos conscientes de que muchas aplicaciones quieren ofrecer una experiencia integrada y fluida a los usuarios cuando seleccionan fotos o vídeos. El selector de fotos insertado se ha diseñado para eso: permite a los usuarios acceder rápidamente a sus fotos recientes sin salir de tu aplicación. También pueden explorar toda su biblioteca en su proveedor de contenido multimedia en la nube preferido (por ejemplo, Google Fotos), incluidas las fotos favoritas, los álbumes y la función de búsqueda. De esta forma, los usuarios no tienen que cambiar de aplicación ni preocuparse por si la foto que quieren está almacenada de forma local o en la nube.
Integración perfecta y privacidad mejorada
Con el selector de fotos insertado, tu aplicación no necesita acceder a las fotos ni a los vídeos del usuario hasta que este seleccione algo. Esto significa una mayor privacidad para tus usuarios y una experiencia más optimizada. Además, el selector de fotos insertado proporciona a los usuarios acceso a toda su biblioteca multimedia basada en la nube, mientras que el permiso de fotos estándar se limita a los archivos locales.
El selector de fotos integrado en Mensajes de Google
Mensajes de Google muestra el potencial del selector de fotos integrado. Así es como lo han integrado:
- Ubicación intuitiva: el selector de fotos se encuentra justo debajo del botón de la cámara, lo que ofrece a los usuarios una opción clara entre hacer una foto nueva o seleccionar una que ya tengan.
- Vista previa dinámica: inmediatamente después de que un usuario toque una foto, verá una vista previa grande, lo que le permitirá confirmar fácilmente su selección. Si desmarcan la foto, la vista previa desaparece, lo que permite que la experiencia sea clara y ordenada.
- Desplegar para ver más contenido: la vista inicial se ha simplificado para que puedas acceder fácilmente a las fotos recientes. Sin embargo, los usuarios pueden ampliar fácilmente el selector de fotos para buscar y elegir entre todas las fotos y vídeos de su biblioteca, incluido el contenido en la nube de Google Fotos.
- Respetar las decisiones de los usuarios: el selector de fotos insertado solo concede acceso a las fotos o los vídeos específicos que el usuario selecciona, lo que significa que pueden dejar de solicitar los permisos de fotos y vídeos por completo. De esta forma, Mensajes no tendrá que gestionar situaciones en las que los usuarios solo concedan acceso limitado a fotos y vídeos.
Implementación
La integración del selector de fotos insertado es sencilla gracias a la biblioteca Photo Picker Jetpack.
Jetpack Compose
Primero, incluye la biblioteca Jetpack Photo Picker como dependencia.
implementation("androidx.photopicker:photopicker-compose:1.0.0-alpha01")
La función composable EmbeddedPhotoPicker proporciona un mecanismo para incluir la interfaz de usuario del selector de fotos insertado directamente en tu pantalla de Compose. Este elemento componible crea un SurfaceView que aloja la interfaz de usuario del selector de fotos insertado. Gestiona la conexión al servicio EmbeddedPhotoPicker, se encarga de las interacciones de los usuarios y comunica los URIs de contenido multimedia seleccionados a la aplicación que llama.
@Composable fun EmbeddedPhotoPickerDemo() { // We keep track of the list of selected attachments var attachments by remember { mutableStateOf(emptyList<Uri>()) } val coroutineScope = rememberCoroutineScope() // We hide the bottom sheet by default but we show it when the user clicks on the button val scaffoldState = rememberBottomSheetScaffoldState( bottomSheetState = rememberStandardBottomSheetState( initialValue = SheetValue.Hidden, skipHiddenState = false ) ) // Customize the embedded photo picker val photoPickerInfo = EmbeddedPhotoPickerFeatureInfo .Builder() // Set limit the selection to 5 items .setMaxSelectionLimit(5) // Order the items selection (each item will have an index visible in the photo picker) .setOrderedSelection(true) // Set the accent color (red in this case, otherwise it follows the device's accent color) .setAccentColor(0xFF0000) .build() // The embedded photo picker state will be stored in this variable val photoPickerState = rememberEmbeddedPhotoPickerState( onSelectionComplete = { coroutineScope.launch { // Hide the bottom sheet once the user has clicked on the done button inside the picker scaffoldState.bottomSheetState.hide() } }, onUriPermissionGranted = { // We update our list of attachments with the new Uris granted attachments += it }, onUriPermissionRevoked = { // We update our list of attachments with the Uris revoked attachments -= it } ) SideEffect { val isExpanded = scaffoldState.bottomSheetState.targetValue == SheetValue.Expanded // We show/hide the embedded photo picker to match the bottom sheet state photoPickerState.setCurrentExpanded(isExpanded) } BottomSheetScaffold( topBar = { TopAppBar(title = { Text("Embedded Photo Picker demo") }) }, scaffoldState = scaffoldState, sheetPeekHeight = if (scaffoldState.bottomSheetState.isVisible) 400.dp else 0.dp, sheetContent = { Column(Modifier.fillMaxWidth()) { // We render the embedded photo picker inside the bottom sheet EmbeddedPhotoPicker( state = photoPickerState, embeddedPhotoPickerFeatureInfo = photoPickerInfo ) } } ) { innerPadding -> Column(Modifier.padding(innerPadding).fillMaxSize().padding(horizontal = 16.dp)) { Button(onClick = { coroutineScope.launch { // We expand the bottom sheet, which will trigger the embedded picker to be shown scaffoldState.bottomSheetState.partialExpand() } }) { Text("Open photo picker") } LazyVerticalGrid(columns = GridCells.Adaptive(minSize = 64.dp)) { // We render the image using the Coil library itemsIndexed(attachments) { index, uri -> AsyncImage( model = uri, contentDescription = "Image ${index + 1}", contentScale = ContentScale.Crop, modifier = Modifier.clickable { coroutineScope.launch { // When the user clicks on the media from the app's UI, we deselect it // from the embedded photo picker by calling the method deselectUri photoPickerState.deselectUri(uri) } } ) } } } } }
Visualizaciones
Primero, incluye la biblioteca Jetpack Photo Picker como dependencia.
implementation("androidx.photopicker:photopicker:1.0.0-alpha01")
Para añadir el selector de fotos insertado, debes añadir una entrada al archivo de diseño.
<view class="androidx.photopicker.EmbeddedPhotoPickerView"
android:id="@+id/photopicker"
android:layout_width="match_parent"
android:layout_height="match_parent" />Inicialízalo en tu actividad o fragmento.
// We keep track of the list of selected attachments private val _attachments = MutableStateFlow(emptyList<Uri>()) val attachments = _attachments.asStateFlow() private lateinit var picker: EmbeddedPhotoPickerView private var openSession: EmbeddedPhotoPickerSession? = null val pickerListener = object EmbeddedPhotoPickerStateChangeListener { override fun onSessionOpened (newSession: EmbeddedPhotoPickerSession) { openSession = newSession } override fun onSessionError (throwable: Throwable) {} override fun onUriPermissionGranted(uris: List<Uri>) { _attachments += uris } override fun onUriPermissionRevoked (uris: List<Uri>) { _attachments -= uris } override fun onSelectionComplete() { // Hide the embedded photo picker as the user is done with the photo/video selection } } override fun onCreate(savedInstanceState: Bundle?) { super.onCreate(savedInstanceState) setContentView(R.layout.main_view) // // Add the embedded photo picker to a bottom sheet to allow the dragging to display the full photo library // picker = findViewById(R.id.photopicker) picker.addEmbeddedPhotoPickerStateChangeListener(pickerListener) picker.setEmbeddedPhotoPickerFeatureInfo( // Set a custom accent color EmbeddedPhotoPickerFeatureInfo.Builder().setAccentColor(0xFF0000).build() ) }
Puedes llamar a diferentes métodos de EmbeddedPhotoPickerSession para interactuar con el selector insertado.
// Notify the embedded picker of a configuration change openSession.notifyConfigurationChanged(newConfig) // Update the embedded picker to expand following a user interaction openSession.notifyPhotoPickerExpanded(/* expanded: */ true) // Resize the embedded picker openSession.notifyResized(/* width: */ 512, /* height: */ 256) // Show/hide the embedded picker (after a form has been submitted) openSession.notifyVisibilityChanged(/* visible: */ false) // Remove unselected media from the embedded picker after they have been // unselected from the host app's UI openSession.requestRevokeUriPermission(removedUris)
Es importante tener en cuenta que la experiencia del selector de fotos insertado está disponible para los usuarios que tengan Android 14 (nivel 34 de la API) o una versión posterior con extensiones del SDK 15 o versiones posteriores. Consulta más información sobre la disponibilidad del selector de fotos en los dispositivos.
Para mejorar la privacidad y la seguridad de los usuarios, el sistema renderiza el selector de fotos insertado de forma que se impida cualquier dibujo o superposición. Esta decisión de diseño implica que tu experiencia de usuario debe considerar el área de visualización del selector de fotos como un elemento independiente y específico, como si se tratara de un banner publicitario.
Si tienes alguna sugerencia o comentario, envía una incidencia a nuestro gestor de incidencias.
Seguir leyendo
-
Noticias sobre productos
Nos complace anunciar importantes actualizaciones de nuestros recursos de diseño, que te ofrecen la guía completa que necesitas para crear aplicaciones Android adaptables y de alta calidad en todos los factores de forma. Ahora tenemos una guía sobre la experiencia de escritorio y una galería de diseño de Android renovada.
Ivy Knight • Tiempo de lectura: 2 min
-
Noticias sobre productos
Se ha lanzado la primera versión alfa de Room 3.0. Room 3.0 es una versión principal de la biblioteca que introduce cambios importantes y se centra en Kotlin Multiplatform (KMP). Además, añade compatibilidad con JavaScript y WebAssembly (WASM) a la compatibilidad con Android, iOS y JVM para ordenadores.
Daniel Santiago Rivera • Tiempo de lectura: 4 min
-
Noticias sobre productos
Hoy nos complace compartir cómo estamos incorporando la optimización automática dirigida por comentarios (AutoFDO) al kernel de Android para ofrecer a los usuarios mejoras significativas en el rendimiento.
Yabin Cui • Tiempo de lectura: 4 min
Mantente al día
Recibe cada semana en tu bandeja de entrada las últimas novedades sobre el desarrollo para Android.