Cara statis untuk mendapatkan 'Konteks' di Android?

970

Apakah ada cara untuk mendapatkan Contextinstance saat ini di dalam metode statis?

Saya mencari cara itu karena saya benci menyimpan contoh 'Konteks' setiap kali itu berubah.

Andrea Baccega
sumber
57
Tidak menyimpan Konteks adalah ide yang bagus bukan hanya karena tidak nyaman, tetapi lebih karena dapat menyebabkan kebocoran memori yang besar!
Vikram Bodicherla
12
@ VikramBodicherla Ya, tetapi jawaban di bawah ini mengasumsikan bahwa kita berbicara tentang konteks aplikasi. Jadi, kebocoran memori bukan masalah, tetapi pengguna hanya boleh menggunakan solusi ini di mana itu konteks yang tepat untuk digunakan.
Tom
Jika Anda harus menggunakan cara statis untuk mendapatkan Context, maka mungkin ada cara yang lebih baik untuk merancang kode.
Anonsage
3
Dokumentasi Android merekomendasikan untuk meneruskan konteks kepada pengambil singletons. developer.android.com/reference/android/app/Application.html
Marco Luglio
Untuk memilih lajang dan konteks yang diteruskan dengan getInstance () daripada konteks statis, silakan lihat, saya mencoba menjelaskan alasan saya di sini didukung dengan kode kerja: stackoverflow.com/a/38967293/4469112
Alessio

Jawaban:

1302

Melakukan hal ini:

Dalam file Android Manifest, nyatakan yang berikut ini.

<application android:name="com.xyz.MyApplication">

</application>

Kemudian tulis kelas:

public class MyApplication extends Application {

    private static Context context;

    public void onCreate() {
        super.onCreate();
        MyApplication.context = getApplicationContext();
    }

    public static Context getAppContext() {
        return MyApplication.context;
    }
}

Sekarang di mana-mana panggilan MyApplication.getAppContext()untuk mendapatkan konteks aplikasi Anda secara statis.

Rohit Ghatol
sumber
81
Apakah ada kerugian untuk metode ini? Ini sepertinya curang. (
Retas
203
The downside adalah bahwa tidak ada jaminan bahwa onCreate () non-statis akan dipanggil sebelum beberapa kode inisialisasi statis mencoba mengambil objek Konteks Anda. Itu berarti kode panggilan Anda harus siap untuk berurusan dengan nilai-nilai nol yang mengalahkan seluruh poin dari pertanyaan ini.
Melinda Green
8
Mungkin juga .. haruskah kita mendeklarasikan static contextvariabel ini sebagai volatile?
Vladimir Sorokin
14
@ Tom Ini bukan kasus anggota data statis yang awalnya statis. Dalam kode yang diberikan, anggota statis diinisialisasi non-statis di onCreate (). Bahkan data yang diinisialisasi secara statis tidak cukup baik dalam hal ini karena tidak ada yang menjamin bahwa inisialisasi statis dari kelas yang diberikan akan terjadi sebelum akan diakses selama inisialisasi statis dari beberapa kelas lain.
Melinda Green
10
@MelindaGreen Menurut dokumentasi untuk Aplikasi, onCreate () dipanggil sebelum aktivitas, layanan, atau penerima (tidak termasuk penyedia konten) telah dibuat. Jadi bukankah solusi ini aman selama Anda tidak mencoba mengakses getAppContext () dari penyedia konten?
Magnus W
86

Mayoritas aplikasi yang menginginkan metode yang nyaman untuk mendapatkan konteks aplikasi membuat kelas mereka sendiri yang meluas android.app.Application.

PANDUAN

Anda dapat melakukannya dengan terlebih dahulu membuat kelas di proyek Anda seperti berikut:

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;
    }
}

Kemudian, di AndroidManifest Anda, Anda harus menentukan nama kelas Anda di tag AndroidManifest.xml:

<application 
    ...
    android:name="com.example.App" >
    ...
</application>

Anda kemudian dapat mengambil konteks aplikasi dalam metode statis menggunakan yang berikut:

public static void someMethod() {
    Context context = App.getContext();
}

PERINGATAN

Sebelum menambahkan sesuatu seperti di atas ke proyek Anda, Anda harus mempertimbangkan apa yang dikatakan dokumentasi:

