Get string extra from activity Kotlin - android

I want to get a string extra in another activity from an intent. This is the way to create my intent
val intent = Intent(this, Main2Activity::class.java)
intent.putExtra("samplename", "abd")
startActivity(intent)
How can i get the value of this intent in the another activity

Answer found, in the next activity, you have to do this to get the string:
val ss:String = intent.getStringExtra("samplename").toString()

LOAD
val value: String = txt_act_main.text.toString() // or just your string
val intent = Intent(this, SecondActivity::class.java)
intent.putExtra("value", value)
startActivity(intent)
//option 2 all inner classes should be implemented to Serializable
getIntent().putExtra("complexObject", clickedTitle);
GET
var bundle :Bundle ?=intent.extras
var message = bundle!!.getString("value") // 1
var strUser: String = intent.getStringExtra("value") // 2
Toast.makeText(this, message, Toast.LENGTH_SHORT).show()
//option 2
var myProg = intent.getSerializableExtra("complexObject") as MenuModel
IMPLICIT (To Share with other apps)
val value: String = txt_act_main.text.toString()
var intent = Intent()
intent.action = Intent.ACTION_SEND
intent.putExtra(Intent.EXTRA_TEXT, value)
intent.type="text/plain"
startActivity(Intent.createChooser(intent,"Share to "))

Can use this code :
val bundle = intent.extras
var sampleName: String = ""
if (bundle != null) {
sampleName = bundle.getString("samplename")
}

you can check if the intent value is null or not
val bundle :Bundle ?=intent.extras
if (bundle!=null){
val message = bundle.getString("object") // 1
Toast.makeText(this, message, Toast.LENGTH_SHORT).show()
}

In Main2Activity you can have your code like this :
val intent = getIntent();
val myValue = intent.getStringExtra("key")
Log.d(TAG,"myValue"+myValue)

The accepted answer doesn't solve the case where the intent is not there. Because when the key is not exist in intent, getStringExtra() will give you null even its signature indicates a String rather than a String?.
You can use val text:String = intent.getStringExtra(intentKey) ?: "" to make sure no NPE happened.
But one more answer here:
This is for the case where, you try to retrieve the string from intent, if the value is there, we get the value, otherwise, it will go back to the previous screen because this intent is critical. Something wrong will happen but we don't want to crash the activity.
private fun getStringFromIntentOrShowError(intentKey: String):String {
val text:String? = intent.getStringExtra(intentKey)
if (text == null) {
showDialog(
"Error",
"No $intentKey found"
) {
it.dismiss()
finish()
}
return ""
}
return text
}
// I use anko to show a dialog, you can use your one.
private fun showDialog(
title:String,
message:String,
yesButtonCallback: (d:DialogInterface) -> Unit
) {
alert(message, title){ yesButton{
yesButtonCallback(it)
} }.show()
}
Then you can use it like this:
val text:String = getStringFromIntentOrShowError("asd")
and text will always have a value

You can use this simple Kotlin Extension
fun Intent.getData(key: String): String {
return extras?.getString(key) ?: "intent is null"
}
this Extension checks if the intent value is null, if the value is null it will return intent is null otherwise, it will return the value
use it like this
val username = intent.getData("username")

First you need to initialize the intent variable.
Then take out the data like we do in java :)
val intent: Intent = intent
var data = intent.getStringExtra("mydata")

Related

SharedPreferences not working when Activity is started from somewhere else?

