with tutorial parameter onattach fragments example android constructor android-fragments default-constructor

tutorial - onattach android



Crear un fragmento: constructor vs newInstance() (2)

Personalmente encuentro que usar constructores es una práctica mucho más común que saber usar newInstance () y pasar parámetros.

El patrón de método de fábrica se usa con bastante frecuencia en el desarrollo de software moderno.

Así que básicamente mi pregunta es, ¿por qué Google no quiere que uses constructores con parámetros para Fragmentos?

Ha respondido a su propia pregunta:

Mi única conjetura es que no intentes establecer una variable de instancia sin usar el Bundle, que no se establecerá cuando se vuelva a crear el Fragment.

Correcto.

Todavía no siento que esto sea motivo suficiente para no permitir el uso de parámetros en los constructores.

Eres bienvenido a tu opinión Le invitamos a desactivar esta verificación de pelusa, ya sea por cada constructor o por cada forma de trabajo.

Recientemente me cansé de tener que saber constantemente las Claves de String para pasar argumentos a Bundles cuando creo mis Fragments . Así que decidí hacer constructores para mis Fragments que tomarían los parámetros que quería establecer, y colocar esas variables en los Bundles con las claves de String correctas, eliminando así la necesidad de otros Fragments y Activities necesiten conocer esas claves.

public ImageRotatorFragment() { super(); Log.v(TAG, "ImageRotatorFragment()"); } public ImageRotatorFragment(int imageResourceId) { Log.v(TAG, "ImageRotatorFragment(int imageResourceId)"); // Get arguments passed in, if any Bundle args = getArguments(); if (args == null) { args = new Bundle(); } // Add parameters to the argument bundle args.putInt(KEY_ARG_IMAGE_RES_ID, imageResourceId); setArguments(args); }

Y luego saco esos argumentos como normal.

@Override public void onCreate(Bundle savedInstanceState) { super.onCreate(savedInstanceState); Log.v(TAG, "onCreate"); // Set incoming parameters Bundle args = getArguments(); if (args != null) { mImageResourceId = args.getInt(KEY_ARG_IMAGE_RES_ID, StaticData.getImageIds()[0]); } else { // Default image resource to the first image mImageResourceId = StaticData.getImageIds()[0]; } }

Sin embargo, Lint se molestó con esto, diciendo que no tenía subclases de Fragment con constructores con otros parámetros, requiriéndome usar @SuppressLint("ValidFragment") incluso para ejecutar la aplicación. El caso es que este código funciona perfectamente bien. Puedo usar ImageRotatorFragment(int imageResourceId) o el antiguo método de la escuela ImageRotatorFragment() y llamar a setArguments() manualmente en él. Cuando Android necesita recrear el Fragmento (cambio de orientación o poca memoria), llama al constructor ImageRotatorFragment() y luego pasa el mismo argumento Bundle con mis valores, que se configuran correctamente.

Así que he estado buscando el enfoque "sugerido" y veo muchos ejemplos usando newInstance() para crear Fragments con parámetros, lo que parece hacer lo mismo que mi constructor. Así que hice lo mío para probarlo, y funciona tan impecablemente como antes, menos Lint quejándose al respecto.

public static ImageRotatorFragment newInstance(int imageResourceId) { Log.v(TAG, "newInstance(int imageResourceId)"); ImageRotatorFragment imageRotatorFragment = new ImageRotatorFragment(); // Get arguments passed in, if any Bundle args = imageRotatorFragment.getArguments(); if (args == null) { args = new Bundle(); } // Add parameters to the argument bundle args.putInt(KEY_ARG_IMAGE_RES_ID, imageResourceId); imageRotatorFragment.setArguments(args); return imageRotatorFragment; }

Personalmente encuentro que usar constructores es una práctica mucho más común que saber usar newInstance() y pasar parámetros. Creo que puedes usar esta misma técnica de constructor con Activities y Lint no se quejará de ello. Así que básicamente mi pregunta es, ¿por qué Google no quiere que uses constructores con parámetros para Fragments ?

Mi única conjetura es que no intentes establecer una variable de instancia sin usar el Bundle , que no se establecerá cuando se vuelva a crear el Fragment . Al usar un método static newInstance() , el compilador no le permitirá acceder a una variable de instancia.

public ImageRotatorFragment(int imageResourceId) { Log.v(TAG, "ImageRotatorFragment(int imageResourceId)"); mImageResourceId = imageResourceId; }

Todavía no siento que esto sea motivo suficiente para no permitir el uso de parámetros en los constructores. ¿Alguien más tiene una idea de esto?


Android solo recrea fragmentos que mata utilizando el constructor predeterminado, por lo que cualquier inicialización que hagamos en constructores adicionales se perderá. Se perderán los datos de host.