fragmentos

34
Aula 03 (Android Basico)

Upload: natanael-fonseca

Post on 11-Jun-2015

3.782 views

Category:

Technology


0 download

TRANSCRIPT

Page 1: Fragmentos

Aula 03(Android Basico)

Page 2: Fragmentos

Fragments

Natanael FonsecaArquiteto de Software

Site Pessoal: www.natanaelfonseca.com.br

Page 3: Fragmentos

Ementa O que é um fragmento ? Qual versão surgiu ? Suporte em plataformas anteriores ao HoneyComb. Classes de suporte; Baixando o pacote de compatibilidade; Ciclo de Vida de um Fragment; Tipos de Uso(Dinâmico ou Estático); Manipulando mudanças em Runtime; Comunicação com à Atividade; Inicialização Avançada; Algumas SubClasses de Fragment;

Page 4: Fragmentos

O que é um fragmento ?• É uma classe que implementa uma porção de uma activity.• Representa uma operação em particular ou interface rodando dentro de

uma Activity maior.• Permite um design de activities mais modular, fazendo com que uma

aplicação se adapte facilmente a diferentes orientações e resoluções.• Fragments devem ser embutidos em activities, ou seja, eles não podem

rodar sem estarem associados a uma activity.• É comum definir fragments que definam seus proprios layouts, e estes

vivem dentro da hierarquiva de view da propria activity.• È possivel ter um fragment sem UI.• Possui seu proprio ciclo de vida e muito proximo do ciclo de vida da

activity que a contém.• Mais importate, você pode adicionar e remover fragments

dinamicamente.

Page 5: Fragmentos

Qual versão surgiu ?

Foram implementados no android Honeycomb, API 11. As principais classes relacionadas são:

android.app.Fragment - Classe base para definição de fragments. android.app.FragmentManager - Classe para iteragir com

fragments dentro de uma activity. android.app.FragmentTransaction - Classe para suportar um

conjunto de operações atômicas com fragments, por exemplo : adicionar, remover e substituir.

Page 6: Fragmentos

Suporte para versões antigas O Google provê um pacote de compatibilidade que permite com

que aplicações que utilizem fragments rodem perfeitamente em smartphones com android anterior ao HoneyComb.

Este pacote pode ser utilizado no android 1.6 (API 4) ou anteriores.

Se você escrever sua aplicação utilizando o pacote de suporte, você estara forçando com que o android sempre utilize essas classes mesmo em plataformas mais novas(Jelly Bean, por exemplo), ou seja, o android não irá forçar carregamento da implementação nativa.

Page 7: Fragmentos

Classes de suporteSão essas as classes relacionadas ao pacote de suporte :

android.support.v4.app.FragmentActivity – Classe base para todas as activities que desejem utilizar o pacote de suporte.

android.support.v4.app.Fragment – Classe base para definição de fragments

android.support.v4.app.FragmentManager - Classe para iteragir com fragments dentro de activities.

android.support.v4.app.FragmentTransaction – Classe para realizar operações atômicas nos fragments, tais como: inclusão, remoção e substituição.

Obs: Para usar o pacote de compatibilidade na hora de criar a activity, você deve extender de “android.support.v4.app.FragmentActivity” ao invés de android.app.Activity ou uma de suas subclasses.

Page 8: Fragmentos

Baixando o pacote de compatibilidade

Basta baixar o componente “Android Compatibility Package” utilizando o Android SDK.

Page 9: Fragmentos

Usando o pacote de compatibilidade

Para usar o pacote de compatibilidade, você deve adicionar ele para o buildpath do seu projeto..

Ache a opção ao lado no ADT;

Page 10: Fragmentos

Ciclo de vida de um Fragment

Assim como uma Activity, um fragment é um exemplo de padrão de projeto : “Template Method”;

O Ciclo de vida da atividade na qual o fragmento vive afeta diretamente o ciclo de vida do fragment;

Cada callback do ciclo de vida da activity resulta em um callback para o ciclo de vida do fragment.

Por exemplo, quando a activity recebe onPause(), cada fragmento da activity reccebe onPause().

Page 11: Fragmentos

Os Fragments possuem um ciclo de vida a par que trabalha em conjunto com o ciclo de vida da activity que o contem.

• onAttach(Activity) – Chamado quando o fragmento tem sido adicionado a Activity.• onCreateView(LayoutInflater, ViewGroup, Bundle) – Chamado para criar a View

associada ao Fragmento.• onActivityCreated(Bundle) – Chamado quando o método onCreate() da activity

retornou.• onDestroyView() - chamado quando a hieraquia de view associada ao fragmento

tem sido removida.• onDetach() - Chamado quando o fragmento tem sido dessaciado da Activity.