I have a ThreadActivity with two functions, saveContacts and loadContacts. They both use sharedpreferences and Gson to save an ArrayList consisting of Objects called SimpleContacts. Somehow it cannot retrieve data from sharedpreferences once I start the Activity from somewhere else. (I tried loading instantly after saving and that works, but not if I close the Activity and re-open it)
The save function:
private fun saveContact() {
val gson = Gson()
val sharedPreferences = PreferenceManager.getDefaultSharedPreferences(applicationContext)
try {
val editor = sharedPreferences.edit()
val json = gson.toJson(participants)
editor.putString(threadId.toString()+"_Contact", json)
editor.apply()
} catch(e: Exception) {
e.printStackTrace()
}
}
The load function:
private fun loadContact() {
val gson = Gson()
val sharedPreferences = PreferenceManager.getDefaultSharedPreferences(applicationContext)
val type = object : TypeToken<ArrayList<SimpleContact?>?>() {}.type
try {
val json = sharedPreferences.getString(threadId.toString()+"_Contact", "")
participants = gson.fromJson(json, type)
} catch(e: Exception) {
e.printStackTrace()
}
}
I have 2 Activities that can open this ThreadActivity, if I start it from the same one, it all works perfectly fine. But when I use the other Activity to start it, the sharedPrefs are empty.
Launch Activity that works (I don't know if its because its the way the Intent is build so I will write them both here):
private fun launchThreadActivity(phoneNumber: String, name: String) {
hideKeyboard()
val text = intent.getStringExtra(Intent.EXTRA_TEXT) ?: ""
val numbers = phoneNumber.split(";").toSet()
val number = if (numbers.size == 1) phoneNumber else Gson().toJson(numbers)
Intent(this, ThreadActivity::class.java).apply {
putExtra(THREAD_ID, getThreadId(numbers))
putExtra(THREAD_TITLE, name)
putExtra(THREAD_TEXT, text)
putExtra(THREAD_NUMBER, number)
if (intent.action == Intent.ACTION_SEND && intent.extras?.containsKey(Intent.EXTRA_STREAM) == true) {
val uri = intent.getParcelableExtra<Uri>(Intent.EXTRA_STREAM)
putExtra(THREAD_ATTACHMENT_URI, uri?.toString())
} else if (intent.action == Intent.ACTION_SEND_MULTIPLE && intent.extras?.containsKey(Intent.EXTRA_STREAM) == true) {
val uris = intent.getParcelableArrayListExtra<Uri>(Intent.EXTRA_STREAM)
putExtra(THREAD_ATTACHMENT_URIS, uris)
}
startActivity(this)
}
}
Start Activity that does not work:
Intent(this, ThreadActivity::class.java).apply {
putExtra(THREAD_ID, (it as Conversation).threadId)
putExtra(THREAD_TITLE, it.title)
putExtra("fromMain", true)
startActivity(this)
}
Nevermind, it was my mistake.
When saveContact was called the threadId was not initialized yet. So basically the keys were always different.

Retrieving intent extras from widget

I'm making a widget for my WebView app, and it's got a list of buttons on it. Currently, It's firing an intent whenever their pressed. In that intent, I'm putting some string extra's, but when the onNewIntent receives the intent, the value for the extra is NULL. So I'm stuck on receiving the actual string extra.
Here's the code on my list provider:
override fun getViewAt(positionIndexNum: Int): RemoteViews {
........
val extrasObj = Bundle()
extrasObj.putString("shortcutUrl", listViewUrlArr[positionIndexNum]) // I've tried hardcoding this part and it still returns null.
extrasObj.putString("shortcutJs", listViewJsArr[positionIndexNum])
extrasObj.putString("shortcutId", listViewIdArr[positionIndexNum])
val fillInIntentObj = Intent()
fillInIntentObj.putExtras(extrasObj)
viewObj.setOnClickFillInIntent(listViewItemId, fillInIntentObj)
return viewObj
}
Here's the code from the onNewIntent function:
override fun onNewIntent(intentObj: Intent) {
super.onNewIntent(intentObj)
val bundle = intentObj.extras
if (bundle != null) {
for (key in bundle.keySet()) {
Log.e("TAG", key + " : " + if (bundle[key] != null) bundle[key] else "NULL")
}
}
.....
}
That outputs in the logcat:
shortcutUrl : NULL
shortcutId : NULL
shortcutJs : NULL
I've also tried: intentObj.getStringExtra("shortcutId") which still returns NULL
EDIT:
I also have this PendingIntent code in the updateAppWidget function:
val clickIntent = Intent(contextObj, MainActivity::class.java)
val clickPI = PendingIntent.getActivity(contextObj, 0,
clickIntent, PendingIntent.FLAG_IMMUTABLE or PendingIntent.FLAG_UPDATE_CURRENT);
viewsObj.setPendingIntentTemplate(R.id.widget_list, clickPI)
I finally found a fix for this, I'm not sure how it really works but I changed:
PendingIntent.FLAG_IMMUTABLE
to
PendingIntent.FLAG_MUTABLE
in the PendingIntent. Hopefully this helps someone else!
Here is a full answer which I posted on another question:
Application widget with bundle?
Read the Intent in MyActivity:
private fun readIntent() {
val intentExtras: Bundle? = intent.extras
intentExtras?.let {
val intentMessage: String? = intentExtras.getString(APPWIDGET_INTENT_MESSAGE)
println(intentMessage)
}
}
Here is a method in Kotlin to get pending intent to open your activity
fun getPendingIntentMyActivity(context: Context, message: String): PendingIntent {
val intent = Intent(context, MyActivity::class.java)
intent.action = APPWIDGET_INTENT
intent.data = Uri.parse(intent.toUri(Intent.URI_INTENT_SCHEME))
val extras = Bundle().apply {
putString(APPWIDGET_INTENT, APPWIDGET_OPEN_APP)
putString(APPWIDGET_INTENT_MESSAGE, message)
}
intent.putExtras(extras)
return PendingIntent.getActivity(context, 0, intent, FLAG_UPDATE_CURRENT or FLAG_IMMUTABLE)
}
Then set it in the Widget
remoteViews.setOnClickPendingIntent(R.id.rootView, getPendingIntentMyActivity(context, "Hello World")

Unable to send string from one activity to another (third activity) in Android Studio using Kotlin

So I have three activities for my app. I am taking the username from the user(on Main Screen) and I want to show it to the last screen (Result Screen). I have tried using string constants and then sending the string value using Intent from one activity to the second and to the third one. But I am not able to see the name on the Result Screen. What is that I am doing wrong ?
I am following all the rules and the app is working fine without errors but the username is not been shown to the screen.
In Constants.kt
const val USER_NAME: String = "user_name"
In MainActivity.kt
val nameEditText = findViewById<TextView>(R.id.name_edit_text)
val name = nameEditText.text.toString()
val Intent = Intent(this, QuizQuestionActivity::class.java)
intent.putExtra(Constants.USER_NAME, name)
startActivity(intent)
In QuizQuestionActivity.kt
private var mUsername: String? = null
mUsername = intent.getStringExtra(CONSTANTS.USER_NAME)
val intent = Intent(this, ResultActivity::class.java)
intent.putExtra(Constants.USER_NAME, mUsername)
startActivity(intent)
In ResultActivity.kt
val username = intent.getStringExtra(Constants.USER_NAME)
tv_name.text = username
This is the whole code I am trying to execute. Anybody please help!!
I have two Observations in your code snippet
1)Do you have two Constant files?
Constant.kt
CONSTANT.kt
As in your QuizQuestionActivity, there is a line
mUsername = intent.getStringExtra(CONSTANTS.USER_NAME)
No matter the file that you refer to, the USER_NAME field string values should be the same.
2)Another thing in MainActivity
val Intent = Intent(this, QuizQuestionActivity::class.java)
intent.putExtra(Constants.USER_NAME, name)
startActivity(intent)
Here variable that you use is "Intent"
val Intent = Intent(this, QuizQuestionActivity::class.java)
and you pass "intent" for starting activity
intent.putExtra(Constants.USER_NAME, name)
startActivity(intent)
Try this
In MainActivity:
val nameEditText = findViewById<TextInputEditText>(R.id.name_edit_text)
val name = nameEditText.text.toString()
val intent = Intent(this, QuizQuestionActivity::class.java)
intent.putExtra(Constants.USER_NAME, name)
startActivity(intent)
In QuizQuestionActivity:-
var mUsername: String? = null
mUsername = intent.getStringExtra(Constants.USER_NAME)
val intent = Intent(this, ResultActivity::class.java)
intent.putExtra(Constants.USER_NAME, mUsername)
startActivity(intent)
In ResultActivity:-
val username = intent.getStringExtra(Constants.USER_NAME)
tv_name.text = username

