No puedo envolver mi cabeza alrededor de Android Fragments

Estoy luchando para envolver mi cabeza alrededor de Fragmentos y Actividades.

Estoy escribiendo una aplicación que utiliza una barra de acción para navegar a través de "artículos de audio destacados" lista, y una lista de "programas" que contienen su propia lista de "elementos de audio". Estoy utilizando ActionBarSherlock y los paquetes de compatibilidad.

Al hacer clic en una pestaña ActionBar, debe mostrar esa actividad / fragmento. Al hacer clic en algo en una lista, debe abrir un nuevo fragmento / actividad que muestre ese elemento de programa / audio.

He mirado varias demostraciones / muestras y entiendo que hay algunas maneras de hacer esto.

Mis preguntas:

  • ¿Cuál es la estructura del programa?
    • Por ejemplo, una actividad para cada fragmento? Una actividad con muchos fragmentos?
  • ¿Cómo navegas por los fragmentos?
    • Por ejemplo Intents?
  • ¿Cómo puedo tener una ActionBar persistente en todas las actividades?

Gracias por cualquier ayuda que usted puede dar

EDIT – Respondiendo a mi propia pregunta:

Así que he ido para este enfoque:

  • Actividad principal que inicializa ActionBar, maneja la Navegación principal del fragmento.
  • Cada fragmento principal tiene un onClickListener
  • El onClickListener reemplaza al Fragmento que se muestra actualmente con uno nuevo, inicializado para mostrar el elemento correcto

Esto se basa en la demo de ActionbarSherlock FragmentLayoutSupport que menciono en los comentarios.

Fragmento del fragmento de la lista principal:

//public class ProgrammesFragment extends SherlockListFragment @Override public void onListItemClick(ListView l, View v, int position, long id) { showDetails(id); } /** * Helper function to show the details of a selected item, either by * displaying a fragment in-place in the current UI, or starting a * whole new activity in which it is displayed. */ void showDetails(long index) { // Check what fragment is currently shown, replace if needed. ProgrammeFragment details = (ProgrammeFragment) getFragmentManager().findFragmentByTag(ProgrammeFragment.TAG); if (details == null || details.getShownIndex() != index) { // Make new fragment to show this selection. details = ProgrammeFragment.newInstance(index); // Execute a transaction, replacing any existing fragment // with this one inside the frame. FragmentTransaction ft = getFragmentManager().beginTransaction(); ft.remove(getFragmentManager().findFragmentByTag(ProgrammesFragment.TAG)); ft.add(android.R.id.content, details, ProgrammeFragment.TAG); ft.addToBackStack(null); ft.commit(); } } 

Detalles Fragmento fragmento:

 //public class ProgrammeFragment extends SherlockListFragment /** * Create a new instance of ProgrammeFragment, initialized to * show the text at 'index'. */ public static ProgrammeFragment newInstance(long index) { ProgrammeFragment f = new ProgrammeFragment(); // Supply index input as an argument. Bundle args = new Bundle(); args.putLong("programme_id", index); f.setArguments(args); return f; } public long getShownIndex() { return getArguments().getLong("programme_id", 0); } 

El fragmento de detalles utiliza un LoaderManager en la parte superior de un ContentResolver de SQL y llama a getShownIndex para crear las condiciones para la consulta de selección.

Esto funciona (por ahora), no estoy seguro sobre el uso de la memoria o cualquier otro tipo de cosas. Pero ya veremos!

Parece que sí es bueno para obtener pensamientos más claros en su mente para que pueda responder a sus propias preguntas: P