Biasanya tidak perlu untuk subkelas Aplikasi. Dalam sebagian besar situasi, lajang statis dapat menyediakan fungsionalitas yang sama dengan cara yang lebih modular. Jika singleton Anda memerlukan konteks global (misalnya untuk mendaftarkan penerima siaran), fungsi untuk mengambilnya dapat diberikan Konteks yang secara internal menggunakan Context.getApplicationContext () ketika pertama kali membangun singleton.


REFLEKSI

Ada juga cara lain untuk mendapatkan konteks aplikasi menggunakan refleksi. Refleksi sering dipandang rendah di Android dan saya pribadi berpikir ini tidak boleh digunakan dalam produksi.

Untuk mengambil konteks aplikasi kita harus memanggil metode pada kelas tersembunyi ( ActivityThread ) yang telah tersedia sejak API 1:

public static Application getApplicationUsingReflection() throws Exception {
    return (Application) Class.forName("android.app.ActivityThread")
            .getMethod("currentApplication").invoke(null, (Object[]) null);
}

Ada satu lagi kelas tersembunyi ( AppGlobals ) yang menyediakan cara untuk mendapatkan konteks aplikasi secara statis. Itu mendapatkan konteks menggunakan ActivityThreadsehingga benar-benar tidak ada perbedaan antara metode berikut dan yang diposting di atas:

public static Application getApplicationUsingReflection() throws Exception {
    return (Application) Class.forName("android.app.AppGlobals")
            .getMethod("getInitialApplication").invoke(null, (Object[]) null);
} 

Selamat coding!

Jared Rummler
sumber
56

Dengan asumsi kita sedang berbicara tentang mendapatkan Konteks Aplikasi, saya menerapkannya seperti yang disarankan oleh @Rohit Ghatol memperluas Aplikasi. Apa yang terjadi kemudian, adalah bahwa tidak ada jaminan bahwa konteks yang diambil sedemikian rupa akan selalu non-nol. Pada saat Anda membutuhkannya, biasanya karena Anda ingin menginisialisasi pembantu, atau mendapatkan sumber daya, Anda tidak dapat menunda waktu; menangani case null tidak akan membantu Anda. Jadi saya mengerti bahwa saya pada dasarnya berjuang melawan arsitektur Android, seperti yang dinyatakan dalam dokumen

Catatan: Biasanya tidak perlu untuk subkelas Aplikasi. Dalam kebanyakan situasi, lajang statis dapat menyediakan fungsionalitas yang sama dengan cara yang lebih modular. Jika singleton Anda memerlukan konteks global (misalnya untuk mendaftarkan penerima siaran), sertakan Context.getApplicationContext () sebagai argumen Konteks saat menggunakan metode getInstance () singleton Anda.

dan dijelaskan oleh Dianne Hackborn

Satu-satunya alasan Aplikasi ada sebagai sesuatu yang dapat Anda peroleh adalah karena selama pengembangan pra-1.0 salah satu pengembang aplikasi kami terus-menerus menggangguku tentang perlunya memiliki objek aplikasi tingkat atas yang dapat mereka peroleh sehingga mereka dapat memiliki yang lebih "normal". "kepada mereka model aplikasi, dan saya akhirnya menyerah. Saya akan selamanya menyesal menyerah pada yang satu itu. :)

Dia juga menyarankan solusi untuk masalah ini:

Jika yang Anda inginkan adalah keadaan global yang dapat dibagikan di berbagai bagian aplikasi Anda, gunakan singleton. [...] Dan ini mengarah secara lebih alami pada bagaimana Anda seharusnya mengelola hal-hal ini - menginisialisasinya sesuai permintaan.

jadi apa yang saya lakukan adalah menyingkirkan memperpanjang Aplikasi, dan meneruskan konteks langsung ke getInstance () pembantu tunggal, sambil menyimpan referensi ke konteks aplikasi di konstruktor pribadi:

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;
    }
}

penelepon kemudian akan memberikan konteks lokal kepada penolong:

Helper.getInstance(myCtx).doSomething();

Jadi, untuk menjawab pertanyaan ini dengan benar: ada cara untuk mengakses Konteks Aplikasi secara statis, tetapi mereka semua harus berkecil hati, dan Anda harus lebih suka meneruskan konteks lokal ke getInstance singleton ().


Bagi siapa pun yang tertarik, Anda dapat membaca versi yang lebih rinci di blog fwd

