Gibt es eine Möglichkeit, die aktuelle Context
Instanz innerhalb einer statischen Methode?
Ich bin auf der Suche nach dieser Möglichkeit, weil ich es hasse, die Instanz "Context" jedes Mal zu speichern, wenn sie sich ändert.
Gibt es eine Möglichkeit, die aktuelle Context
Instanz innerhalb einer statischen Methode?
Ich bin auf der Suche nach dieser Möglichkeit, weil ich es hasse, die Instanz "Context" jedes Mal zu speichern, wenn sie sich ändert.
Tun Sie dies:
Geben Sie in der Android-Manifest-Datei Folgendes an.
<application android:name="com.xyz.MyApplication">
</application>
Dann schreiben Sie die Klasse:
public class MyApplication extends Application {
private static Context context;
public void onCreate() {
super.onCreate();
MyApplication.context = getApplicationContext();
}
public static Context getAppContext() {
return MyApplication.context;
}
}
Jetzt überall anrufen MyApplication.getAppContext()
um Ihren Anwendungskontext statisch zu erhalten.
Die meisten Anwendungen, die eine bequeme Methode zum Abrufen des Anwendungskontexts benötigen, erstellen ihre eigene Klasse, die die android.app.Application
.
GUIDE
Sie können dies erreichen, indem Sie zunächst eine Klasse in Ihrem Projekt wie die folgende erstellen:
import android.app.Application;
import android.content.Context;
public class App extends Application {
private static Application sApplication;
public static Application getApplication() {
return sApplication;
}
public static Context getContext() {
return getApplication().getApplicationContext();
}
@Override
public void onCreate() {
super.onCreate();
sApplication = this;
}
}
Dann sollten Sie in Ihrem AndroidManifest den Namen Ihrer Klasse im Tag AndroidManifest.xml angeben:
<application
...
android:name="com.example.App" >
...
</application>
Sie können dann den Anwendungskontext in jeder statischen Methode wie folgt abrufen:
public static void someMethod() {
Context context = App.getContext();
}
WARNUNG
Bevor Sie so etwas in Ihr Projekt einbauen, sollten Sie sich überlegen, was in der Dokumentation steht:
Normalerweise ist es nicht notwendig, Application zu unterklassifizieren. In den meisten Situationen, können statische Singletons die gleiche Funktionalität auf modularere Weise Weise bereitstellen. Wenn Ihr Singleton einen globalen Kontext benötigt (z.B. zur Registrierung von Broadcast-Empfänger), kann die Funktion, die ihn abruft, mit einem Context übergeben werden, der intern Context.getApplicationContext() verwendet, wenn wenn das Singleton zum ersten Mal konstruiert wird.
REFLECTION
Es gibt auch eine andere Möglichkeit, den Anwendungskontext mit Hilfe von Reflection zu erhalten. Reflection wird in Android oft verachtet und ich persönlich denke, dass dies nicht in der Produktion verwendet werden sollte.
Um den Anwendungskontext abzurufen, müssen wir eine Methode für eine verborgene Klasse aufrufen ( ActivityThread ), die seit API 1 verfügbar ist:
public static Application getApplicationUsingReflection() throws Exception {
return (Application) Class.forName("android.app.ActivityThread")
.getMethod("currentApplication").invoke(null, (Object[]) null);
}
Es gibt eine weitere versteckte Klasse ( AppGlobals ), die eine Möglichkeit bietet, den Anwendungskontext auf statische Weise zu erhalten. Es erhält den Kontext mit ActivityThread
Es gibt also keinen wirklichen Unterschied zwischen der folgenden Methode und der oben beschriebenen:
public static Application getApplicationUsingReflection() throws Exception {
return (Application) Class.forName("android.app.AppGlobals")
.getMethod("getInitialApplication").invoke(null, (Object[]) null);
}
Viel Spaß beim Codieren!
Wenn wir davon ausgehen, dass es darum geht, den Anwendungskontext zu erhalten, habe ich es wie von @Rohit Ghatol vorgeschlagen implementiert, indem ich Application. Was dann passierte, war, dass es keine Garantie dafür gibt, dass der auf diese Weise abgerufene Kontext immer nicht null ist. Zu dem Zeitpunkt, an dem man ihn braucht, will man in der Regel einen Helfer initialisieren oder eine Ressource abrufen, die man nicht aufschieben kann; die Behandlung des Null-Falls hilft einem nicht. Ich habe also verstanden, dass ich im Grunde gegen die Android-Architektur kämpfe, wie in der docs
Hinweis: Normalerweise ist es nicht notwendig, Application zu unterklassifizieren. In den meisten Situationen können statische Singletons die gleiche Funktionalität auf modularere Weise bereitstellen. Wenn Ihr Singleton einen globalen Kontext benötigt (zum Beispiel um Broadcast-Empfänger zu registrieren), fügen Sie Context.getApplicationContext() als Context-Argument ein, wenn Sie die getInstance()-Methode Ihres Singletons aufrufen.
und erklärt von Dianne Hackborn
Der einzige Grund, warum es Application als etwas gibt, von dem man ableiten kann, ist, dass einer unserer Anwendungsentwickler mich während der Vor-1.0-Entwicklung ständig damit genervt hat, dass er ein Top-Level-Anwendungsobjekt braucht, von dem er ableiten kann, damit er ein für ihn "normaleres" Anwendungsmodell hat, und ich habe schließlich nachgegeben. Ich werde es immer bereuen, dass ich nachgegeben habe :)
Sie schlägt auch die Lösung für dieses Problem vor:
Wenn Sie einen globalen Zustand wünschen, der von verschiedenen Teilen Ihrer Anwendung gemeinsam genutzt werden kann, verwenden Sie ein Singleton. [...] Und das führt natürlich dazu, wie Sie diese Dinge verwalten sollten - sie bei Bedarf initialisieren.
Was ich also tat, war, die Erweiterung Application loszuwerden und den Kontext direkt an getInstance() des Singleton-Helpers zu übergeben, während ich einen Verweis auf den Anwendungskontext im privaten Konstruktor speicherte:
private static MyHelper instance;
private final Context mContext;
private MyHelper(@NonNull Context context) {
mContext = context.getApplicationContext();
}
public static MyHelper getInstance(@NonNull Context context) {
synchronized(MyHelper.class) {
if (instance == null) {
instance = new MyHelper(context);
}
return instance;
}
}
übergibt der Aufrufer dann einen lokalen Kontext an die Hilfskraft:
Helper.getInstance(myCtx).doSomething();
Um also die Frage richtig zu beantworten: Es gibt Möglichkeiten, statisch auf den Anwendungskontext zuzugreifen, aber von allen sollte abgeraten werden, und Sie sollten es vorziehen, einen lokalen Kontext an getInstance() des Singletons zu übergeben.
Interessierte können eine ausführlichere Version lesen unter fwd blog
Nein, ich glaube nicht, dass es das gibt. Leider sind Sie darauf angewiesen, dass Sie getApplicationContext()
von Activity
oder eine der anderen Unterklassen von Context
. Auch, este Frage ist in gewisser Weise verwandt.
Kotlin Weg :
Manifest:
<application android:name="MyApplication">
</application>
MeineAnwendung.kt
class MyApplication: Application() {
override fun onCreate() {
super.onCreate()
instance = this
}
companion object {
lateinit var instance: MyApplication
private set
}
}
Sie können dann auf die Immobilie über MyApplication.instance
CodeJaeger ist eine Gemeinschaft für Programmierer, die täglich Hilfe erhalten..
Wir haben viele Inhalte, und Sie können auch Ihre eigenen Fragen stellen oder die Fragen anderer Leute lösen.