How i can use context in Singleton? - android

I need in my Singleton -> Context. I know that I can't passing argument in constructor, because object hasn't constructor.
Then I call it from my Application class.
Here is the code:
object Singleton {
var userAgentInfo: String = UserAgentTools.buildUserAgent(context)
fun initializeSdk() {
AuthenticatorApiManager.initializeSdk(userAgentInfo)
}
}

Move the initialization of userAgentInfo to the initializeSDK method, and send the Context as an argument, make sure to send the ApplicationContext.
object Singleton {
var userAgentInfo: String? = null
fun initializeSdk(context: Context) {
userAgentInfo = UserAgentTools.buildUserAgent(context)
AuthenticatorApiManager.initializeSdk(userAgentInfo)
}
}

Make Application class and write below code.
companion object {
private lateinit var sInstance: ApplicationClass
fun getInstance(): ApplicationClass {
return sInstance
}
}
Use in object like below.
ApplicationClass.getInstance()

You can use context in your Singleton class using Application class instance.here it is

Related

How to get static context in FlutterPlugin

I want to set static get and set context method in FlutterPlugin, how should I implement it in kotlin way?
class FlutterPushPlugin : FlutterPlugin {
private var context: Context? = null
fun getContext(): Context? {
return this.context
}
fun setContext(context: Context?) {
this.context = context
}
}
// In another class
FlutterPushPlugin.getContext // return the context property in FlutterPushPlugin
You could use a companion object or object itself to do the job, but it is strongly not recommended to put context in static objects as this could cause memory leaks. But if you do, you have to be very careful how you use them. Now for your question:
object StaticContext {
var context: Context? = null
}
Or
class FlutterPushPlugin : FlutterPlugin {
companion object {
var context: Context? = null
}
}
There is no need for getters and setters as Kotlin generates them when using var.

Accessing method from Application class in Kotlin Android

I have created an application class in Kotlin. I need to access a method that returns a variable from anywhere in my application. The problem is I am not able to access that method from other parts of the program. I am able to access when code is written in Java , but when code is written in Kotlin,then the method in Application class is not accessible. Please find below code for reference:
class MyRetroApplication : Application() {
lateinit var apiComponent:APIComponent
companion object {
var ctx: Context? = null
}
override fun onCreate() {
super.onCreate()
ctx = applicationContext
apiComponent = initDaggerComponent()
}
fun getMyComponent(): APIComponent {
return apiComponent
}
fun initDaggerComponent():APIComponent{
apiComponent = DaggerAPIComponent
.builder()
.aPIModule(APIModule(APIURL.BASE_URL))
.build()
return apiComponent
} }
In the above code how to access the function getMyComponent() globally in Kotlin.
Put getMyComponen() inside companion like #Md. Asaduzzaman answer or use applicationContext to access it like -
(application as MyRetroApplication).getMyComponent()
or
(applicationContext as MyRetroApplication).getMyComponent()
or
MyRetroApplication.ctx?.let{
(it as MyRetroApplication).getMyComponent() //by your companion app context
}
Approach-1:
Put getMyComponent() inside companion
companion object {
var ctx: Context? = null
private lateinit var apiComponent: APIComponent
fun getMyComponent(): APIComponent = apiComponent
}
And then from anywhere:
MyRetroApplication.getMyComponent()
Approach-2:
Change the type of ctx to MyRetroApplication instead of Context and then from anywhere:
MyRetroApplication.ctx.getMyComponent()
Approach-3:
Same as approach 2 but in a formal way. Create getInstance() inside companion and pass ctx (private)
companion object {
private lateinit var ctx: MyRetroApplication
fun getInstance(): MyRetroApplication {
return ctx
}
}
And then from anywhere:
MyRetroApplication.getInstance().getMyComponent()

Synchronized singleton in Kotlin