Alessio
sumber
1
@Alessio Bukankah metode ini menyebabkan kebocoran memori
Phillip Kigenyi
2
@cephephillip Saya tidak mengerti apa yang Anda bicarakan. Singleton merujuk konteks aplikasi yang diambil dari aktivitas yang lewat, bukan aktivitas host. Itu sah, dan itu tidak akan menyebabkan kebocoran memori. Itulah poin utama dari blog yang saya tulis. Jika Anda benar-benar berpikir Anda benar, kirimkan saya contoh kode di mana saya dapat mereproduksi kebocoran memori yang Anda bicarakan, karena bukan itu masalahnya.
Alessio
1
Saya pikir @KigenyiPhillip benar, dan ini masih merupakan sumber kebocoran. Bayangkan bagan referensi setelah panggilan pertama Anda ke getInstance(ctx). Anda memiliki akar instancetipe GC MyHelper, yang memiliki bidang mContexttipe pribadi Context, yang merujuk konteks aplikasi yang dikumpulkan melalui konteks yang diteruskan ke getInstance(). instancetidak pernah diset kedua kalinya, juga tidak dihapus, sehingga GC tidak akan pernah menangkap konteks aplikasi yang dirujuk oleh instance. Anda tidak membocorkan kegiatan apa pun sehingga IMO biaya rendah.
Mark McKenna
1
@MarkMcKenna ketika Anda menyatakan "yang memiliki bidang pribadi mContext dari tipe Context, yang mereferensikan konteks aplikasi", jadi jelas bagi Anda bahwa mContext adalah referensi ke konteks aplikasi, bukan konteks apa pun. Dalam dokumen getApplicationContext () Anda membaca: "Konteks yang siklus hidupnya terpisah dari konteks saat ini, yang terkait dengan masa proses daripada komponen saat ini". Bagaimana ini bisa membuat kebocoran memori? Konteks aplikasi GC hanya ketika proses keluar.
Alessio
1
@Alessio jika Anda menerima bahwa referensi ke konteks aplikasi tidak memenuhi syarat sebagai kebocoran sumber daya, maka Anda dapat menyederhanakan ini dengan posting referensi statis untuk thisdi Application.onCreate(), yang membuat jawaban yang diterima lebih baik.
Mark McKenna
49

Tidak, saya kira tidak ada. Sayangnya, Anda mengalami panggilan macet getApplicationContext()dari Activityatau salah satu subclass dari Context. Juga, ini pertanyaan agak terkait.

Erich Douglass
sumber
8
Tautan yang tepat ke artikel: android-developers.blogspot.co.il/2009/01/…
Tal Weiss
38

Berikut adalah cara tidak berdokumen untuk mendapatkan Aplikasi (yang merupakan Konteks) dari mana saja di utas UI. Itu bergantung pada metode statis tersembunyi ActivityThread.currentApplication(). Ini harus bekerja setidaknya di Android 4.x.

try {
    final Class<?> activityThreadClass =
            Class.forName("android.app.ActivityThread");
    final Method method = activityThreadClass.getMethod("currentApplication");
    return (Application) method.invoke(null, (Object[]) null);
} catch (final ClassNotFoundException e) {
    // handle exception
} catch (final NoSuchMethodException e) {
    // handle exception
} catch (final IllegalArgumentException e) {
    // handle exception
} catch (final IllegalAccessException e) {
    // handle exception
} catch (final InvocationTargetException e) {
    // handle exception
}

Perhatikan bahwa mungkin untuk metode ini mengembalikan nol, misalnya ketika Anda memanggil metode di luar utas UI, atau aplikasi tidak terikat pada utas.

Masih lebih baik menggunakan solusi @RohitGhatol jika Anda dapat mengubah kode Aplikasi.

kennytm
sumber
1
Saya menggunakan metode KennyTM di atas, tetapi kadang-kadang metode mengembalikan null. Apakah ada alternatif lain untuk ini? Seperti jika kita mendapatkan nol di sini, kita dapat mengambil konteks dari tempat lain. Dalam kasus saya, onCreate () Aplikasi tidak dipanggil. Tetapi metode di atas dipanggil sebelum itu. Bantuan Plzzz
AndroidGuy
Ini tidak akan selalu berhasil jika GC membersihkan semua hal yang terkait aktivitas.
AlexVPerl
32

Tergantung pada apa Anda menggunakan konteks untuk. Saya dapat memikirkan setidaknya satu kelemahan dari metode itu:

Jika Anda mencoba membuat AlertDialogdengan AlertDialog.Builder, Applicationkonteksnya tidak akan berfungsi. Saya percaya Anda perlu konteks untuk saat ini Activity...