Obs: Quando sobrescrevendo esses CallBack de ciclo de vida(Com excessão de onCreateView()) você deve chamar através da implementação da superclasse do método. Caso contrário uma exception é lançada em runtime.

Ciclo de vida de um Fragment

Page 12: Fragmentos

Criando um Fragmento Cada fragmento deve herdar da classe “Fragment”; Muito dos métodos da classe Fragment são analogos aos

encontrados na classe Activity.

• onCreate(Bundle) – Inicializa recursos utilizados pelo fragment, exteto os que são relacionados a interface do usuário.

• onCreateView(LayoutInflater, ViewGroup, Bundle) – Cria e retorna uma hierarquia de View associada com o fragmento.

• onResume() - Aloca “expensive” recursos (Em termos de tempo de bateria, custo monetario e etc.), Tal como um receiver para “location updates”, “sensor updates” e etc.

• onPause()Release “expensive” resources. Commit any changes that should be persisted beyond the current user session.

Page 13: Fragmentos

Adicionando o Fragmento na Activity

• Existem duas maneiras de adicionar um fragmento a uma activity, são eles :

– Estaticamente, atraves do uso da tag <fragment> diretamente no layout;

– Dinamicamente, Adicionando-o a algum ViewGroup existente através de Transações.

Page 14: Fragmentos

Incluindo um Fragmento Estaticamente

Modo mais simples de inclusão de um fragmento da Activity; Isto funciona bem se o fragmento deveria estar presente no layout; Entretanto, esta abordagem não permite que você remova dinamicamente o

fragmento em runtime; No arquivo de layout da activity simplesmente utilize a tag <fragment>/ Use android:name para prover o nome totalmente qualificado da classe de

fragmento; Cada fragmento requer um identificador único que o sistema pode usar para

restaurar o fragmento se a activity for reiniciada. Existem três modos de prover um ID para o fragmento:

Através do atributo android:id com um id único; Fornecendo o atributo android:tag com uma String única; Se não prover nenhum dos atributos acima. O sistema usa o ID do fragment’s

container view.

Page 15: Fragmentos

Incluindo um Fragmento dinamicamente

FragmentManager fragmentManager = getFragmentManager()// Or: FragmentManager fragmentManager = getSupportFragmentManager()FragmentTransaction fragmentTransaction = fragmentManager.beginTransaction(); ExampleFragment fragment = new ExampleFragment(); fragmentTransaction.add(R.id.fragment_container, fragment); fragmentTransaction.commit();

Em qualquer momento durante o funcionamento da activity, você pode incluir um fragmento.1.Primeiro, use Activity.getFragmentManager() para pegar uma referencia a FragmentManager;2.Invoque FragmentManager.beginTransaction() para pegar uma instancia de FragmentTransaction;3.Instancie uma instancia de fragment;4.Use o método FragmentTransaction.add() para adicionar o fragmento ao ViewGroup da activity, especificado por um ID. Opcionalmente, você também pode fornecer uma String, “tag” para identificar o fragmento;5.Commitar a transação usando FragmentTransaction.commit();

Page 16: Fragmentos

Incluindo um Fragmento Estaticamente

<?xml version="1.0" encoding="utf-8"?><LinearLayout xmlns:android="http://schemas.android.com/apk/res/android" android:orientation="horizontal" android:layout_width="match_parent" android:layout_height="match_parent">

<fragment android:name="com.example.news.ArticleListFragment" android:id="@+id/list“ android:layout_weight="1“ android:layout_width="0dp“ android:layout_height="match_parent" />

<fragment android:name="com.example.news.ArticleReaderFragment" android:id="@+id/viewer“

android:layout_weight="2" android:layout_width="0dp“ android:layout_height="match_parent" />

</LinearLayout>

Page 17: Fragmentos

Exemplo

Activity

Exemplo: Aula03_HelloFragments.zip

Fragmento A

Fragmento B

Exemplo simples que demonstraA utilização de fragmentos paracriar uma com duas formas de formulário.

Page 18: Fragmentos

Manipulando mudanças de configuração em Runtime

Quando o sistema destroi e recria a atividade por causa de uma mudança de configuração, a atividade automaticamente reinstancia fragmentos existentes.

• Isto não é um problema para “static” fragments declarados no layout da activity.

• Mas para “dynamic” fragments, você precisará testar para saber se isto está acontecendo e previnir a criação de uma segunda instancia do fragmento.

Para testar se o sistema esta recriando à activity, basta checar se o bundle passado como argumento para o método onCreate() é null.

• Se ele não é nulo entao o sistema está recriando a activity, neste caso, a atividade automaticamente irá reinstanciar os fragmentos existentes.

• Se é null você pode seguramente instanciar seu fragmento.

Exemplo a seguir !

Page 19: Fragmentos

