Probando Xamarin.Forms XAML Hot Reload

Iterar en UI

Si, conozco esa sensación. Hablo de los segundos esperando a desplegar la App de nuevo en un emulador o dispositivo para probar los últimos cambios en UI trabajando con Xamarin.Forms. Realizando la misma tarea varias veces se vuelve en algo que podría/debería ser más eficiente.

En el pasado Xamarin Developer Summit se ha anunciado Xamarin.Forms XAML Hot Reload.

Xamarin.Forms XAML Hot Reload

Llega Xamarin.Forms XAML Hot Reload

El objetivo principal de Hot Reload es permitir ver cambios de XAML al vuelo sin necesidad de compilar y desplegar constantemente. Las características fundamentales son:

  • Permite ver los cambios de XAML al vuelo una vez desplegada la App en modo depuración.
  • Funciona en Visual Studio 2019 tanto en Windows como macOS.
  • Funciona tanto para iOS como Android.
  • Soporta emuladores como dispositivos físicos.
  • Soporta plugins, librerías de terceros, SkiaSharp, etc.

¿Cómo funciona?

Actualmente al trabajar iterando interfaces en Xamarin.Forms el ciclo consiste en hacer un cambio en XAML, compilar, desplegar y depurar. Ante cualquier otro cambio, volver a repetir todo el proceso.

XAML Hot Reload llega para ayudar reducir drásticamente los pasos y tiempos necesarios para iterar en UIs. No hace falta hacer nada especial para usar XAML Hot Reload. Sencillamente, compila y despliega tu App como lo harías normalmente y a partir de ese momento solo tienes que hacer cualquier cambio en XAML. Es decir, tampoco es necesario instalar ningun paquete NuGet adicional en la App o realizar cualquier lógica de incialización en la misma.

Esto es así porque XAML Hot Reload usa el depurador y no una conexión de red, asi que funciona con o sin conectividad. Edita XAML y guarda los cambios. Al volver a cargar, se mantendrá el estado de navegación. Si usas el patrón MVVM, el estado de la interfaz de usuario vinculado a la ViewModel permanecerá intacto.

Suena genial, ¿verdad?. Veamoslo en funcionamiento. Se soportan cambios en cualquier tipo de archivo XAML, es decir, se soportan páginas, ContentView’s, App, recursos o Shell.

Para las pruebas he usado el ejemplo RottenUI de Kym Phillpotts. Es un ejemplo visualmente atractivo pero además:

  • Hace uso de estilos a nivel de App y de página.
  • Hace uso de ContentView definido en otro archivo.
  • Usa plugins de comunidad como PancakeView.
  • Usa SkiaSharp.

Comenzamos haciendo cambios en la página principal:

Cambios a nivel de página

Continuamos haciendo cambios en una ContentView usada en la página pero definida en otro archivo:

ContentView usada en la página

Y también a nivel de App:

Cambios a nivel de App

Y todo…en modo avión sin conexión a internet, etc.

Sin internet!

Preview privada

Si quieres probar XAML Hot Reload, desde ya, puedes registrarte para obtener una Preview. Puede encontrar toda la información  aquí: https://devblogs.microsoft.com/xamarin/xaml-hot-reload.

Se estan añadiendo a grupos por lotes, así que no te preocupes si no puedes obtenerlo de forma inmediato. Y recuerda; cualquier feedback es importante para continuar mejorando.

Estoy seguro de que Hot Reload hará que tu vida desarrollando Xamarin.Forms mucho mejor.

Happy reloading!

Más información

Anuncios

[Offtopic] Me uno al equipo de Xamarin.Forms

Nuevos retos

Hace ya un tiempo que entre a formar parte de Microsoft, en concreto siendo parte del equipo de Visual Studio para macOS. Todo un reto y una gran experiencia!. Me he encontrado un fantástico equipo donde he logrado aprender en muchas áreas (trabajo en remoto, gestión, código, testing, etc.) y donde espero haber contribuido a continuar la continua mejora del IDE.