how to access the extra data in the returned intent and update TextView in Android

I am trying to update the value in the First activity. For this. I have passed parameters from first Activity to second with intent and update text input. Now I want to pass the updated value to the first Activity and update the specific value. I try to send data inside saveButton onClick with setResult() method. And get value in FirstActivity with onActivityResult() method. But it does not update the value. Can you please check where I did a mistake?
First Activity
class ShowProfileActivity : AppCompatActivity() {
private lateinit var fullnameTv: TextView
private lateinit var nicknameTv: TextView
private lateinit var locationTv: TextView
private lateinit var emailTv: TextView
private lateinit var bioTv: TextView
// todo load from sp
private val mockUser: User? = User("TestName", "test", "test#gmail.com", "Italy", "this is a mocked bio")
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_show_profile)
fullnameTv = findViewById(R.id.asp_user_name_tv)
nicknameTv = findViewById(R.id.asp_user_nickname_tv)
locationTv = findViewById(R.id.asp_user_location_tv)
emailTv = findViewById(R.id.asp_user_email_tv)
bioTv = findViewById(R.id.asp_user_bio_tv)
// init views with user data
fullnameTv.text = mockUser?.fullname
nicknameTv.text = mockUser?.nickname
locationTv.text = mockUser?.location
emailTv.text = mockUser?.email
bioTv.text = mockUser?.bio
var editButton = findViewById<ImageButton>(R.id.editBtn);
editButton.setOnClickListener {
editProfile();
}
}
fun editProfile() {
val intent = Intent(this#ShowProfileActivity,EditProfileActivity::class.java)
if (mockUser != null) {
intent.putExtra("group23.lab1.user_fullname", mockUser.fullname)
intent.putExtra("group23.lab1.user_nickname", mockUser.nickname)
intent.putExtra("group23.lab1.user_location", mockUser.location)
intent.putExtra("group23.lab1.user_email", mockUser.email)
intent.putExtra("group23.lab1.user_bio", mockUser.bio)
}
startActivityForResult(intent, 1)
startActivity(intent)
}
override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent?) {
super.onActivityResult(requestCode, resultCode, data)
if(resultCode == Activity.RESULT_OK){
if (data != null) {
if (mockUser != null) {
mockUser.fullname= data.getStringExtra("group23.lab1.user_fullname").toString() //not updated
}
}
}
}
override fun onCreateOptionsMenu(menu: Menu?): Boolean {
menuInflater.inflate(R.menu.show_profile_menu, menu)
return true
}
override fun onOptionsItemSelected(item: MenuItem): Boolean {
return when (item.itemId) {
R.id.menu_show_profile_edit -> {
/*
TODO start edit profile activity (check activity name)
val intent = Intent(this, com.group23.lab1.EditProfileActivity::class.java).apply {
if (mockUser != null) {
putExtra("group23.lab1.user_fullname", mockUser.fullname)
putExtra("group23.lab1.user_nickname", mockUser.nickname)
putExtra("group23.lab1.user_location", mockUser.location)
putExtra("group23.lab1.user_email", mockUser.email)
putExtra("group23.lab1.user_bio", mockUser.bio)
}
}
startActivityForResult(intent)
*/
Toast.makeText(this, "OPEN EDIT PROFILE", Toast.LENGTH_SHORT).show()
true
}
else -> super.onOptionsItemSelected(item)
}
}
}
Second Activity
class EditProfileActivity : AppCompatActivity() {
private lateinit var fullnameTv: TextView
private lateinit var nicknameTv: TextView
private lateinit var locationTv: TextView
private lateinit var emailTv: TextView
private lateinit var bioTv: TextView
override fun onCreate(savedInstanceState: Bundle?) {
super.onCreate(savedInstanceState)
setContentView(R.layout.activity_edit_profile)
val intent = intent
fullnameTv = findViewById(R.id.asp_user_name_tv)
nicknameTv = findViewById(R.id.asp_user_nickname_tv)
locationTv = findViewById(R.id.asp_user_location_tv)
emailTv = findViewById(R.id.asp_user_email_tv)
bioTv = findViewById(R.id.asp_user_bio_tv)
// ageTv = findViewById(R.id.asp_user_age_tv)
fullnameTv.text = intent.getStringExtra("group23.lab1.user_fullname")
nicknameTv.text = intent.getStringExtra("group23.lab1.user_nickname")
locationTv.text = intent.getStringExtra("group23.lab1.user_location")
emailTv.text = intent.getStringExtra("group23.lab1.user_email")
bioTv.text = intent.getStringExtra("group23.lab1.user_bio")
var sharedPreferences = getSharedPreferences("SHARED_PREF", Context.MODE_PRIVATE)
var editor = sharedPreferences.edit()
var saveButton = findViewById<Button>(R.id.btnSave)
val name = sharedPreferences.getString("group23.lab1.user_fullname", null)
val nickName = sharedPreferences.getString("group23.lab1.user_nickname", null)
val location = sharedPreferences.getString("group23.lab1.user_location", null)
val email = sharedPreferences.getString("group23.lab1.user_emai", null)
val bio = sharedPreferences.getString("group23.lab1.user_bio", null)
fullnameTv.text = name
nicknameTv.text = nickName
locationTv.text = location
emailTv.text = email
bioTv.text = bio
saveButton.setOnClickListener {
val name = fullnameTv.text.toString()
val nickName = nicknameTv.text.toString()
val location = locationTv.text.toString()
val email = emailTv.text.toString()
val bio = bioTv.text.toString()
// var age = ageTv.text.toString()
editor.apply {
putString("group23.lab1.user_fullname", name)
putString("group23.lab1.user_nickname", nickName)
putString("group23.lab1.user_location", location)
putString("group23.lab1.user_email", email)
putString("group23.lab1.user_bio", bio)
apply();
setResult(RESULT_OK, intent);
finish();
}
}
}
override fun onCreateOptionsMenu(menu: Menu?): Boolean {
menuInflater.inflate(R.menu.show_profile_menu, menu)
return true
}
override fun onOptionsItemSelected(item: MenuItem): Boolean {
return when (item.itemId) {
R.id.menu_show_profile_edit -> {
Toast.makeText(this, "OPEN EDIT PROFILE", Toast.LENGTH_SHORT).show()
true
}
else -> super.onOptionsItemSelected(item)
}
}
}
You start your activity 2 times:
startActivityForResult(intent, 1)
startActivity(intent)
The crux of your problem is that you're passing back the second activity's original intent, which has the original values that came from the first activity. You need to pass back a new intent with new data.
// Return a NEW intent with NEW data, not this Activity's current intent
val resultIntent = Intent().putString("group23.lab1.user_fullname", name)
setResult(RESULT_OK, resultIntent);
Beyond that, here's a few unsolicited suggestions:
1 - Remove redundant startForActivity:
startActivityForResult(intent, 1)
startActivity(intent) // <- Delete this
2 - Check for the same intent code in onActivityResult. This ensures you're handling the correct result. Doesn't matter in your case as you only have one result, but it's good to build that habit and be correct. So since you started with requestCode 1, check for that same value in the result:
override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent?) {
super.onActivityResult(requestCode, resultCode, data)
if(resultCode == Activity.RESULT_OK && requestCode == 1) { // Check for same request code
if (data != null) {
if (mockUser != null) {
mockUser.fullname= data.getStringExtra("group23.lab1.user_fullname").toString() //not updated
}
}
}
}
3 - Saving a local val named "intent" to shadow the activity's own "intent" property is redundant.
val intent = intent // Delete this - it's pointless
4 - You are setting values in the second activity twice - from the intent and then overwriting that with shared preferences. Pick one.
// Setting values here from Intent ...
fullnameTv.text = intent.getStringExtra("group23.lab1.user_fullname")
nicknameTv.text = intent.getStringExtra("group23.lab1.user_nickname")
locationTv.text = intent.getStringExtra("group23.lab1.user_location")
emailTv.text = intent.getStringExtra("group23.lab1.user_email")
bioTv.text = intent.getStringExtra("group23.lab1.user_bio")
var sharedPreferences = getSharedPreferences("SHARED_PREF", Context.MODE_PRIVATE)
var editor = sharedPreferences.edit()
var saveButton = findViewById<Button>(R.id.btnSave)
val name = sharedPreferences.getString("group23.lab1.user_fullname", null)
val nickName = sharedPreferences.getString("group23.lab1.user_nickname", null)
val location = sharedPreferences.getString("group23.lab1.user_location", null)
val email = sharedPreferences.getString("group23.lab1.user_emai", null)
val bio = sharedPreferences.getString("group23.lab1.user_bio", null)
// ... get completely overwritten here ... so setting them above is pointless
fullnameTv.text = name
nicknameTv.text = nickName
locationTv.text = location
emailTv.text = email
bioTv.text = bio
5 - Related to the above, you seem to be mixing and matching intents and shared preferences. Unless you actually need this data to persist to disk as "preferences", you should remove the shared preferences logic which is confusing things. On the other hand, if you do need to persist the data, then you can remove the passing of data via intents, as it ends up being redundant.
For example, your activity result could read from the shared preferences instead:
override fun onActivityResult(requestCode: Int, resultCode: Int, data: Intent?) {
super.onActivityResult(requestCode, resultCode, data)
if(resultCode == Activity.RESULT_OK && requestCode == 1) { // Check for same request code
if (mockUser != null) {
var sharedPreferences = getSharedPreferences("SHARED_PREF", Context.MODE_PRIVATE)
mockUser.fullname= sharedPreferences.getString("group23.lab1.user_fullname", "")
}
}
}
Please note that if you chose to use preferences, you should use Editor.commit() which is synchronous instead of Editor.apply() which is asynchronous, to ensure you values are ready to be read immediately by the next activity.