ExemploLogo abaixo, um exemplo de manipulação de mudança de configuração em runtime, nesse caso, evitando a reinstanciação do mesmo fragment.

public void onCreate(Bundle savedInstanceState) { // ... if (savedInstanceState == null) { FragmentManager fragmentManager = getFragmentManager() // Ou: FragmentManager fragmentManager = getSupportFragmentManager() FragmentTransaction fragmentTransaction = fragmentManager.beginTransaction(); ExampleFragment fragment = new ExampleFragment(); fragmentTransaction.add(R.id.fragment_container, fragment); fragmentTransaction.commit(); }}

Page 20: Fragmentos

Salvando o Estado de Um Fragmento

A classe Fragment suporta o método onSaveInstanceState do mesmo modo que a classe Activity, mas em contra partida a classe Fragment não suporta o método onRestoreInstanceState

• A implementação padrão salva o estado de todos os fragmentos que possuem ID;

• Você pode sobrescrever este método para gravar alguma informação adicional relacionada ao estado do fragmento.

• Se o sistema esta recriando o fragmento de um estado prévio, ele provê uma referencia para o Bundle(Contento o estado) passado para os métodos onCreate(), onCreateView() e on ActivityCreated();

Page 21: Fragmentos

Mantendo fragmentos através da recriação da Activity

• Quando uma activity é recriada os fragmentos também são recriados.

• Chame o método Fragment.setRetainInstance(boolean) com o valor true para solicitar ao sistema que mantenha a instancia atual caso a atividade seja recriada.

• Se invocado, quando a atividade é recriada, os métodos do gragmento: onDestroy() e onCreate() não são invocados.

• Todos os outros métodos do ciclo de vida do fragmento são invocados em sua sequencia típica.

Se você usar setRetainInstance(true), então o bundle que é passado como argumento para os métodos onCreateView() e onActivityCreated() será sempre nulo, afinal o fragmento não será recriado.

Page 22: Fragmentos

Mantendo fragmentos através da recriação da Atividade

• “Retained fragments ” podem ser muito uteis para propragação de informações de estado, especialmente “thread management”.

• Por exemplo, um fragmento pode servir como “host” para uma instancia de Thread ou AsyncTask, gerenciando a operação.

• O método Activity.onRetainNonConfigurationInstance(), o qual tradicionalmente tem sido criado para este proposito, está depreciado a partir da API 11 em troca das capacidades do método setRetainInstance() do fragment.

Se você está usando a biblioteca de compatibilidade, a classe FragmentActivity sobrescreve o método onRetainNonConfigurationInstance() fazendo ele “final” para implementar as capacidades de retenção.

Page 23: Fragmentos

Usando fragmentos sem Layouts

• Não é obrigatório que um fragmento possua UI.• Por exemplo, se o fragmento foi criado apenas para coordenar uma thread !• Quando o fragmento não possui UI, não é necessário sobrescrever o

método onCreateView().• Você deve adicionar o fragmento para à atividade usando

FragmentTransaction.add(Fragment, String), provendo uma tag String única para identificar o fragmento.

Ex(Activity Code) :

FragmentManager fragmentManager = getFragmentManager() // Or: FragmentManager fragmentManager = getSupportFragmentManager() FragmentTransaction fragmentTransaction = fragmentManager.beginTransaction();BackgroundFragment fragment = new BackgroundFragment(); fragmentTransaction.add(fragment, "thread_manager");fragmentTransaction.commit();

Page 24: Fragmentos

Procurando fragmentos

• A classe FragmentManager tem metodos para encontrar fragmentos contidos dentro de uma atividade, são eles:– findFragmentById(int id) encontra o fragmento com o

ID especificado.– findFragmentByTag(String tag) encontra o fragmento

com a tag especificada.• Ambos destes métodos retornam uma referencia

para o fragmento ou null se nenhum fragmento é encontrado.

Page 25: Fragmentos

Operações com Fragmentos Você pode executar muitas outras operações com fragmentos dinamicos, tais como:

adicionar, remover e mudar a visibilidade. Cada conjunto de mudanças que você comita é chamada de transação. Para realizar operações com Fragmentos você utiliza a classe FragmentTransaction,

esta possui os seguintes métodos :– add() : Adiciona um fragmento a atividade.– remove(): Remove o fragmento da atividade. Esta operação destroy a instancia do fragmento

ao menos que a transação seja adicionada ao “transaction back stack”.– replace(): Remove o fragmento da UI e substitui ele por outro.– hide(): Esconde o fragmento da UI (Sem destrui a hierarquia de Views).– show(): Mostra um fragmento previamente escondido.– detach() (API 13) Desanexa o fragmento da UI, destruindo a hieraquia de View, mas mantendo

a instancia do fragmento.– attach() (API 13) Reanexa o fragmento que tenha sido previamente desanexado, recriando a

hierarquia de view.

Você não pode remover, substituir, desanexar ou anexar um fragmento declarado no layout da activity(Static Fragments).

Page 26: Fragmentos

Executando transações de Fragmento

Para executar uma transação com fragmentos, você deve :

Obter uma instancia de FragmentTransaction chamando FragmentManager.beginTransaction().

Executar qualquer numero de operações usando a instancia da transação. A maioria das operações com FragmentTransaction retorna uma

referencia para a mesma FragmentTransaction , permitindo encadeamento de método.

Chamar commit() para aplicar a transação na atividade. Você pode comitar uma transação utilizando commit() somente antes da activity salvar seu estado (antes do sistema invocar Activity.onSaveInstanceState()). Se você tentar executar depois desse ponto, uma exceção será lançada.

Page 27: Fragmentos

Gerenciando o “Fragment Back Stack”• Similar ao conceito de “Back Stack” para Atividades, você tem a opção de salvar as operações de

fragmentos em uma “Back Stack” gerido pela Atividade;• Se você adicionar as operações de transação para a “Back Stack”, então o usuário pode navegar

para trás atraves das mudanças realizadas pelas transações apenas presionando o “Back Button”;• Se todos os fragmentos tiverem sido removidos da “Back Stack” ao pressionar o “Back Button”,

isso irá destruir a atividade.• Para adicionar uma transação para a “Back Stack”, basta

chamar FragmentTransaction.addToBackStack(String) antes de comitar a transação.• O argumento string é opcional e serve para identificar o estado da “Back Stack”. A classe

FragmentManager tem um método chamado popBackStack(), qual pode retornar para um previo estado da “Back Stack” com um dado nome.

• Se você adicionar multiplas mudanças para a transação e chamar addToBackStack(), então todas as mudanças aplicadas antes de você chamar commit() são adicionadas a back stack como uma única transação e o “BackButton” irá reverte-las todas juntas.

• Se você chamar addToBackStack() quando removendo e substituindo um fragmento:– O sistema invoca onPause(), onStop(), e onDestroyView() no fragmento quando ele é colocado no “back

stack”.– Se o usuário navegar de volta, o sistema invoca onCreateView(), onActivityCreated(),onStart(),

e onResume() no fragmento.

Page 28: Fragmentos

Comunicando um Fragmento e uma Atividade

Na comunicação entre Atividade e Fragmento, podemos: – Chamar métodos publicos do fragmento de dentro de uma

atividade;– Encontrar fragmentos associados à Atividade usando

FragmentManager com os métodos: findFragmentById() ou findFragmentByTag().

– Obter a referencia para à Atividade chamando Fragment.getActivity;

Page 29: Fragmentos

Inicialização Avançada de Fragmentos

• È possivel utilizar o método setArguments(Bundle) passando um bundle com os argumentos.

• Dentro do fragmento basta invocar o método getArguments().

Na activity :

No fragment :

Page 30: Fragmentos

Criando Dialogos usando Fragmento

• A partir do Honeycomb (API 11), the Activity class’s “managed dialog” methods are deprecated in favor of fragments.

• A classe DialogFragment serve como base para um dialogo baseado em fragments;

• Esta classe contem um objeto dialogo que é exibido de acordo com seu estado;

• Você deveria controlar o dialogo usando os métodos fornecidos pela classe fragment;

• Se você planeja usar o fragmento somente como um dialogo, sobrescreva o método onCreateDialog() e retorne uma instancia de Dialog ou uma de suas subclasses.

• Se você quer usar o fragment as ou como um dialogo ou como um fragmento normal, sobrescreva o método onCreateView() e retorna a hierarquia de view.

Page 31: Fragmentos

Exemplo

No Exemplo abaixo podemos observar as práticas:

Uso de interface para comunicação com Activity;Uso do método show() de Fragment Manager;Uso das classes de suporte para exibição do Dialogo;

Exemplo: Aula03_SimpleDialogFragment.zip

Page 32: Fragmentos

MasterDetail com ADT

Um exemplo bem interessante e que é um forte candidato a estudo datecnologia de fragments é o exemplo Fornecido pelo próprio ADT.

• Aula03_MasterDetailFragment.zip

Page 33: Fragmentos

Algumas subclasses de Fragment

Existem algumas subclasses de e Fragment projetadas para usos comuns em aplicações Android:• ListFragment – Um fragmento que

automaticamente gerencia um ListView. Analogo a classe ListActivity.

• WebFragment – Um fragmento que cria e gerencia um WebView.

Page 34: Fragmentos

Referencias

Professional Android 4 Application Development, Wei-Meng Lee, Wiley 2011. Android Training : http://developer.android.com/training/index.html.