Los lectores de este blog, sabrán que me entusiasma el desarrollo móvil y en concreto con C# usando Xamarin; especialmente Xamarin.Forms. Por eso me entusiasma compartir que a partir de hoy, entro a formar parte del equipo de Xamarin.Forms.

Tengo muchas ganas de continuar aprendiendo y sobretodo de poder contribuir a continuar mejorando y hacer crecer a Xamarin.Forms!.

Conversando sobre Xamarin en Viernes de Punto Net

Viernes de .net

Viernes de Punto Net es un canal de Youtube de habla hispana organizado por Claudio Sanchez y Leomaris Reyes, dedicado a promover tecnologías .NET en español.

Conversando sobre Xamarin

Recientemente, he tenido el placer de poder participar y charlar sobre .Net y especialmente de Xamarin. Fue una conversación amena e informal pero donde abordamos muchos temas como las herramientas para diseñar interfaces de usuario, consejos para realizar interfaces atractivas con Xamarin.Forms, hablamos de los retos de UI con Xamarin y mucho más.

La parte más interesante es que llevan bastantes programas y siguen adelante. Si te interesa .NET te recomiendo pasar por su canal de YouTube!.

Más información

Twitch y código en directo

Introducción

Desde el año pasado y en especial este año hemos podido ver una tendencia muy positiva en la comunidad Xamarin, las sesiones de código en vivo en Twitch. Ya sea crear aplicaciones, replicar interfaces de usuario, crear controles, etc. Una idea que ya se me había pasado por la cabeza previamente e incluso había hablado con algunos compañeros de la comunidad.

Código en directo

Ver a alguien analizar, desarrollar y codificar un problema en directo me parece muy instructivo. Además, parece divertido!.

Código en directo

Voy a comenzar a utilizar Twitch para tener sesiones de código en directo. Una forma divertida de continuar aprendiendo además de ayudar a otros.

¿Cuál es la idea?

La idea es similar a la de este blog. Una forma de comunicarse e intentar ayudar. Al igual que en el blog, la clave es la de la constancia. Tendremos sesiones de forma periódica.

Pero…¿y la temática?.

He pensado bien que podría ser interesante para vosotros y divertido para mi. Tras analizar diferentes opciones tendremos tres tipo de contenido:

  • Introducción a Xamarin.Forms: Al comenzar a pensar en que emitir sesiones de código en directo me apetecía bastante replicar diseños o hacer nuevos controles en Xamarin.Forms, etc. Me parecen temas interesantes pero son temas más avanzados. Pensando en una opción divertida de hacer y que ayude a nuevos desarrolladores a inciarse en el desarrollo móvil he pensado en la idea de sesiones de incialización a Xamarin.Forms. Se comenzará desde los conceptos básicos e iremos subiendo viendo casi todo lo necesario para hacer Apps. El contenido fundamental sera código en directo mezclado con alguna pequeña presentación que nos ayude como guia. Todo el contenido que vamos a ir creando lo subiremos a un repositorio en GitHub. La idea es que, al final de todas las trasmisiones relacionadas con este bloque, tendremos una gran cantidad de horas de video y ejemplos que puedan ayudar a desarrolladores a introducirse a Xamarin.Forms.
  • Desarrollo en directo: Principalmente replicaremos diseños de Dribbble o aplicaciones reales junto con la creación de controles (Custom Renderers, SkiaSharp, etc.). Veremos como abordar diseños, utilizaremos alguna herramienta para extraer colores, crear iconos, etc. Al igual que en el caso anterior, cada diseño tendrá su propio repositorio en GitHub.
  • Invitados: La comunidad de Xamarin es increíble. Muchos desarrolladores y empresas haciendo grandes Apps, herramientas, librerías, etc. La idea de este bloque de sesiones será la de tener a alguien de la comunidad viendo un tema concreto. Por ejemplo, si invitamos a alguien que ha creado una librería de controles, veremos en directo que aporta y como usar la librería, consejos para crear librerías, etc.