En el onCreate de su actividad principal, cree y añada todas las pestañas (una pestaña = 1 clase SherlockFragment). En su actividad principal, usted tiene que tener una clase interna que es un TabAdapter. En mi ejemplo a continuación, el TabAdapter es también un ViewPager, por lo que puede deslizar en cualquier parte de la pantalla, izquierda-derecha para cambiar entre las pestañas. Aquí está la clase principal:

 import java.util.ArrayList; import library.DatabaseHandler; import library.UserFunctions; import org.json.JSONObject; import com.actionbarsherlock.R; import com.actionbarsherlock.app.ActionBar; import com.actionbarsherlock.app.ActionBar.Tab; import com.actionbarsherlock.app.SherlockFragment; import com.actionbarsherlock.app.SherlockFragmentActivity; import com.actionbarsherlock.view.Menu; import com.actionbarsherlock.view.MenuInflater; import com.actionbarsherlock.view.MenuItem; import android.app.AlertDialog; import android.app.Dialog; import android.app.ProgressDialog; import android.content.Context; import android.content.DialogInterface; import android.content.Intent; import android.content.SharedPreferences; import android.os.Bundle; import android.util.Log; import android.view.View.OnClickListener; import android.view.View; import android.widget.Button; import android.widget.CheckBox; import android.widget.EditText; import android.widget.Switch; import android.widget.TextView; import android.widget.Toast; import android.support.v4.app.Fragment; import android.support.v4.app.FragmentActivity; import android.support.v4.app.FragmentManager; import android.support.v4.app.FragmentPagerAdapter; import android.support.v4.app.FragmentTransaction; import android.support.v4.view.ViewPager; import android.support.v4.view.ViewPager.OnPageChangeListener; public class Polling extends SherlockFragmentActivity { private ViewPager mViewPager; private TabsAdapter mTabsAdapter; ActionBar bar; public void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); mViewPager = new ViewPager(this); mViewPager.setId(R.id.pager); setContentView(mViewPager); bar = getSupportActionBar(); bar.setNavigationMode(ActionBar.NAVIGATION_MODE_TABS); bar.setDisplayShowTitleEnabled(false); bar.setDisplayShowHomeEnabled(false); mTabsAdapter = new TabsAdapter(this, mViewPager); mTabsAdapter.addTab(bar.newTab().setText(R.string.login), LoginFragment.class, null); mTabsAdapter.addTab(bar.newTab().setText(R.string.economics), EconFragment.class, null); mTabsAdapter.addTab(bar.newTab().setText(R.string.elections), ElectionsFragment.class, null); mTabsAdapter.addTab(bar.newTab().setText(R.string.politics), PoliticsFragment.class, null); mTabsAdapter.addTab(bar.newTab().setText(R.string.science), ScienceFragment.class, null); mTabsAdapter.addTab(bar.newTab().setText(R.string.finance), FinanceFragment.class, null); mTabsAdapter.addTab(bar.newTab().setText(R.string.religion), ReligionFragment.class, null); mTabsAdapter.addTab(bar.newTab().setText(R.string.military), MilitaryFragment.class, null); mTabsAdapter.addTab(bar.newTab().setText(R.string.international), InternationalFragment.class, null); } public static class TabsAdapter extends FragmentPagerAdapter implements ActionBar.TabListener, ViewPager.OnPageChangeListener { private final Context mContext; private final ActionBar mActionBar; private final ViewPager mViewPager; private final ArrayList<TabInfo> mTabs = new ArrayList<TabInfo>(); static final class TabInfo { private final Class<?> clss; private final Bundle args; TabInfo(Class<?> _class, Bundle _args) { clss = _class; args = _args; } } public TabsAdapter(SherlockFragmentActivity activity, ViewPager pager) { super(activity.getSupportFragmentManager()); mContext = activity; mActionBar = activity.getSupportActionBar(); mViewPager = pager; mViewPager.setAdapter(this); mViewPager.setOnPageChangeListener(this); } public void addTab(ActionBar.Tab tab, Class<?> clss, Bundle args) { TabInfo info = new TabInfo(clss, args); tab.setTag(info); tab.setTabListener(this); mTabs.add(info); mActionBar.addTab(tab); notifyDataSetChanged(); } public int getCount() { return mTabs.size(); } public SherlockFragment getItem(int position) { TabInfo info = mTabs.get(position); return (SherlockFragment)Fragment.instantiate(mContext, info.clss.getName(), info.args); } public void onPageSelected(int position) { mActionBar.setSelectedNavigationItem(position); } public void onPageScrollStateChanged(int state) {} public void onPageScrolled(int position, float positionOffset, int positionOffsetPixels) {} public void onTabSelected(Tab tab, FragmentTransaction ft) { mViewPager.setCurrentItem(tab.getPosition()); //Log.v(TAG, "clicked"); Object tag = tab.getTag(); for (int i=0; i<mTabs.size(); i++) { if (mTabs.get(i) == tag) { mViewPager.setCurrentItem(i); } } } public void onTabUnselected(Tab tab, FragmentTransaction ft) {} public void onTabReselected(Tab tab, FragmentTransaction ft) {} public void onTabReselected(Tab tab, android.app.FragmentTransaction ft) {} public void onTabUnselected(Tab tab, android.app.FragmentTransaction ft) {} } } 

Aquí hay un fragmento sin ninguna UI principal (sólo un archivo xml con un TextView en él):

 import com.actionbarsherlock.R; import com.actionbarsherlock.app.SherlockFragment; import android.support.v4.app.Fragment; import android.os.Bundle; import android.view.LayoutInflater; import android.view.View; import android.view.ViewGroup; public class FinanceFragment extends SherlockFragment { @Override public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { return inflater.inflate(R.layout.financefragment, container, false); } } 

Otro fragmento con una interfaz de usuario temporal en onResume / onCreateView:

 import com.actionbarsherlock.R; import com.actionbarsherlock.app.SherlockFragment; import android.app.Activity; import android.app.AlertDialog; import android.content.Context; import android.content.Intent; import android.os.Bundle; import android.util.Log; import android.view.LayoutInflater; import android.view.View; import android.view.ViewGroup; import android.view.View.OnClickListener; import android.view.ViewGroup.LayoutParams; import android.view.inputmethod.InputMethodManager; import android.widget.Button; import android.widget.LinearLayout; import android.widget.RelativeLayout; import android.widget.ScrollView; import android.widget.TableLayout; import android.widget.TableRow; import android.widget.TextView; public class EconFragment extends SherlockFragment { private TableLayout questionContainer; int pos = 0; private String[] titles = {"The first title ", "hallo1","hallo2", "hallo3", "hallo4", "hallo5","hallo6", "hallo7","hallo8", "hallo9"}; public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) { Log.v("Econ", "onCreateView"); View v = inflater.inflate(R.layout.econfragment, container, false); questionContainer = (TableLayout) v.findViewById(R.id.questionContainer); //bs int leftMargin=5; int topMargin=5; int rightMargin=5; int bottomMargin=5; while (pos < 10) { View question = inflater.inflate(R.layout.question, null); question.setId(pos); TextView title = (TextView) question.findViewById(R.id.questionTextView); title.setText(titles[pos]); Button charts = (Button) question.findViewById(R.id.chartsButton); charts.setId(pos); charts.setOnClickListener(chartsListener); TableRow tr = (TableRow) question; TableLayout.LayoutParams trParams = new TableLayout.LayoutParams( TableLayout.LayoutParams.MATCH_PARENT, TableLayout.LayoutParams.WRAP_CONTENT); trParams.setMargins(leftMargin, topMargin, rightMargin, bottomMargin); tr.setLayoutParams(trParams); Log.v("econ", "while loop"); questionContainer.addView(tr); pos++; } pos = 0; return v; } public void onResume() { super.onResume(); Log.v("Econ", "onResume"); } public OnClickListener chartsListener = new OnClickListener() { @Override public void onClick(View v) { Intent chart = new Intent(); chart.setClass(getActivity(), Chart.class); chart.putExtra("key", titles[v.getId()]); Log.v("TAG", Integer.toString(v.getId())); startActivity(chart); } }; public void onAttach(Activity activity) { super.onAttach(activity); Log.d("Econ", "onAttach"); } public void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); Log.d("Econ", "onCreate"); //Log.v("ECON", savedInstanceState.toString()); } public void onActivityCreated(Bundle savedInstanceState) { super.onActivityCreated(savedInstanceState); Log.d("Econ", "onActivityCreated"); } public void onStart() { super.onStart(); Log.d("Econ", "OnStart"); } public void onPause() { super.onPause(); Log.d("Econ", "onpause"); } public void onStop() { super.onStop(); Log.d("Econ", "onstop"); } public void onDestroyView() { super.onDestroyView(); Log.d("Econ", "ondestroyview"); } public void onDestroy() { super.onDestroy(); Log.d("Econ", "ondestroy"); } public void onDetach() { super.onDetach(); Log.d("Econ", "ondetach"); } } 

EDIT ~ No he documentado mi código todavía – algunos de ellos son sólo de los ejemplos que encontré en línea de todos modos. Si hay algún inconveniente o cosas que no entiendas, solo pregunta.

  • Uso del menú Opciones en una actividad de varios fragmentos
  • Dilema: cuándo utilizar Fragmentos vs Actividades:
  • FindViewById en Fragmento
  • Fragmentos, setRetainInstance (true) y bibliotecas enhebradas
  • Pasar datos de búsqueda a la actividad de búsqueda
  • Cómo abrir fragmento de RecyclerView.Adapter <CardAdapter.ViewHolder>
  • DialogFragment.show cuelga la aplicación
  • ArrayAdapter en Fragmento - Android
  • Android Fragment onAttach () desaprobado
  • Problemas de memoria - fragmentos
  • GetResources de FragmentStatePagerAdapter
  • FlipAndroid es un fan de Google para Android, Todo sobre Android Phones, Android Wear, Android Dev y Aplicaciones para Android Aplicaciones.