How can I update a var inside a whole kotlin class through a method and then retrieve it updated with another method call

I've written a kotlin class with an overridden fun and a fun to update a var into the class scope (I'm tragically new to Kotlin!)
class mySampleClass: sampleReference(){
var varToBeUpdated:String = "my string" //var in class scope to be updated
fun updateMyVar(gotString:String){
//I tried this, it didn't work
this.varToBeUpdated = gotString
// also this didn't work
varToBeUpdated = gotString
}
override fun sample(context: Context, intent: Intent){
//here i need my varToBeUpdated with new string
runSomeThing(varToBeUpdated)
//some work to be done here
}
}
In the place where I call the methods i do:
myObject.updateMyVar("new string")
myObject.sample()
I wonder how I can update the var i need, since I cannot add new args in the "fun sample", due to the fact it's overriding a class method
Thanks in advance, best regards to everyone :)
UPDATE: add my actual code, due to the fact that the class it seems unable to keep on the right updated value as i call the overrid method:
Here is my BroadcastReceiver, to check whem download is completed and them perform some action
class DownloadBroadcastManager: BroadcastReceiver() {
var myClassFilename:String = "default"
var myClassExtension:String = ".default"
override fun onReceive(context: Context, intent: Intent) {
val action = intent.action
if (DownloadManager.ACTION_DOWNLOAD_COMPLETE == action) {
//Show a notification
// here there's a log to check if var are updated
println("myTag - variables $myClassFilename, $myClassExtension")
Toast.makeText(context, "Download of $myClassFilename$myClassExtension completed", Toast.LENGTH_LONG).show()
// richiama azioni come player o display image o altro?
//player
var uri = Uri.parse (Environment.getExternalStorageDirectory().getPath() + "/Download/$myClassFilename$myClassExtension") //myClassExtension is ".mp3", dot is included, however it seems class is re-intialized as i call the method
println("myTag - uri: $uri")
println("myTag - context: $context")
var mPlayer = MediaPlayer() // I added this declaration (that's be re-done later) cause I had a problem in making the player running (of course giving it a valid path to a valid file). Now this is "junk code"
mPlayer.stop()
mPlayer.reset()
mPlayer.release()
mPlayer = MediaPlayer.create(context, uri) // here there's the proper declaration + initialization
mPlayer.start()
}
}
}
Here is the part from my DownloaderClass...
var brReceiver = DownloadBroadcastManager()
// shows when download is completed
println("myTag - ${brReceiver.myClassFilename}, ${brReceiver.myClassExtension}: originals") //here shows the default: it's right
val intent = Intent(context, MainActivity::class.java)
brReceiver.myClassFilename = myTitle // inject filename
brReceiver.myClassExtension = ".mp3" // inject file extension
println("myTag - ${brReceiver.myClassFilename}, ${brReceiver.myClassExtension}: modified") // here it shows my class property as correctly updated
brReceiver.onReceive(context, intent) // here, as calling the override fun, it get back to default value of the property
You can just do the following:
Get rid of updateMyVar function:
class MySampleClass: SampleReference(){
var varToBeUpdated:String = "my string" //var in class scope to be updated
override fun sample(context: Context, intent: Intent){
//here i need my varToBeUpdated with new string
runSomeThing(varToBeUpdated)
//some work to be done here
}
}
Update varToBeUpdated property directly:
val myObject = MySampleClass()
myObject.varToBeUpdated = "new string"
myObject.sample()
Update:
If you call brReceiver.onReceive(...) the values in DownloadBroadcastManager are updated. But you shouldn't do that. The Android framework calls it for you. And when it happens new instance of DownloadBroadcastManager class is created and default values are set. We use Intents to pass data to BroadcastReceiver, e.g. call intent.putExtra("filename", "yourFileName") when you create BroadcastReceiver, and call intent.getStringExtra("filename") in onReceive() function to get the value. Here is how to pass/get data to/from BroadcastReceiver
Accoirding to kotlin's docs you can define getter and setter methods for any variable like this way:
var <propertyName>[: <PropertyType>] [= <property_initializer>]
[<getter>]
[<setter>]
in your case it's might be something like:
var varToBeUpdated:String = "my string"
get() = field
set(value) { field = value }
Ok, at first thank to M.SamiAzar and especially to Sergey, for their answers and for the unbelievable patience!
Unluckily it seems that, as it is re-initialized by the framework, the BroadcastReceiver also loses any extras that i previously put in the Intent variable.
I finally solved this issue, letting me to retrieve the strings I needed, only writing a line of text into a file in the internal storage and retrieving it in my BroadcastReceiver class.
Here's the code:
this is my "onReceive" methond in BroadcastReceiver class
override fun onReceive(context: Context, intent: Intent) {
val action = intent.action
Log.i("Receiver", "myTag - Broadcast received: " + action)
var myFilename = "deafult"
if (DownloadManager.ACTION_DOWNLOAD_COMPLETE == action) {
// read the previously created file from internal storage
var fileInputStream: FileInputStream? = null
fileInputStream = context.openFileInput("storeDownloadedData")
var inputStreamReader: InputStreamReader = InputStreamReader(fileInputStream)
val bufferedReader: BufferedReader = BufferedReader(inputStreamReader)
// here setting string var and stringbuilder var to catch the text updated outside the while loop
val stringBuilder: StringBuilder = StringBuilder()
var text: String? = null
var sumText:java.lang.StringBuilder? = null
// while loop for reading the file line by line (in this case the file can contains just one line a time)
while ({ text = bufferedReader.readLine(); text }() != null) {
sumText = stringBuilder.append(text)
}
// convert stringBuilder to a list of string splitting the original string obtained by file reading
var secondText:String = "default"
println("myTag - text: $text, $sumText")
if (sumText != null){
secondText = sumText.toString()
var listFromText = secondText.split(",")
// set filename to the title contained in the string
myFilename = listFromText[0]
}
//player - finally play the file retrieving the title from the file in internal storage
var uri = Uri.parse (Environment.getExternalStorageDirectory().getPath() + "/Download/$myFilename.mp3")
println("myTag - uri: $uri")
println("myTag - context: $context")
var mPlayer = MediaPlayer.create(context, uri)
mPlayer.start()
}
this is the code added in my DownloadManager class:
// strore into an internal storage file the data of title and extensione for the file's gonna be downloaded
val myStoredFile:String = "storeDownloadedData"
val data:String = "$myTitle,.mp3"
val fileOutputStream: FileOutputStream
// write file in internal storage
try {
fileOutputStream = context.openFileOutput(myStoredFile, Context.MODE_PRIVATE)
fileOutputStream.write(data.toByteArray())
}catch (e: Exception){
e.printStackTrace()
}
// it notifies when download is completed
val intent = Intent(context, MainActivity::class.java)
var brReceiver = DownloadBroadcastManager()
I do not know if this is "ortodox", but it seems to work atm
:)

Categories

Resources