La introducción a Xamarin.Forms será en español mientras que los otros dos bloques pueden llegar a tener alguna sesión en español también (dependerá del invitado o del espectadores).

¿Cuándo comienza?

Comenzaré a muy pronto. Anunciaré cada trasmisión días antes vía Twitter.

¿Qué os parece la idea?.

[Material DotNet2019] Optimizar Apps con Xamarin.Forms

El evento

El pasado 19 de Junio tenía lugar la DotNet2019. Un gran día repleto de sesiones técnicas cubriendo todo el espectro de tecnologías .NET, desde Xamarin, Azure, IoT, VR, etc.

Fue un día genial de grandes sesiones pero también de encontrarte con  excompañeros, grandes amigos, desvirtualizar a nuevos amigos, networking, etc. Quisiera agradecer a todos los ponentes y asistentes por hacer posible el evento. Y por supuesto, mi enhorabuena a toda la organización por hacer que algo tan grande y complejo fluyese de forma tan natural y sencilla.

El Material

He tenido en placer de poder participar en el evento con una sesión acerca de Xamarin.Forms y formas de obtener el mejor rendimiento posible.

En esta sesión vimos siempre con forma de gráficas, diferentes medidas, etc.

  • Uso de XAMLC.
  • Uso de Fast Renderers y comparativa de rendimiento.
  • Rendimiento de CollectionView en comparación al ListView.
  • Compresión de Layouts.
  • Consejos al utilizar Layouts.
  • Consejos al utilizar imágenes.
  • Consejos al crear Custom Renderers.
  • Revisión del rendimiento usando Visual o Shell.
  • Etc.

Puedes encontrar todos los ejemplos, gráficas y comparativas en GitHub:

Ver GitHub

Hasta el año próximo!

Más información

Xamarin UI Julio

Introducción

Recientemente hablé con Steven Thewissen que quería volver a promover la idea de Snppts. También hablamos de que sería genial tener más y más comunidad haciendo ejemplos con interfaces atractivas con Xamarin.Forms. De esta forma, y basandose en idea de Luis Matos que en Febrero hizo el mes de Xamarin, de la mano de Steven nace el Xamarin UI de Julio.

Xamarin UI de Julio

El objetivo es lograr publicar durante todo el mes de julio un artículo de parte de la comunidad de Xamarin. Cada uno de los  colaboradores lo publicará en su propio blog, y luego estará disponible en un calendario común. De esa manera, entre todos crearemos una publicación sorpresa  diaria. Las publicaciones del blog se escribirán en inglés y tratarán sobre un tema concreto.
Suena bien, pero ¿cuál es el tema?.

La creación de interfaces de usuario es una parte esencial de la creación de una aplicación. En actualizaciones recientes, Xamarin.Forms ha agregado más y más características relacionadas como Visual y Shell, y controles adicionales como CollectionView para permitir a los desarrolladores crear aplicaciones con mejor aspecto.  Así que el tema fundamental será crear interfaces de usuario con Xamarin.Forms.

¿No sabes de que escribir?. No te preocupes, sabemos que es un tema bastante amplio. Si tienes dificultades para encontrar inspiración, a continuación algunas ideas:

  • Animaciones.
  • Empezando con Shell.
  • Utilizar y/o personalizar Visual.
  • Interfaz avanzada con CollectionView,
  • Herramientas a usar (generación de iconos, LiveXAML, MFractor, etc.)
  • Recreando una interfaz de usuario existente con Xamarin.
  • Construyendo un control personalizado.
  • Etc.