gulchrider
sumber
6
Betul. Jika Anda menggunakan konteks aplikasi untuk itu, Anda mungkin melihat dialog Anda tersembunyi di bawah kegiatan foreground.
Nate
3
+1 pertama-tama. Dan kemungkinan kesalahan yang muncul adalah Tidak dapat memulai aktivitas ComponentInfo {com.samples / com.MyActivity}: android.view.WindowManager $ BadTokenException: Tidak dapat menambahkan window - token null bukan untuk aplikasi
Govind
15

Cara Kotlin :

Nyata:

<application android:name="MyApplication">

</application>

MyApplication.kt

class MyApplication: Application() {

    override fun onCreate() {
        super.onCreate()
        instance = this
    }

    companion object {
        lateinit var instance: MyApplication
            private set
    }
}

Anda kemudian dapat mengakses properti melalui MyApplication.instance

PHNNN
sumber
11

Jika Anda terbuka untuk menggunakan RoboGuice , Anda dapat menyuntikkan konteksnya ke kelas yang Anda inginkan. Berikut adalah contoh kecil bagaimana melakukannya dengan RoboGuice 2.0 (beta 4 pada saat penulisan ini)

import android.content.Context;
import android.os.Build;
import roboguice.inject.ContextSingleton;

import javax.inject.Inject;

@ContextSingleton
public class DataManager {
    @Inject
    public DataManager(Context context) {
            Properties properties = new Properties();
            properties.load(context.getResources().getAssets().open("data.properties"));
        } catch (IOException e) {
        }
    }
}
pengguna605331
sumber
8

Saya telah menggunakan ini di beberapa titik:

ActivityThread at = ActivityThread.systemMain();
Context context = at.getSystemContext();

Ini adalah konteks yang valid yang saya gunakan untuk mendapatkan layanan sistem dan bekerja.

Tapi, saya menggunakannya hanya dalam modifikasi framework / base dan tidak mencobanya di aplikasi Android.

Sebuah peringatan bahwa Anda harus tahu: Ketika mendaftar untuk penerima siaran dengan konteks ini, tidak akan bekerja dan Anda akan mendapatkan:

java.lang.SecurityException: Paket penelepon yang diberikan android tidak berjalan dalam proses ProcessRecord

ungalcrys
sumber
7

Kotlin

open class MyApp : Application() {
    override fun onCreate() {
        super.onCreate()
        mInstance = this
    }

    companion object {
        lateinit var mInstance: MyApp
        fun getContext(): Context? {
            return mInstance.applicationContext
        }
    }
}

dan dapatkan Context like

MyApp.mInstance

atau

MyApp.getContext()
Khemraj
sumber
4

Anda dapat menggunakan yang berikut ini:

MainActivity.this.getApplicationContext();

MainActivity.java:

