La forma adecuada para evitar el método estático (en la clase Util quizás) que se utiliza para actualizar la interfaz de usuario
Soy principiante en Android, he leído y ver si el uso del método estático en la clase Util para actualizar la interfaz de usuario no es bueno para la prueba de unidad. ¿Cómo evitarlo de manera adecuada para mantener el código y la prueba de unidad?
Ejemplo:
- Fragmentos parece ser excesivo? ¿No es posible una arquitectura MVC?
- ¿Por qué algunos métodos del SDK de Android aceptan una matriz como parámetro en lugar de devolver una matriz?
- Comparación de MVC de Java con patrón de diseño Android
- ¿Cómo uso eficazmente un bus de eventos?
- Arquitectura limpia contra MVPC / MVC / MVP
class ActivityA { private View view; private MyListener myListener; public void methodB() { Util.callLogicB(this, view, myListener); } } class ActivityB { private View view; private MyListener myListener; public void methodC() { Util.callLogicB(this, view, myListener); } } class Util { public static void callLogicB(Context context, View view, MyListener listener) { // do something with view } }
- ¿Es IntentService una implementación del patrón de comandos?
- Parcelable y herencia en Android
- ¿Deshacer / rehacer rápidamente con el patrón del memento / comando?
- ¿Hay un patrón de diseño para reducir la duplicación de código cuando subclases Actividades en Android?
- ¿Es el manejo de llamadas http de servicios de múltiples intenciones buen enfoque?
- Cómo implementar el patrón Decorator para las vistas de Android
- UITextView en Android (¿Qué es EditText?)
- ¿He usado Singleton con Realm Database correcto?
Creo que la mejor manera de implementar esto es desconectar completamente sus vistas (su actividad) de su clase lógica. Esto se puede hacer usando una interfaz .
Mira el código a continuación para entender cómo funciona una interfaz. He creado una mainActivity con un textView como un diseño. La clase LogicWithTextUpdate que creé es capaz de actualizar un textView dentro de su mainActivity sin una referencia directa a él .
public class MainActivity extends Activity implements MyViewListener { //Your logic class, that is capable of updating a textview LogicWithTextUpdate logicWithTextUpdate; @Override protected void onCreate(Bundle savedInstanceState) { //This is just to create a layout (with a textview inside) super.onCreate(savedInstanceState); setContentView(R.layout.activity_main); //This creates the class using constructor (and set listener) logicWithTextUpdate = new LogicWithTextUpdate(this); //Update or execute your logic. This will update textview using interface MyViewListener (onUpdateTextListener) //This can be executed using a button (Onclick...) logicWithTextUpdate.doSomeLogic(2); } @Override public void onUpdateTextListener(String text) { //Only here code runs inside your activity class TextView textView = (TextView) findViewById(R.id.textView); textView.setText(text); } }
Como puedes ver. MainActivity actualizará textview usando un "listener" onUpdateTextListener. Esto se describe dentro de una clase de interfaz:
public interface MyViewListener { //to be implemented inside your mainActivity public void onUpdateTextListener(String text); }
Ahora puedo implementar una clase que puede hacer algo de lógica y activar el oyente :
public class LogicWithTextUpdate { MyViewListener myViewListener; //Constructor here is used to set myViewListener (but you can use a setter like setMyViewListener) public LogicWithTextUpdate(MyViewListener myViewListener) { this.myViewListener = myViewListener; } public void doSomeLogic(int a) { //Some logic a = a * 2; a = a + 1; //Update text using listener. This will update mainActivity, because it is implementing MyViewListener myViewListener.onUpdateTextListener(String.valueOf(a)); } }
El método doSomeLogic se ejecuta desde su actividad, pero la lógica está dentro de la clase. Una vez ejecutada la lógica, activa myViewListener.onUpdateTextListener que ejecuta onUpdateTextListener dentro de su actividad.
Todo está desconectado . Puede cambiar sus vistas sin ninguna modificación en LogicWithTextUpdate, o cambiar la lógica sin modificaciones en Actitivy . Siempre una buena práctica.
AFAIK, es una buena práctica utilizar exclusivamente clases de utilidad para los métodos estáticos y auxiliares que generalmente devuelven datos primitivos y de referencia, en lugar de actualizar la interfaz de usuario, que debe realizarse sólo en Actividades. Por ejemplo, una clase de utilidad de ejemplo implicaría una serie de métodos tales como:
- Un método que genera un objeto URL de una URL de solicitud HTTP en formato String
- Un método que devuelve datos JSON legibles después de conectarse correctamente al servidor HTTP
- Un método que extrae los datos JSON y los almacena en un ArrayList retornable
- Un método público, estático que invocó todo lo anterior para finalmente devolver el ArrayList de datos a una Actividad a través de su subproceso de fondo para luego procesar la interfaz de usuario a través de su subproceso de interfaz de usuario
La clase estática es mala para las pruebas unitarias, porque no se puede burlar ni esbozar. Pero la clase de utilidad estática podría ser un enfoque muy útil. Le sugeriría que incluya alguna referencia de interfaz en una clase de utilidad estática, todavía tendrá la misma firma de clase de utilidad, pero le permite cambiar el comportamiento de clases de utilidad para pruebas u otro propósito:
final class Util { static IUtil util = new DefaultUtil(); private Util() {} public static void callLogicB(Context context, View view, MyListener listener) { util.callLogicB(context, view, listener); } } interface IUtil { public void callLogicB(Context context, View view, MyListener listener); } final class DefaultUtil implemets IUtil { @Override public void callLogicB(Context context, View view, MyListener listener) { // do something with view } } final class TestUtil implemets IUtil { @Override public void callLogicB(Context context, View view, MyListener listener) { //your test logic } } @Before void setUp() { Util.util = new TestUtil(); }
- La vista de texto cambia el color de fondo sin ninguna razón
- ¿Existe una forma estándar de suscribirse a un feed mediante una aplicación de podcast?