¿Cuáles son los pasos a seguir para participar?

  1. Reserva un slot en Twitter (usando los hashtags #Xamarin y #XamarinUIJuly).
  2. Escribe tu blog, en inglés (animo a toda la comunidad, si necesitas ayuda con ello, puedo ayudar).
  3. Publica tu artículo en tu blog en la fecha especificada (según la fecha elegida en el calendario).
  4. Publica el enlace a tu blog en Twitter con los hashtags #Xamarin #XamarinUIJuly.

Sencillo, ¿verdad?.

Más información

[Xamarin.Forms] Mejorar el rendimiento en el tiempo de arranque

Introducción

Además de cuidar detalles como la funcionalidad o la apariencia visual de nuestra aplicación, nuestra aplicación debe funcionar correctamente bajo todas las condiciones en todos los dispositivos para la que sea lanzada.

Un punto importante a revisar siempre suele ser, el tiempo de arranque de la aplicación.

¿Conoces conceptos como AOT?, ¿fast renderers?. En este artículo vamos a repasar algunos conceptos que podemos aplicar para tener un impacto positivo en los tiempos de arranque de la aplicación.

XAMLC

Si defines la interfaz de usuario de la aplicación Xamarin.Forms con XAML tienes la opción de utilizar XamlCompilationOptions.

Cuenta con dos valores:

Compile.

  • Acelera la carga de elementos visuales.
  • Reduce el tamaño del paquete.
  • La compilación (AOT) es más larga.

Skip.

  • Valor por defecto para mantener retocompatibilidad con versiones antiguas de Xamarin.Forms.
  • No hay validación en tiempo de ejecución de XAML.

Ejemplo de uso:

[assembly: XamlCompilation(XamlCompilationOptions.Compile)]

La diferencia:

Rendimiento con XAMLC

NOTA: Resultado obtenido tras 5 mediciones utilizando Android.

Fast Renderers

Hablamos de cambios realizados en Xamarin.Forms con el objetivo de reducir a mínimos el número de operaciones y cálculos a realizar para renderizar el control y gestionar su tamaño y posición.

Hasta ahora, la mayoría de los renderers en Android se componían de dos vistas:

  • Control nativo, como Button.
  • Un contenedor ViewGroup que se encargaba de controlar aspectos como los gestos, etc.

Sin embargo, este enfoque tiene una implicación directa en el rendimiento al crear dos elementos por cada control, lo que resulta en un árbol visual más complejo, requiere más memoria y más capacidad de procesamiento para representar en la pantalla.

Los Fast Renderers reducen la inflación y los tiempos para el renderizado de un control de Xamarin.Forms.

Veamos un ejemplo de jerarquía de elementos sin utilizar Fast Renderers:

Jerarquía sin utilizar Fast Renderers

Y utilizando Fast Renderers:

Jerarquía utilizando Fast Renderers

La diferencia:

Rendimiento con Fast Renderers

Los Fast Renderers están disponibles para los siguientes controles de Xamarin.Forms en Android:

  • Button
  • Image
  • Label
  • Frame

Desde Xamarin.Forms 4.0 se utilizan por defecto los Fast Renderers. Si quieres no utilizarlos, puedes hacerlo:

Forms.SetFlags("UseLegacyRenderers");

Configuración de la App

La opción compilación AOT habilita la compilación Ahead Of Time de los ensamblados. Cuando esta opción está habilitada, la sobrecarga de inicio Just-In-Time (JIT) se minimiza al precompilar ensamblados antes del tiempo de ejecución. El código nativo resultante se incluye en el paquete (APK) junto con los ensamblados sin compilar. Esto da como resultado un tiempo de inicio de la aplicación más reducido, pero a costa de tamaños APK más grandes.

A costa de tiempos de compilación más lentos, el compilador de optimización de LLVM debe crear un código compilado más pequeño y rápido (en las pruebas, efectivamente conseguimos un paquete más ligero aunque no tenemos reducción en lso tiempos de arranque de la aplicación).

A continuación, una comparativa del tiempo de arranque de la aplicación en milisegundos entre el uso de JIT, AOT y AOT junto con la opciónde optimización de LLVM:

Rendimiento con diferentes configuraciones

Como se puede observar, la reducción de tiempo usando AOT es notoria pero…¿cómo afecta al tamaño del paquete?.

Comparativa del peso del paquete

Puedes encontrar los ejemplos utilizados así como archivos Excel con las medidas en GitHub:

Ver GitHub

Más información

[Xamarin.Forms] Mejorar el rendimiento al trabajar con imágenes

Introducción

El uso de imágenes en aplicaciones móviles es habitual. Es un elemento clave a la hora de conseguir buenos resultados visuales. Sin embargo, también suelen ser uno de los puntos clave que impactan en el rendimiento de la aplicación. Problemas como:

  • Alto consumo de memoria.
  • Bloqueo de la UI (carga de imágenes en el hilo de UI, etc).
  • Etc.

En este artículo, vamos a realizar comparaciones en el rendimiento del control Image de Xamarin.Forms entre diferentes versiones, así como una comparativa con FFImageLoading y GlideX.

Para realizar las comaparativas vamos a necesitar un ejemplo y algo de código para obtener información. Nuestro ejemplo va a ser una versión modificada del gran ejemplo realizado por Jonathan Peppers en Glidex.

El ejemplo

A la hora de medir, vamos a utilizar:

System.Diagnostics.Process.GetCurrentProcess().WorkingSet64

Para obtener la cantidad de bytes que se estan consumiendo.

Imágenes en Xamarin.Forms

El control Image de Xamarin.Forms permite la carga de imágenes desde diferentes fuentes (URL, recurso incrustrado, etc.). El rendimiento general es correcto aunque con mejoras (mejoras en la cache, reutilizar recursos, etc.).

Desde la versión 4.0 de Xamarin.Forms se han comenzado a realizar mejoras en la gestión de imágenes. Pero…¿realmente tenemos mejora?.

Para contestar de forma correcta, vamos a cargar 100 imágenes en un Grid (evitamos usar listados y reutilización de celdas para conseguir tener un volumen elevado de imágenes en el árbol visual y en memoria).

Lanzamos la aplicación tanto utilizando la versión 3.6 como la versión 4.0. Tras lanzar la aplicación 5 veces y hacer la media de la memoria consumida:

Mejoras en la gestión de imágenes en Xamarin.Forms 4.0

Xamarin.Forms 4.0 consume una media de un 15% menos de memoria con respecto a la versión 3.6. Una buena mejora en la gestión de imágenes pero…¿podemos conseguir mejorar más al gestionar las imágenes?.

FFImageLoading

FFImageLoading es una de las librerías de la comunidad más usadas y más recomendadas. Esta librería tiene como objetivo cargar imágenes de la forma más eficiente posible. Entre las características principales (y que tienen impacto en el rendimiento):

  • Cache de imágenes en memoria y disco.
  • Múltiples imágenes usando el mismo origen (url, ruta, recurso) usarán solo un mapa de bits que se almacena en caché en memoria (menos uso de memoria).
  • Placeholders de carga y error.
  • Las imágenes se pueden ajustar automáticamente a un tamaño especificado (menos uso de memoria).
  • Etc.

Tras realizar benchmarking entre FFImageLoading y el control Image de Xamarin.Forms, gracias a las opciones de cache, ajuste de tamaño, etc., obtenemos mejor rendimiento con FFImageLoading.

GlideX

GlideX.Forms nos permite utilizar Glide (Una librería de carga y almacenamiento de imágenes para Android enfocada en el rendimiento) en Xamarin.Forms Android.

Al igual que anteriormente, hemos realizado benchmarking en Android entre el control Image de Xamarin.Forms, FFImageLoading y GlideX. GlideX es la opción más óptima en Android superando levemente a FFImageLoading y con una diferencia más considerable con respecto al control Image.

IImageSourceHandler

Así que, GlideX es más eficiente en Android pero…¿que usamos en iOS?. Podríamos utilizar FFImageLoading directamente en ambas plataformas, es una buena opción. Sin embargo, podríamos usar FFImageLoading en iOS y GlideX en Android.

Desde Xamarin.Forms 2.3.5, tenemos la interfaz IImageSourceHandler. Permite implementar ImageSource en la plataforma.

Ejemplo básico (en iOS):

public class ImageSourceHandler : IImageSourceHandler
{
     public Task<UIImage> LoadImageAsync(
          ImageSource imageSource,
          CancellationToken cancellationToken = new CancellationToken(),
          float scale = 1)
     {
          ...
     }
}

Podemos gestionar la fuente de imágenes de forma sencilla, utilizando en cada plataforma la opción que necesitemos. Jean-Marie Alfonsi ha creado Xamarin.Forms.ImageSourceHandlers con esta misma idea. Su uso es sencillo.

En Android, vamos a utilizar GlideX. Necesitaremos la inicialización de la librería.

Android.Glide.Forms.Init();

Mientras que en iOS, vamos a usar FFImageLoading:

FFImageLoading.FormsHandler.Init();

Benchmarking

Llegados a este punto, tenemos todo lo necesario para obtener datos y sacar algunas conclusiones. La gestión de imágenes es un punto importante a la hora de crear aplicaciones móviles. En Xamarin.Forms se continua mejorando y lo podemos ver en los datos obtenidos comparando la versión 3.6 y la versión 4.0.

A continuación, una comparativa en Android de la misma aplicación cargando 100 imágenes utilizando el control Image de Xamarin.Forms, FFImageLoading y GlideX:

La comparativa

NOTA: Los datos salen de la media de 5 medidas.

Puedes encontrar los ejemplos utilizados así como archivos Excel con las medidas en GitHub:

Ver GitHub

Otras recomendaciones

Podemos aplicar otra serie de acciones para mejorar considerablemente el rendimiento a la hora de trabajar con imágenes:

  • Evitar la necesidad de reducir el tamaño de imágenes (memoria consumida) en el dispositivo. Si tenemos control sobre el servidor proveedor de las imágenes, gestionar las imágenes en el mismo.
  • Además del punto anterior, reducir las imágenes locales utilizadas. Podemos conseguirlo de varias formas. Controlando el tamaño (o formato) de la imagen,  o bien, se pueden utilizar servicios como tinypng.

Más información

[Quedada Informal] CartujaDotNet

Quedada múltiple

Desde CartujaDotNet, grupo de usuarios .NET de Sevilla vamos a realizar una quedada informal para charlar abiertamente sobre tecnologías Microsoft, herramientas utilizadas, intercambiar impresiones, etc. Además, se hablará de próximos eventos entre otros temas de interés.

No hace falta confirmar asistencia, y por supuesto será gratuito.

¿Te apuntas?

A continuación tienes disponible la fecha, hora y lugar:

  • Día: 28 de Mayo (Martes)
  • Horario:  19:00h
  • Lugar: En la Terraza del McDonald’s de Santa Justa

Más información

[Xamarin.Forms UI Challenge] Art News, transiciones entre páginas

Introducción

Volvemos a por un reto de interfaz de usuario con Xamarin.Forms. En este artículo, vamos a tomar como referencia un diseño de Dribbble (por Shirley Yao), que intentaremos replicar con paso a paso.

Art News

Vamos a intentar replicar la UI del diseño paso a paso en Xamarin.Forms.

Los retos del ejemplo

Vamos a replicar dos pantallas con algunos retos, pero la clave del ejemplo es la transición de elementos compartidos entre las dos páginas.

  • Listado horizontal: La llegada de CollectionView es no solo una mejora en el rendimiento a la hora de trabajar con colecciones, también con diferentes Layouts (listados horizontales, GridViews, etc.). En este ejemplo, el número de elementos en el listado horizontal es bajo, por lo que podemos también hacer uso de un sencillo StackLayout y Bindable Layout.
  • Grid de fotos en los detalles: En caso de mostrar un número limitado o concreto de fotos en la galería mostrada en la página de detalles, podría usar un Layout. Probablemente un Grid o FlexLayout. Sin embargo, en caso de no ser limitado, CollectionView nos permite mostrar un número indeterminado de fotos en dos columnas de forma sencilla.
  • Transición entre páginas: Por defecto, no tenemos soporte a transiciones de páginas en Xamarin.Forms. Contamos con dos tipos de transiciones diferentes. Por un lado, las transiciones tradiciones que implican una animación de toda la página al entrar o salir. Por otro lado, tenemos las conocidas como transcisiones de elementos compartidos. En muchas ocasiones, tenemos un elemento visual compartido entre dos páginas (por ejemplo, una imagen) para trasmitir una sensación de fluidez y continuidad. En este ejemplo, veremos ambas opciones. Es necesario crear un Custom Renderer de la NavigationPage para conseguir el objetivo. Por suerte, no partimos de cero, utilizaremos Xamarin.Plugin.SharedTransitions.
  • Animaciones: Necesitamos una sencilla animación de Fade In y translación desde la parte inferior hacia la superior al navegar a la página de detalles (además de la transición). Xamarin.Forms cuenta con una completa Api de animaciones. En el ejemplo usaremos Xamanimation que nos ofrece animaciones prepadas, Storyboard y la posibilidad de usarlo todo desde XAML.

Listado horizontal

Para crear el listado horizontal utilizaremos Bindable Layouts.

<ScrollView 
     Orientation="Horizontal"
     HorizontalScrollBarVisibility="Default"
     VerticalScrollBarVisibility="Never">
     <StackLayout 
          x:Name="Highlights"
          Padding="20, 0, 0, 36"
          Orientation="Horizontal"
          BindableLayout.ItemsSource="{Binding Author.Highlights}">
          <BindableLayout.ItemTemplate>
               <DataTemplate>
                     <Grid
                          x:Name="HighlightTemplate"
                          RowSpacing="0"
                          Style="{StaticResource HighlightStyle}">
                          ...
                    </Grid>
               </DataTemplate>
          </BindableLayout.ItemTemplate>
     </StackLayout>
</ScrollView>

Usamos un scroll horizontal (sin mostrar la barra de scroll vertical) con un StackLayout apilando los elementos horizontalmente. La clave es el uso de las propiedades BindableLayout.ItemsSource y BindableLayout.ItemTemplate.

El resultado:

Listado horizontal

NOTA: En caso de contar con un número de elementos elevado, recuerda que no tenemos virtualización, etc. al usar Bindable Layouts. En dicho caso, es más recomendable utilizar CollectionView.

Grid de fotos en los detalles

El Layout de fotos se puede conseguir de diferentes formas. Probablemente, y ante un número determinado de elementos (un número bajo de elementos) se podría usar un Grid o FlexLayout con Bindable Layouts. Sin embargo, en este caso se ha utilizado CollectionView.

<CollectionView
     Grid.Row="1"
     ItemsSource="{Binding ArtItem.Related}"
     SelectionMode="None"
     InputTransparent="True">
     <CollectionView.ItemsLayout>
           <GridItemsLayout 
                Orientation="Vertical" 
                Span="2"/>
     </CollectionView.ItemsLayout>
     <CollectionView.ItemTemplate>
          <DataTemplate>
               <templates:RelatedContentTemplate />
          </DataTemplate>
     </CollectionView.ItemTemplate>
</CollectionView>

Para mostrar las dos columnas, utilizamos la propiedad ItemsLayout con GridItemsLayout utilizando la propiedad Span para indicar el número de columnas deseadas.

El resultado:

Grid de contenido relacionado

Sencillo, ¿verdad?. La llegada de BindableLayouts y de CollectionView nos permite conseguir resultados que hasta ahora requerían la creación de Custom Controls o Custom Renderers.

Transiciones entre páginas

Llegamos al “plato fuerte” del ejemplo, las transiciones entre páginas. Vamos a utilizar una versión modificada (al momento de escribir este artículo quedan algunas Pull Request pendientea por mergear, aunque los cambios de este ejemplo acabarán estando probablemente en la librería) de Xamarin.Plugin.SharedTransitions.

La idea de la librería es:

  • Custom Renderer de NavigationPage donde permitir las transiciones tradicionales (animación de entrada y salida de una página).
  • Effects que poder aplicar a elementos de la UI para permitir aplicar transiciones de elementos compartidos.

En cualquier página (ContentPage), podemos indicar la transición a utilizar de forma sencilla utilizando el método SetBackgroundAnimation:

SharedTransitionNavigationPage.SetBackgroundAnimation(this, BackgroundAnimation.SlideFromLeft);
SharedTransitionNavigationPage.SetSharedTransitionDuration(this, 500);

Entre las opciones disponibles:

  • Fade
  • Flip
  • SlideFromLeft
  • SlideFromRight
  • SlideFromTop
  • SlideFromBottom

¿Y las transiciones de elementos conectados?

Vamos a ver como utilizarlas. Comenzando añadiendo el namespace XAML necesario:

xmlns:sharedTransitions="clr-namespace:Plugin.SharedTransitions;assembly=Plugin.SharedTransitions"

En casos básicos, por ejemplo, conectar dos elementos individuales, por ejemplo un botón en dos páginas diferentes, bastará con utilizar la propiedad Tag disponible en la clase Transition.

En caso de querer hacer transiciones entre elementos de una colección como es nuestro caso (imagen correspondiente a una plantilla usada en un Bindable Layout), necesitamos utilizar además de Tag, la propiedad TagGroup.

sharedTransitions:Transition.TagGroup="1"
sharedTransitions:Transition.Tag="{Binding Number}"

NOTA: Cada elemento debe tener un Tag único.

En la página de destino, volvemos a aplicar el mismo Tag utilizado en la página anterior.

sharedTransitions:Transition.Tag="{Binding ArtItem.Number}"

NOTA: No es necesario utilizar TagGroup en la página de destino.

¿Limitaciones?

  • De momento, entre las transiciones tradicionales soportadas se incluyen las opciones vistas previamente. Proximamente espero añadir alguna opción más (Scale, etc.).
  • Las transiciones de elementos compartidos funcionan con: Label, Image, Button. Próximamente se añadirá soporte a más elementos.
  • Funciona utilizando una NavigationPage. No tiene integración con Shell por ahora.

Animaciones

Llegamos al detalle final del ejemplo. Aunque al navegar a la página de detalles la transición realizada con la imagen que se situará como cabecera conseguirá ya un efecto de fluidez y continuidad elevado, también contamos con una animación del resto del contenido.

Xamarin.Forms cuenta con una API de animaciones completa y sencilla de utilizar. Sin embargo, vamos a conseguir el efecto buscado de forma aún más sencilla directamente desde XAML utilizando Xamanimation.

Para utilizar la librería, comenzamos añadiendo el namespace en la página de detalles:

xmlns:xamanimation="clr-namespace:Xamanimation;assembly=Xamanimation"

A continuación, vamos a crear un Storyboard:

<xamanimation:StoryBoard
     x:Key="ArtItemContentAnimation"
     Target="{x:Reference ArtItemContent}">
     <xamanimation:TranslateToAnimation TranslateY="0" Duration="300"/>
     <xamanimation:FadeInAnimation />
</xamanimation:StoryBoard>

El Storyboard nos permite realizar una animación más compleja, compuesta por otras animaciones. Vamos a hacer una animación de translación hacia arriba además de hacer animar la opacidad del contenido (de 0 a 1).

¿Y cómo se lanza la animación?

Utilizamos un Trigger, para lanzar la animación en el evento Appearing de la página:

<ContentPage.Triggers>
     <EventTrigger Event="Appearing">
          <xamanimation:BeginAnimation 
               Animation="{StaticResource ArtItemContentAnimation}" />
     </EventTrigger>
</ContentPage.Triggers>

El resultado final:

El resultado

¿Qué te parece?

En cuanto al ejemplo, esta disponible en GitHub:

Ver GitHub

Llegamos hasta aquí. Estamos ante un UI Challenge donde el mayor punto de interés recae en las transiciones. Espero que te haya resultado interesante. Pronto más y mejor. Recuerda, cualquier comentario es bienvenida en el artículo!.

Más información