I am new to Kotlin. Still learning basic syntax.
I've heard about companion objects similar to static in Java. But don't know how to create synchronized singleton in Kotlin.
Just use
object Singleton {
// any members you need
}
It's already synchronized properly:
Object declaration's initialization is thread-safe.
Note that this doesn't guarantee calls on it thread-safe, but that's just as in Java.
There are also other ways, but those two are the most simple ones to generate a singleton class
Method 1- Kotlin Way
object SingletonObj {
init {
// do your initialization stuff
}
}
Method 2- Double Null Check Way in Kotlin
class SingletonObj {
private constructor(context: Context)
companion object {
#Volatile private var mInstance: SingletonObj? = null
public fun get(context: Context): SingletonObj =
mInstance ?: synchronized(this) {
val newInstance = mInstance ?: SingletonObj(context).also { mInstance = it }
newInstance
}
}
}
I think, little bit more research, and i found it . Here is how to do it . Please correct me if it can be done in better way.
companion object {
#Volatile private var INSTANCE: Singleton ? = null
fun getInstance(): Singleton {
if(INSTANCE == null){
synchronized(this) {
INSTANCE = Singleton()
}
}
return INSTANCE!!
}
}
Thread-safe and lazy:
class Singleton private constructor() {
companion object {
val instance: Singleton by lazy { Singleton() }
}
}
Double null check already implemented inside by lazy.

Static like methods in Android application with kotlin

I am trying to add a "static" method to my MyApplication class in kotlin
I have added (as a property) the variable :
private var context: Context? = null
in method:
override fun onCreate()
I added:
context = applicationContext
then I add a companion object like this
companion object {
#JvmStatic fun getMyApplicationContext(): Context?
{
return MyApplication().context
}
}
when I call this method from other parts of the application like
MyApplication.getMyApplicationContext() it always returns null. I have gleaned all this from several sources but I am not sure if it is anywhere near correct or not.
It sounds like you want a global application context object. Now casting aside my dislike for global variables, I think you are pretty close.
I think you just need to add the variable into the MyApplication classes companion object and use that directly. You only need the #JvmField annotation if you're going to access the field from Java.
class MyApplication {
companion object {
#JvmField
var context: Context? = null
// Not really needed since we can access the variable directly.
#JvmStatic fun getMyApplicationContext(): Context? {
return context
}
}
override fun onCreate() {
...
MyApplication.context = appContext
}
}

Kotlin singleton application class

On Android I want to make my application class a singleton.
Making it like this:
object MyApplication: Application(){}
won't work. The following error is thrown at runtime:
java.lang.IllegalAccessException: private com....is not accessible from class android.app.Instrumentation.
Doing this is also not possible:
class MyApp: Application() {
private val instance_: MyApp
init{
instance_ = this
}
override fun onCreate() {
super.onCreate()
if (BuildConfig.DEBUG) {
Timber.plant(Timber.DebugTree());
}
}
companion object{
fun getInstance() = instance_
}
}
How can I get an instance of my application class everywhere in my app? I would like to use MyApp.instance() instead of (applicationContext as MyApp).
Also an explanation why I want this: I have classes in my app. For example, a SharedPreference Singleton which is initialised with a context, and as it’s a singleton, it can't have arguments.
You can do the same thing you would do in Java, i.e. put the Application instance in a static field. Kotlin doesn't have static fields, but properties in objects are statically accessible.
class MyApp: Application() {
override fun onCreate() {
super.onCreate()
instance = this
}
companion object {
lateinit var instance: MyApp
private set
}
}
You can then access the property via MyApp.instance.
If you want to use it to access some static properties you have there: You will only have one instance of your Application, so simply use the name you gave to the class. Don't worry about it not being an actual singleton, you can use it the same way.
Example:
class MyApp : Application() {
companion object {
const val CONSTANT = 12
lateinit var typeface: Typeface
}
override fun onCreate() {
super.onCreate()
typeface = Typeface.createFromAsset(assets, "fonts/myFont.ttf")
}
}
Then you can use MyApp.CONSTANT and MyApp.typeface anywhere in your app.
-
If what you want is to use it as an application context you can create an extension property for Context:
val Context.myApp: MyApp
get() = applicationContext as MyApp
Then you can use myApp to get the the application context anywhere you have a context.
class AppController : Application() {
init {
instance = this
}
companion object {
private var instance: AppController? = null
fun applicationContext() : AppController {
return instance as AppController
}
}
override fun onCreate() {
super.onCreate()
}
}
You cannot do that because Android creates an Application instance using its parameterless constructor.
The problem you want to solve can be easily solved with DI. Just create instances with an injector so that the Context can be injected into objects as a dependency.

Categories

Resources