Come iniettare le classi statiche utilizzando Dagger?

Voglio introdurre l'iniezione di dipendenza attraverso il Dagger ad un progetto. Il seguente codice funge da esempio per descrivere il problema dell'iniezione in classi statiche .

Il metodo statico setupTextView() viene chiamato da più classi:

  • Accesso a localhost (Xamarin)
  • Studio Android - Imansible completare l'esecuzione della graduazione - errore nell'apertura del file zip
  • Imansible trovare annotations.jar dopo l'aggiornamento a ADT 23
  • Android TranslateAnimation si ripristina dopo l'animation
  • Rispondere automaticamente alla chiamata in arrivo programmata?
  • Come posso trovare l'ultimo frammento nella mainActivity
  •  public abstract class TextViewHelper { public static void setupTextView(TextView textView, Spanned text, TrackingPoint trackingPoint) { textView.setText(text, TextView.BufferType.SPANNABLE); textView.setMovementMethod(LinkMovementMethod.getInstance()); textView.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { MyApp.getTracker().track(trackingPoint); } }); } } 

    Ecco un esempio di utilizzo del metodo dell'helper:

     TextViewHelper.setupTextView(this, R.id.some_text_view, R.string.some_text, TrackingPoint.SomeTextClick); 

    Il tracking utilizzato nel metodo di aiuto è fornito dalla class di applicazione:

     public class MyApp extends Application { private static Tracking mTracking; public void onCreate() { super.onCreate(); mTracking = getTracking(getApplicationContext()); } private Tracking getTracking(Context context) { if (BuildConfig.DEBUG) { return new NoTracking(); } else { return new NsaTracking(context); } } public static Tracking getTracker() { return mTracking; } } 

    Ora, voglio iniettare il monitoraggio tramite Dagger. Quando ho rifattato il codice ho notato che avrei dovuto passare l'object di tracciamento dalla mia attività o frammento all'assistente statico poiché non posso inoltrare direttamente la class statica:

     TextViewHelper.setupTextView(this, R.id.some_text_view, R.string.some_text, TrackingPoint.SomeTextClick, Tracking tracking); 

    Questo non mi sembra un buon model di progettazione – poiché passa l'object TrackPoint e l'object Tracking . Come migliorare questa situazione?

  • Come copiare il text in Clip Board in Android?
  • La class di applicazione Android viene chiamata due volte
  • Come eseguire e visualizzare il risultato di un command con shell ssh con JSch?
  • Elemento random dall'arrays di string
  • Rotondo a 2 cifre decimali
  • Java httpPost in formato .asp
  • One Solution collect form web for “Come iniettare le classi statiche utilizzando Dagger?”

    Nel tuo TextViewHelper creare un field statico con il tracker.

     public class TextViewHelper { private TextViewHelper(){} @Inject static Tracking sTracker; public static void setupTextView(TextView textView, Spanned text, TrackingPoint trackingPoint) { textView.setText(text, TextView.BufferType.SPANNABLE); textView.setMovementMethod(LinkMovementMethod.getInstance()); textView.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { sTracker.track(trackingPoint); } }); } } 

    Ecco come configurare il module:

     @Module(staticInjections = TextViewHelper.class) public class TrackerModule { ... } 

    E il più importnte, call injectStatics sul tuo grafico.

     mObjectGraph = ObjectGraph.create(new TrackerModule()); mObjectGraph.injectStatics(); 

    Edit:

    Come notai che la documentazione di Dagger afferma che le iniezioni statiche "dovrebbero essere utilizzate in modo ridotto perché le dependencies statiche sono difficili da testare e riutilizzarle". È tutto vero, ma perché hai chiesto come iniettare l'object in class di utilità, questa è la soluzione migliore.

    Ma se vuoi che il tuo codice sia più testabile, crea un module come sotto:

     @Module(injects = {classs that utilizes TextViewHelper}) public class TrackerModule { @Provides Tracking provideTracker() { ... } @Provides @Singleton TextViewHelper provideTextViewHelper(Tracking tracker) { return new TextViewHelper(tracker); } } 

    Ora è ansible rimuovere static dai methods di TextViewHelper perché questa class di utilità verrà iniettata utilizzando il pugnale.

     public class TextViewHelper { private final Tracking mTracker; public TextViewHelper(Tracking tracker){ mTracker = tracker; } public void setupTextView(TextView textView, Spanned text, TrackingPoint trackingPoint) { ... } } 

    Questo è il modo in cui dovrebbe essere fatto se si desidera seguire le buone pratiche. Entrambe le soluzioni functionranno, quindi è a voi scegliere uno.

    L'Android è un fan Android di Google, tutto su telefoni Android, Android Wear, Android Dev e applicazioni Android Games e così via.