studio - onstart android fragment
¿Por qué se llama a onCreateView, onCreate, onActivityCreated del fragmento? (3)
Tengo una aplicación que trata con fragmentos y ViewPager. Tengo tres fragmentos en una ViewPager. Cuando cambias entre ellos, siempre hace que los otros dos fragmentos llamen a los de ellos en los métodos de Crear vista. ¿Cómo hacerlo solo una vez, solo cuando se crea FragmentActivity ??? He leído algunas preguntas y he intentado con las soluciones, pero los fragmentos siguen teniendo el mismo comportamiento.
ListFragment onCreate llamado dos veces
onCreate () y onCreateView () invocan mucho más de lo necesario (Fragmentos)
Aquí hay un código, si te ayuda, muchachos:
Actividad principal:
public class StartingActivity extends FragmentActivity implements View.OnClickListener {
ViewPager viewPager;
CirclePageIndicator pageIndicator;
Button discount;
Button qrCode;
Button pay;
TabHost tabHost;
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
setContentView(R.layout.starting_layout);
viewPager = (ViewPager) findViewById(R.id.pager);
if (savedInstanceState == null) {
Fragment firstPage = Fragment.instantiate(this, FindTovarFragment.class.getName());
Fragment secondPage = Fragment.instantiate(this, MainWindowActivity.class.getName());
Fragment thirdPage = Fragment.instantiate(this, MapActivity.class.getName());
if ((firstPage != null && !firstPage.isDetached())|| (secondPage != null && !secondPage.isDetached()) || (thirdPage != null && !thirdPage.isDetached())) {
List<Fragment> viewPagerFragments = new ArrayList<Fragment>();
viewPagerFragments.add(firstPage);
viewPagerFragments.add(secondPage);
viewPagerFragments.add(thirdPage);
PageAdapter pageAdapter = new PageAdapter(getSupportFragmentManager(), viewPagerFragments);
viewPager.setAdapter(pageAdapter);
pageIndicator = (CirclePageIndicator) findViewById(R.id.circle);
pageIndicator.setViewPager(viewPager);
pageIndicator.setCurrentItem(pageAdapter.getCount() - 2);
}
}
}
MapActivity:
public class MapActivity extends Fragment implements OnMyLocationListener {
//Тэг для логов
private static final String TAG = "MapActivity";
List<Address> addressList;
private static final String STRING_LOCATION = "";
ArrayList<TorgCentr> randomTorgCentr;
ArrayList<String> torgCentrNames;
Context context;
AutoCompleteTextView searchTorgCentr;
OverlayManager overlayManager;
MapController mapController;
TextView textView;
double longitude;
double latitude;
double itemLongitude;
double itemLatitude;
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
Log.d(TAG, "MapActivity onCreateView");
View view = (LinearLayout) inflater.inflate(R.layout.map_layout, container, false);
final MapView mapView = (MapView) view.findViewById(R.id.map);
textView = (TextView) view.findViewById(R.id.searchlocation);
searchTorgCentr = (AutoCompleteTextView) view.findViewById(R.id.autoCompleteTextView);
mapView.showBuiltInScreenButtons(true);
mapController = mapView.getMapController();
context = getActivity();
return view;
}
@Override
public void onResume() {
super.onResume();
}
@Override
public void onCreate(Bundle savedInstanceState) {
super.onCreate(savedInstanceState);
Log.d(TAG, "MapActivity onCreate");
}
public void onActivityCreated(Bundle savedInstanceState) {
Log.d(TAG, "MapActivity onActivityCreated");
context = getActivity();
SetRightMapDisplayAddress rightMapDisplayAddress = new SetRightMapDisplayAddress();
rightMapDisplayAddress.execute(STRING_LOCATION);
DownloadSuperMarketsArray superMarketsArray = new DownloadSuperMarketsArray();
superMarketsArray.execute();
overlayManager = mapController.getOverlayManager();
overlayManager.getMyLocation().setEnabled(false);
super.onActivityCreated(savedInstanceState);
}
Segundo Fragmento:
public class MainWindowActivity extends Fragment {
private static final String TAG = "MainWindowActivity";
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
Log.d(TAG, "MainWindowActivity onCreateView");
View view = (RelativeLayout) inflater.inflate(R.layout.main_window_layout, container, false);
if (container == null) {
return null;
}
return view;
}
}
Y el tercero:
public class FindTovarFragment extends Fragment {
private static final String TAG= "FindTovarFragment";
Context context;
ArrayList<Category> categories;
Spinner categoryContainer;
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
Log.d(TAG, "FindTovarFragment onCreateView");
View view = (LinearLayout) inflater.inflate(R.layout.find_tovar_main_layout, container, false);
categoryContainer = (Spinner) view.findViewById(R.id.category);
return view;
}
@Override
public void onActivityCreated(Bundle savedInstanceState) {
super.onActivityCreated(savedInstanceState);
Log.d(TAG, "FindTovarFragment onActivityCreated");
DownloadCategory downloadCategory = new DownloadCategory();
downloadCategory.execute();
}
Registros para MapActivity:
06-20 11:06:37.709: DEBUG/MapActivity(1290): MapActivity onCreate
06-20 11:06:37.709: DEBUG/MapActivity(1290): MapActivity onCreateView
06-20 11:06:38.509: DEBUG/MapActivity(1290): MapActivity onActivityCreated
Entonces una y otra vez
06-20 11:07:53.239: DEBUG/MapActivity(1290): MapActivity onCreate
06-20 11:07:53.239: DEBUG/MapActivity(1290): MapActivity onCreateView
06-20 11:07:53.429: DEBUG/MapActivity(1290): MapActivity onActivityCreated
06-20 11:08:23.029: DEBUG/MapActivity(1290): MapActivity onCreate
06-20 11:08:23.039: DEBUG/MapActivity(1290): MapActivity onCreateView
06-20 11:08:23.269: DEBUG/MapActivity(1290): MapActivity onActivityCreated
Muchas gracias por adelantado.
Cambiaría tu arquitectura por esta en la documentación del desarrollador de Android:
http://developer.android.com/reference/android/support/v4/app/FragmentPagerAdapter.html
pero cambiaría algunas cosas ...
1-Yo cambiaría este método:
/**
* The Fragment''s UI is just a simple text view showing its
* instance number.
*/
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
View v = inflater.inflate(R.layout.fragment_pager_list, container, false);
View tv = v.findViewById(R.id.text);
((TextView)tv).setText("Fragment #" + mNum);
return v;
}
Para algo como esto, donde decidimos qué fragmento rellenas dependiendo de la posición de viewPager:
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,Bundle savedInstanceState) {
super.onCreateView(inflater, container, savedInstanceState);
SupportFragmentManager ft = getChildFragmentManager().beginTransaction();
String tag = "";
Fragment fragment = null;
switch (mNum) {
case 0:
fragment = new MyFragmentZero();
tag = FragmentTags.TAG_0;
break;
case 1:
fragment = new MyFragmentOne();
tag = FragmentTags.TAG_3;
break;
case 2:
fragment = new MyFragmentTwo();
tag = FragmentTags.TAG_2;
break;
default:
break;
}
/*OPTIONAL We can pass arguments to the fragments
Bundle args = new Bundle();
args.putInt(Arguments.ARG_POSITION, mNum);
fragment.setArguments(args);*/
//Place the fragment in the container
ft.replace(R.id.fragment_container fragment, tag);
ft.commit();
//You need a base layout for all fragment and use nested fragments later or you can define the layout for each position(mNum) inside the switch.
return inflater.inflate(R.layout.fragment_layout_default_for_all_views, container,
false);
}
De esta manera, tendrás una buena arquitectura y una vez que esté funcionando así, debería estar bien.
De todos modos, debes saber cómo funciona viewPager al poblar el fragmento en las diferentes posiciones.
Cuando comienzas en la posición 0, se crean el fragmento en la posición 0 y el de la posición 1.
Luego, cuando deslizas hacia la posición 1, se crea el fragmento en la posición 2, por lo que ahora tienes los tres fragmentos creados en las diferentes posiciones (0,1,2 ... suponiendo que tienes solo 3 páginas en viewPager).
Pasamos a la posición 2, la última, y el fragmento en la primera posición (0) se destruye, por lo que ahora tenemos los fragmentos en las posiciones 2 y 3.
Espero que haya sido útil y avíseme si tiene algún problema. Aclamaciones
Finalmente pude resolverlo. Solo necesita anular el método destroyItem para que no destruya objetos. Espero que esto sea útil para alguien.
@Override
public void destroyItem(ViewGroup container, int position, Object object) {
Log.d(TAG, "destroy!");
}
ViewPager conserva en la memoria 1 página de forma predeterminada, a ambos lados de la página actual. Por lo tanto, no volvería a crear esas páginas al deslizar 1 página a la izquierda / derecha de la página actual. Pero cuando desliza más de 1 página hacia la izquierda / derecha, volvería a crear esas páginas, por lo que se llama OnCreateView (), OnCreate ().
Si la aplicación usa pocas páginas 3, puede aumentar el número de páginas para retener llamando,
mViewPager.setOffscreenPageLimit(2);
Descrito here