Xamarin Forms - Usando o RefreshView
 Neste artigo veremos como usar o RefreshView para implementar o PullToRefresh no Xamarin Forms.

O RefreshView é um novo controle incluído na versão 4.3 do Xamarin Forms que permite adicionar o PullToRefresh (puxe para atualizar) em qualquer componente de tela rolável como ListView, CollectionView e ScrollView.

O container RefreshView define as seguintes propriedades :

  1. Command - do tipo ICommand - É executado quando um refresh é disparado;
  2. CommandParameter - do tipo object - É o parametro que é passado para o Command;
  3. IsRefreshing, do tipo bool - Indica o estado atual do RefreshView;
  4. RefreshColor, do tipo Color -  Indica a cor do circulo progressivo que aparece durante o refresh;

Sendo que todas essas propriedades são apoidas por objetos BindableProperty oque significa que elas podem ser usadas com o databinding e com estilos.

Vejamos a seguir um exemplo prático mostrando o recurso funcionando.

recursos usados:

Criando o projeto Xamarin Forms

Vamos criar um projeto Xamarin Forms usando o template Blank chamado XF_RefreshView1;

Você pode ver como criar um projeto no Xamarin Forms neste link: Criar Projeto Xamarin Forms

Vamos começar criando a classe Item que representa um item com nome e cor que iremos exibir no FlexLayout.

    public class Item
    {
        public string Name { get; set; }
        public Color Color { get; set; }
    }

Com o projeto criado inclua uma pasta chamada ViewModels no projeto e nesta pasta crie a classe MainPageViewModel com o código abaixo:

using System;
using System.Collections.ObjectModel;
using System.ComponentModel;
using System.Runtime.CompilerServices;
using System.Threading.Tasks;
using System.Windows.Input;
using Xamarin.Forms;
namespace XF_RefreshView1.ViewModels
{
    public class MainPageViewModel : INotifyPropertyChanged
    {
        const int RefreshDuration = 2;
        int itemNumber = 1;
        readonly Random random;
        bool isRefreshing;
        public bool IsRefreshing
        {
            get { return isRefreshing; }
            set
            {
                isRefreshing = value;
                OnPropertyChanged();
            }
        }
        public ObservableCollection<Item> Items { get; private set; }
        public ICommand RefreshCommand => new Command(async () => await RefreshItemsAsync());
        public MainPageViewModel()
        {
            random = new Random();
            Items = new ObservableCollection<Item>();
            AddItems();
        }
        void AddItems()
        {
            for (int i = 0; i < 50; i++)
            {
                Items.Add(new Item
                {
                    Color = Color.FromRgb(random.Next(0, 255), random.Next(0, 255), random.Next(0, 255)),
                    Name = $"Item {itemNumber++}"
                });
            }
        }
        async Task RefreshItemsAsync()
        {
            IsRefreshing = true;
            await Task.Delay(TimeSpan.FromSeconds(RefreshDuration));
            AddItems();
            IsRefreshing = false;
        }
        public event PropertyChangedEventHandler PropertyChanged;
        void OnPropertyChanged([CallerMemberName] string propertyName = null)
        {
            PropertyChanged?.Invoke(this, new PropertyChangedEventArgs(propertyName));
        }
    }
}

Neste código implementamos a interface INotifyPropertyCHanged e definimos as propriedades IsRefreshing e Items que é uma coleção ObservableCollection de item.

Também definimos o comando que vai executar o método RefreshItemsAsync() :

public ICommand RefreshCommand => new Command(async () => await RefreshItemsAsync());

No arquivo MainPage.xaml altere o código conforme abaixo:

<?xml version="1.0" encoding="utf-8" ?>
<ContentPage xmlns="http://xamarin.com/schemas/2014/forms"
             xmlns:x="http://schemas.microsoft.com/winfx/2009/xaml"
             xmlns:d="http://xamarin.com/schemas/2014/forms/design"
             xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" 
             xmlns:local="clr-namespace:XF_RefreshView1.ViewModels"
             mc:Ignorable="d"
             x:Class="XF_RefreshView1.MainPage">
    <ContentPage.Resources>
        <DataTemplate x:Key="ColorItemTemplate">
            <Grid Margin="5" HeightRequest="120" WidthRequest="105">
                <BoxView Color="{Binding Color}" />
                <Label Text="{Binding Name}" HorizontalOptions="Center"
                       VerticalOptions="Center" />
            </Grid>
        </DataTemplate>
    </ContentPage.Resources>    
    <StackLayout Margin="10,35,10,10">
        <Label Text="RefreshView Demo"
               FontAttributes="Bold"
               HorizontalOptions="Center" />
        <Label Text="Puxe os itens para baixo para atualizar o ScrollView." />
        <Label Text="{Binding Items.Count, StringFormat='Número de Itens: {0}'}" />

        <RefreshView IsRefreshing="{Binding IsRefreshing}"
                     RefreshColor="Teal"
                     Command="{Binding RefreshCommand}">
            <ScrollView>
                <FlexLayout Direction="Row"
                            Wrap="Wrap"
                            AlignItems="Center"
                            AlignContent="Center"
                            BindableLayout.ItemsSource="{Binding Items}"
                            BindableLayout.ItemTemplate="{StaticResource ColorItemTemplate}" />
            </ScrollView>
        </RefreshView>
    </StackLayout>
</ContentPage>

Neste código o RefreshView fornece a funcionalidade pull para atualizar para um ScrollView cujo filho é um FlexLayout. O FlexLayout usa um layout vinculável para gerar seu conteúdo vinculando a uma coleção de itens e define a aparência de cada item com um DataTemplate.

O valor da propriedade
RefreshView.IsRefreshing indica o estado atual do RefreshView. Quando uma atualização é acionada pelo usuário, essa propriedade muda automaticamente para true. Depois que a atualização for concluída, você deve redefinir a propriedade para false.

Quando o usuário inicia uma atualização, o
ICommand definido pela propriedade Command é executado, o que deve atualizar os itens que estão sendo exibidos. Uma visualização de atualização é mostrada enquanto a atualização ocorre, que consiste em um círculo de progresso animado.

No arquivo MainPage.xaml.cs definimos a vinculação com o modelo:

using System.ComponentModel;
using Xamarin.Forms;
using XF_RefreshView1.ViewModels;

namespace XF_RefreshView1
{
    [DesignTimeVisible(false)]
    public partial class MainPage : ContentPage
    {
        public MainPage()
        {
            InitializeComponent();
         
  this.BindingContext = new MainPageViewModel();
        }
    }
}

Executando o projeto teremos o resultado abaixo:

Pegue o código do projeto compartilhado aqui :  XF_RefreshView1.zip

"Sede unânimes entre vós; não ambicioneis coisas altas, mas acomodai-vos às humildes; não sejais sábios em vós mesmos;"
Romanos 12:16

Referências:


José Carlos Macoratti