Zoom tradicional y Zoom Semántico | XAML | WinRT

Intermedio

Tradicionalmente las herramientas de desarrollo de UI modernas han incorporado controles para hacer Zoom, los cuales permiten agrandar el tamaño de la información mostrada sean imágenes o texto.

Megaman Zoom

El zoom tradicionalmente tiene el problema de ocasionar que las imágenes y demás componentes como controles y texto se pixelen

Texto pixelado

XAML desde siempre ha incorporado funcionalidades para hacer zoom, la mas destacada de ellas es el ViewBox, este control hace zoom a todos los controles que contiene, WinRT ha incorporado el SemanticZoom , el cual permite hacer Zoom no sobre imagenes, pixeles o vectores,sino sobre el conjunto de datos.

ViewBox

Viewbox y XAML tienen una importante ventaja, las fuentes y todas las formas de los controles estan basadas en vectores no en mapas de bits, por ende cada vez que se usa ViewBox sobre este tipo de elementos no se genera el efecto de 'pixeleo'.

Texto no pixelado

Este ejemplo de XAML nos muestra como usar el ViewBox.

Acá tenemos un CheckBox con su label en tamaño normal, y debajo un CheckBox con su label en tamaño 100. Lo primero que notamos es que solo el texto cambia el tamaño, porque en efecto se ha establecido su propiedad FontSize en tamaño 100:

 <StackPanel >
    <CheckBox Content="Texto"/>
    <CheckBox Content="Texto" FontSize="100" />
</StackPanel>

Checkbox normal y otro con fuente tamaño 100

El efecto no es el deseado, crece solo el label pero el cuadro del CheckBox se mantiene igual.

Sin embargo si queremos obtener un mejor resultado podemos utilizar el ViewBox:

 <StackPanel >
    <CheckBox Content="Texto" />
    <Viewbox Width="400" HorizontalAlignment="Left">
        <CheckBox Content="Texto" IsChecked="True" />
    </Viewbox>
</StackPanel>

ViewBox effect

SemanticZoom

Otra forma de hacer zoom es utilizando SemanticZoom, pero este control no hace zoom a nivel gráfico sobre los elementos, es más un artilugio visual para detallar más los datos que se muestran.

En este ejemplo vemos una lista de objetos de un feed RSS:

 <GridView ItemsSource="{Binding Source={StaticResource BlogRssConsumer},Path=FeedSource}"
        SelectionMode="None">
    <ItemsControl.ItemTemplate>
        <DataTemplate>
            <Border Width="250" Height="250" Background="DarkSlateBlue">
                <StackPanel>
                    <Image Source="{Binding ImageUrl}" HorizontalAlignment="Stretch" MaxHeight="125"
                            MinHeight="125" Stretch="UniformToFill" />
                    <TextBlock Text="{Binding Titulo}" FontSize="20" TextWrapping="Wrap" />
                    <TextBlock Text="{Binding Autor}" FontSize="15" />
                </StackPanel>
            </Border>
        </DataTemplate>
    </ItemsControl.ItemTemplate>
</GridView>

Este es el resultado

GridView

SemanticZoom permite dos niveles de Zoom

  • ZoomedInView
  • ZoomedOutView

Sus nombres son bastante dicientes ,ZoomedOutView es algo como la vista normal y el ZoomedInView es la vista Aumentada.

La filosofía de SemanticZoom es que al hacer Zoom sobre los datos, estos se despliegan con mayor detalle.

Para darle la funcionalidad de SemanticZoom debemos envolver el GridView dentro de un SemanticZoom, y dejarlo dentro de uno de los tag que se ven a continuación:

 <SemanticZoom IsZoomedInViewActive="False">
    <SemanticZoom.ZoomedOutView>
    </SemanticZoom.ZoomedOutView>
    <SemanticZoom.ZoomedInView>
    </SemanticZoom.ZoomedInView>
</SemanticZoom>