...
public class MainActivity ... {
    static MainActivity ma;
...
    public void onCreate(Bundle b) {
         super...
         ma=this;
         ...

Kelas lain:

public ...
    public ANY_METHOD... {
         Context c = MainActivity.ma.getApplicationContext();
barwnikk
sumber
3
Ini hanya berfungsi jika Anda berada di dalam kelas batin, yang hampir tidak terjadi di OP.
Richard J. Ross III
3
Ini akan berfungsi selama ANY_METHOD dipanggil setelah MainActivity dibuat, tetapi menjaga referensi statis untuk aktivitas hampir pasti menimbulkan kebocoran memori (seperti tanggapan lain atas pertanyaan OP sudah disebutkan), jadi jika Anda benar-benar harus menyimpan referensi statis, gunakan aplikasi hanya konteks.
handtwerk
1
Kelas batin itu jahat. Bagian terburuknya adalah banyak orang melakukan itu untuk AsyncTasks dan hal-hal seperti itu, karena banyak tutorial melakukannya dengan cara itu ...
Reinherd
4

Jika Anda tidak ingin mengubah file manifes, Anda dapat secara manual menyimpan konteks dalam variabel statis di aktivitas awal Anda:

public class App {
    private static Context context;

    public static void setContext(Context cntxt) {
        context = cntxt;
    }

    public static Context getContext() {
        return context;
    }
}

Dan atur konteks saat aktivitas (atau aktivitas) Anda dimulai:

// MainActivity

@Override
public void onCreate(Bundle savedInstanceState) {
    super.onCreate(savedInstanceState);
    setContentView(R.layout.activity_main);

    // Set Context
    App.setContext(getApplicationContext());

    // Other stuff
}

Catatan: Seperti semua jawaban lain, ini adalah potensi kebocoran memori.

Sheharyar
sumber
1
Apa yang sebenarnya akan bocor karena konteks dalam kasus ini terikat pada aplikasi? Jika aplikasi mati, begitu juga semua hal lainnya.
TheRealChx101
3

Saya pikir Anda memerlukan tubuh untuk getAppContext()metode ini:

public static Context getAppContext()
   return MyApplication.context; 
Kognos
sumber
3

Menurut sumber ini Anda bisa mendapatkan Konteks Anda sendiri dengan memperluas ContextWrapper

public class SomeClass extends ContextWrapper {

    public SomeClass(Context base) {
      super(base);
    }

    public void someMethod() {
        // notice how I can use "this" for Context
        // this works because this class has it's own Context just like an Activity or Service
        startActivity(this, SomeRealActivity.class);

        //would require context too
        File cacheDir = getCacheDir();
    }
}

JavaDoc untuk ContextWrapper

Proksi implementasi Konteks yang hanya mendelegasikan semua panggilannya ke Konteks lain. Dapat disubklasifikasikan untuk memodifikasi perilaku tanpa mengubah Konteks asli.

BlueWizard
sumber
1
Ini menarik. Bagus untuk belajar tentang ContextWrapper. Namun, jika Anda harus meneruskan konteks aplikasi ke konstruktor ini, Anda masih perlu mendapatkannya dari suatu tempat.
jk7
2

Jika Anda karena suatu alasan menginginkan konteks Aplikasi di kelas mana pun, bukan hanya yang memperpanjang aplikasi / aktivitas, mungkin untuk beberapa kelas pabrik atau pembantu. Anda dapat menambahkan singleton berikut ke aplikasi Anda.

public class GlobalAppContextSingleton {
    private static GlobalAppContextSingleton mInstance;
    private Context context;

    public static GlobalAppContextSingleton getInstance() {
        if (mInstance == null) mInstance = getSync();
        return mInstance;
    }

    private static synchronized GlobalAppContextSingleton getSync() {
        if (mInstance == null) mInstance = 
                new GlobalAppContextSingleton();
        return mInstance;
    }

    public void initialize(Context context) {
        this.context = context;
    }

    public Context getApplicationContext() {
        return context;
    }
}

kemudian inisialisasi di onCreate dengan kelas aplikasi Anda

GlobalAppContextSingleton.getInstance().initialize(this);

gunakan di mana saja dengan menelepon

GlobalAppContextSingleton.getInstance().getApplicationContext()

Saya tidak merekomendasikan pendekatan ini untuk apa pun kecuali konteks aplikasi. Karena dapat menyebabkan kebocoran memori.

Versa
sumber
Ini tidak seperti nama-nama kelas / metode diatur dalam batu, disimpan lama dan (mudah-mudahan) deskriptif untuk T&J, disingkat untuk penggunaan saya sendiri.
Versa
1

Saya menggunakan variasi pola desain Singleton untuk membantu saya dalam hal ini.

import android.app.Activity;
import android.content.Context;

public class ApplicationContextSingleton {
    private static Activity gContext;

    public static void setContext( Activity activity) {
        gContext = activity;
    }

    public static Activity getActivity() {
        return gContext;
    }

    public static Context getContext() {
        return gContext;
    }
}

Saya kemudian menelepon ApplicationContextSingleton.setContext( this );di saya activity.onCreate () dan ApplicationContextSingleton.setContext( null );di onDestroy () ;

Bamaco
sumber
Jika yang Anda butuhkan adalah konteks, Anda dapat menghubungi activity.getApplicationContext (); Itu bisa dipertahankan secara statis tanpa harus khawatir tentang kebocoran.
MinceMan
2
ini akan menghasilkan kebocoran memori
BlueWizard
1

Saya baru saja merilis kerangka kerja yang terinspirasi jQuery untuk Android bernama Vapor API yang bertujuan untuk membuat pengembangan aplikasi lebih sederhana.

Kelas $fasad pusat mempertahankan WeakReference(tautan ke posting blog Java yang mengagumkan tentang ini oleh Ethan Nicholas) ke Activitykonteks saat ini yang dapat Anda ambil dengan menelepon:

$.act()

A WeakReferencemenyimpan referensi tanpa mencegah pengumpulan sampah merebut kembali objek asli, jadi Anda seharusnya tidak memiliki masalah dengan kebocoran memori.

Kelemahannya tentu saja adalah Anda menjalankan risiko yang $.act()bisa mengembalikan nol. Saya belum menemukan skenario ini, jadi itu mungkin hanya risiko minimal, layak disebut.

Anda juga dapat mengatur konteks secara manual jika Anda tidak menggunakan VaporActivitysebagai Activitykelas Anda :

$.act(Activity);

Juga, banyak kerangka kerja Vapor API menggunakan konteks tersimpan ini secara inheren yang mungkin berarti Anda tidak perlu menyimpannya sama sekali jika Anda memutuskan untuk menggunakan kerangka kerja tersebut. Lihatlah situs untuk informasi lebih lanjut dan sampel.

Saya harap itu membantu :)

Darius
sumber
1
Rupanya ini baru saja diturunkan .. sebuah penjelasan akan menyenangkan !?
Darius
1
Saya tidak downvote ini, tetapi Javascript tidak ada hubungannya dengan pertanyaan yang ada, yang akan menjelaskan downvotes yang mungkin Anda miliki! Bersulang.
Ernani Joppert
Itu akan sangat tidak masuk akal mengingat itu terinspirasi oleh beberapa aspek jQuery seperti antarmuka yang lancar, dan abstraksinya .. itu adalah prinsip agnostik dari bahasa yang mendasarinya!
Darius
1
Jadi Anda downvoting karena terinspirasi oleh semantik API kerangka kerja yang tidak pada platform yang sama ?! Saya pikir kalian kehilangan titik menerapkan prinsip platform-agnostik .........................................
Darius
3
jawaban ini sama sekali tidak terkait dengan JavaScript. Baca jawabannya sebelum Anda downvote: /
BlueWizard
1

Jawaban Rohit sepertinya benar. Namun, perlu diketahui bahwa "Instant Run" AndroidStudio tergantung pada tidak memiliki static Contextatribut dalam kode Anda, sejauh yang saya tahu.

berbayar
sumber
1
Kamu benar. Dan itu juga akan mengakibatkan kebocoran memori!
user1506104
1

di Kotlin, menempatkan Konteks / Konteks Aplikasi di objek pendamping masih menghasilkan peringatan Do not place Android context classes in static fields; this is a memory leak (and also breaks Instant Run)

atau jika Anda menggunakan sesuatu seperti ini:

    companion object {
        lateinit var instance: MyApp
    }

Ini hanya menipu serat untuk tidak menemukan kebocoran memori, contoh App masih dapat menghasilkan kebocoran memori, karena kelas Aplikasi dan turunannya adalah sebuah Konteks.

Atau, Anda dapat menggunakan antarmuka fungsional atau properti Fungsional untuk membantu Anda mendapatkan konteks aplikasi Anda.

Cukup buat kelas objek:

object CoreHelper {
    lateinit var contextGetter: () -> Context
}

atau Anda bisa menggunakannya lebih aman menggunakan jenis nullable:

object CoreHelper {
    var contextGetter: (() -> Context)? = null
}

dan di kelas Aplikasi Anda tambahkan baris ini:


class MyApp: Application() {

    override fun onCreate() {
        super.onCreate()
        CoreHelper.contextGetter = {
            this
        }
    }
}

dan di manifes Anda menyatakan nama aplikasi ke . MyApp


    <application
            android:name=".MyApp"

Ketika Anda ingin mendapatkan konteksnya, hubungi:

CoreHelper.contextGetter()

// or if you use the nullable version
CoreHelper.contextGetter?.invoke()

Semoga ini bisa membantu.

Hayi Nukman
sumber
Kelas objek corehelper ini akan diinisialisasi dan dapat digunakan melalui kegiatan di tahap selanjutnya? Maaf saya baru ke kotlin
Dr. aNdRO
ya persis.
Hayi Nukman
-1

Coba sesuatu seperti ini

import androidx.appcompat.app.AppCompatActivity;  
import android.content.Context; 
import android.os.Bundle;

public class MainActivity extends AppCompatActivity {
    private static Context context;

    @Override
    protected void onCreate(Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);
        setContentView(R.layout.activity_main);
        context = getApplicationContext();
    }

    public static void getContext(View view){
        Toast.makeText(context, "Got my context!",
                    Toast.LENGTH_LONG).show();    
    }
}
chandra shekar
sumber