quedando así

 <SemanticZoom IsZoomedInViewActive="False">
    <SemanticZoom.ZoomedOutView>
        <GridView ItemsSource="{Binding Source={StaticResource BlogRssConsumer},Path=FeedSource}"
                SelectionMode="None">
            <ItemsControl.ItemTemplate>
                <DataTemplate>
                    <Border Width="250" Height="250" Background="DarkSlateBlue">
                        <StackPanel>
                            <Image Source="{Binding ImageUrl}" HorizontalAlignment="Stretch" MaxHeight="125"
                                    MinHeight="125" Stretch="UniformToFill" />
                            <TextBlock Text="{Binding Titulo}" FontSize="20" TextWrapping="Wrap" />
                            <TextBlock Text="{Binding Autor}" FontSize="15" />
                        </StackPanel>
                    </Border>
                </DataTemplate>
            </ItemsControl.ItemTemplate>
        </GridView>
    </SemanticZoom.ZoomedOutView>
    <SemanticZoom.ZoomedInView>
    </SemanticZoom.ZoomedInView>
</SemanticZoom>

Visualmeente no hay ningún cambio, pero si hacemos el gesto de Zoom In con los dedos nos damos cuenta que nos muestra un espacio vacio y si hacemos de nuevo el gesto de Zoom out retornamos a nuestra resentación anterior.

Gestos de Zoom In y Zoom Out

Gesto de Zoom

Ahora para terminar la funcionalidad solo basta colocar un elemento dentro del ZoomedInView, para lo cual solo realizo algunas modificaciones a la vista, muestro algunos datos de mas, cambio algunos tamaños etc.:

 <SemanticZoom.ZoomedInView>
    <GridView ItemsSource="{Binding Source={StaticResource BlogRssConsumer},Path=FeedSource}"
            SelectionMode="None">
        <ItemsControl.ItemTemplate>
            <DataTemplate>
                <Border Width="1024" VerticalAlignment="Stretch" Background="DarkSlateGray">
                    <StackPanel>
                        <TextBlock Text="{Binding Titulo}" FontSize="35" TextWrapping="Wrap" />
                        <Image Source="{Binding ImageUrl}" MaxWidth="600" MinWidth="600" MaxHeight="300"
                                MinHeight="300" Stretch="UniformToFill" />
                        <TextBlock Text="{Binding Autor}" FontSize="15" />
                        <TextBlock  HorizontalAlignment="Stretch" Text="{Binding Content}" FontSize="20"
                                TextWrapping="Wrap" Height="600" />
                    </StackPanel>
                </Border>
            </DataTemplate>
        </ItemsControl.ItemTemplate>
    </GridView>
</SemanticZoom.ZoomedInView>

De esta forma al hacer ZoomIn obtenemos esta vista:

Semantic Zoom

Este es el código XAML resultante

 <SemanticZoom Grid.Row="1" IsZoomedInViewActive="False">
    <SemanticZoom.ZoomedOutView>
        <GridView ItemsSource="{Binding Source={StaticResource BlogRssConsumer},Path=FeedSource}"
                SelectionMode="None">
            <ItemsControl.ItemTemplate>
                <DataTemplate>
                    <Border Width="250" Height="250" Background="DarkSlateBlue">
                        <StackPanel>
                            <Image Source="{Binding ImageUrl}" HorizontalAlignment="Stretch" MaxHeight="125"
                                    MinHeight="125" Stretch="UniformToFill" />
                            <TextBlock Text="{Binding Titulo}" FontSize="20" TextWrapping="Wrap" />
                            <TextBlock Text="{Binding Autor}" FontSize="15" />
                        </StackPanel>
                    </Border>
                </DataTemplate>
            </ItemsControl.ItemTemplate>
        </GridView>
    </SemanticZoom.ZoomedOutView>
    <SemanticZoom.ZoomedInView>
        <GridView ItemsSource="{Binding Source={StaticResource BlogRssConsumer},Path=FeedSource}"
                SelectionMode="None">
            <ItemsControl.ItemTemplate>
                <DataTemplate>
                    <Border Width="1024" VerticalAlignment="Stretch" Background="DarkSlateGray">
                        <StackPanel>
                            <TextBlock Text="{Binding Titulo}" FontSize="35" TextWrapping="Wrap" />
                            <Image Source="{Binding ImageUrl}" MaxWidth="600" MinWidth="600" MaxHeight="300"
                                    MinHeight="300" Stretch="UniformToFill" />
                            <TextBlock Text="{Binding Autor}" FontSize="15" />
                            <TextBlock  HorizontalAlignment="Stretch" Text="{Binding Content}" FontSize="20"
                                    TextWrapping="Wrap" Height="600" />
                        </StackPanel>
                    </Border>
                </DataTemplate>
            </ItemsControl.ItemTemplate>
        </GridView>
    </SemanticZoom.ZoomedInView>
</SemanticZoom>

Queda chevere!