Dismissing Anko Dialog in onClickListener - android

I would like to dismiss Anko Dialog when pressing the button defined in my customLayout
val dialog = alert {
val view = layoutInflater.inflate(R.layout.match_stats, null)
val closeButton = view.findViewById<ImageButton>(R.id.closeButton)
closeButton.setOnClickListener { _ -> dialog.dismiss()}
customView = view
}
dialog.show()
I tried above code, unfortunately, I can’t get a reference to dialog in my onClickListener. Do you have any idea how to solve it?

You could declare variable before and assign null:
var dialog: DialogInterface? = null
dialog = alert {
val view = layoutInflater.inflate(R.layout.match_stats, null)
val closeButton = view.findViewById<ImageButton>(R.id.closeButton)
closeButton.setOnClickListener { _ -> dialog?.dismiss()}
customView = view
}.show()
Of course now your dialog variable is muttable and optional.

Related

Hiding SoftKeyboard when button inside dialog is clicked

I have custom dialog where inside its xml has a Submit button that whenever clicked, it should dismiss the softKeyboard.
I have the following code:
MainActivity.kt (Inherits from BaseActivity)
val updateDialog = Dialog(this, R.style.CustomDialog)
updateDialog.setContentView(R.layout.dialog_update)
val tvSubmitToFirestore = updateDialog.findViewById<HelveticaBoldTextView>(R.id.tv_update_item)
tvSubmitToFirestore.setOnClickListener {
hideKeyboard(currentFocus ?: View(this))
}
BaseActivity:
open class BaseActivity : AppCompatActivity() {
//hide keyboard when instance of an event
fun Context.hideKeyboard(view: View) {
val inputMethodManager = getSystemService(Activity.INPUT_METHOD_SERVICE) as InputMethodManager
inputMethodManager.hideSoftInputFromWindow(view.windowToken, 0)
}
}
But the keyboard remains on its position after clicking the said button.
Update:
//update item
val tvUpdate = showItemDialog.findViewById<HelveticaNormalTextView>(R.id.tv_update)
tvUpdate.setOnClickListener {
//close search dialog
showItemDialog.dismiss()
val updateDialog = Dialog(this, R.style.CustomDialog)
updateDialog.setContentView(R.layout.dialog_update)
updateDialog.setCancelable(false)
//spinner settings
val spinner = updateDialog.findViewById<Spinner>(R.id.sp_update)
populateSpinner(spinner, dialogProductCategory.text.toString())
//set default values of update dialog fields == the current product's properties(name, category, price)
val etProductName = updateDialog.findViewById<TextInputEditText>(R.id.et_update_product_name)
val etProductPrice = updateDialog.findViewById<TextInputEditText>(R.id.et_update_product_price)
etProductName.setText(dialogProdName.text.toString())
etProductPrice.setText(dialogProductPrice.text.toString())
//update item
val tvSubmitToFirestore = updateDialog.findViewById<HelveticaBoldTextView>(R.id.tv_update_item)
//TODO allow user to update an item with the same name provided that it should only exist once
// and must be unique
tvSubmitToFirestore.setOnClickListener {
// hideKeyboard(currentFocus ?: tvSubmitToFirestore)
hideKeyboard1(it, this#MainActivity)
val newProductName = etProductName.text.toString().trim()
val newProductCategory = spinner.selectedItem.toString().uppercase()
val newProductPrice = etProductPrice.text.toString().toDouble()
GlobalScope.launch {
validateProduct(newProductName, newProductCategory, newProductPrice)
}
//TODO : allow user to reuse the product name when updating
}
You can use the new WindowInsetsController library to hide and show keyboard. Use this function:
fun hideKeyboard(view: View, activity: Activity) {
WindowInsetsControllerCompat(activity.window, view).hide(WindowInsetsCompat.Type.ime())
}
In your case, you call use it like this:
tvSubmitToFirestore.setOnClickListener { view ->
hideKeyboard(view, this) // 'this' refers to MainActivity
}

Issue with custom dialog after removing Kotlin extension from the Android project

I have a custom dialog in my android project and it was working fine. After I removed kotlin extension from the project, I have modified my code as follows but there is some issue with the Views in the custom dialog. Codes etTitle.visibility = View.GONE and val newRequest = etDetail.text.toString() didn't work as I expected. It didn't hide the view etTitle and the value in the EditText etDetail is not picked also, it always returns emplty even when there is some value.
private lateinit var bindingDialogLayout: CustomDialogBinding
fun specialRequestDialog(currentRequest: String?) {
bindingDialogLayout = CustomDialogBinding.inflate(layoutInflater)
val dialogLayout = layoutInflater.inflate(R.layout.custom_dialog, null)
val etTitle = bindingDialogLayout.etTitle
val etDetail = bindingDialogLayout.etDetails
etTitle.visibility = View.GONE
etDetail.setText(currentRequest)
MaterialAlertDialogBuilder(this)
.setTitle("What is your special request?")
.setCancelable(false)
.setPositiveButton("Save") { dialog, which ->
val newRequest = etDetail.text.toString()
if (newRequest.isEmpty()) {
showErrorSnackBar("Type in if you have any special request, else hit cancel", true)
} else {
addButton.visibility = View.GONE
deleteButton.visibility = View.VISIBLE
}
}
.setNegativeButton("Cancel") { dialog, which ->
dialog?.dismiss()
}
.setView(dialogLayout)
.show()
}
You set the wrong view to the dialog.
Use this instead:
.setView(bindingDialogLayout.root)

Button in dialog always return null in onStart() in a Fragment

I have Dialog in Fragment. when I click on the OK button inside the dialog, I get null object reference error.
fun showDialog(){
//get Dialog : Numbers
val dialogView = LayoutInflater.from(context)
.inflate(R.layout.dialog_b, null)
//AlertDialog builder
val dialogBuilder = AlertDialog.Builder(context)
.setView(dialogView)
//Show Dialog
val alertDialog = dialogBuilder.show()
//setOnClickListener(android.view.View$OnClickListener)' on a null object reference
dialogView.btn_ok.setOnClickListener {
Log.d("Clicked", et_one.text.toString())
alertDialog.dismiss()
}
}
Logcat
java.lang.IllegalStateException: et_one must not be null at com.example.algorithmsapp.AlgorithmsFragments.BFragment$onStart$1$1.onClick(BFragment.kt:63)
You need to intialise Edittext here to fetch value from edittext. Add below line your code
var et_one: EditText
var btn_ok: Button
et_one= layoutInflateView.findViewById(R.id.et_one)
btn_ok= layoutInflateView.findViewById(R.id.btn_ok)
So Your Code Look Like This:
fun showDialog(){
//get Dialog : Numbers
val dialogView = LayoutInflater.from(context)
.inflate(R.layout.dialog_b, null)
//AlertDialog builder
val dialogBuilder = AlertDialog.Builder(context)
.setView(dialogView)
//Show Dialog
val alertDialog = dialogBuilder.show()
var et_one: EditText
var btn_ok: Button
et_one= layoutInflateView.findViewById(R.id.et_one)
btn_ok= layoutInflateView.findViewById(R.id.btn_ok)
//setOnClickListener(android.view.View$OnClickListener)' on a null object reference
dialogView.btn_ok.setOnClickListener {
Log.d("Clicked", et_one.text.toString())
alertDialog.dismiss()
}
}

why Dialog doesn't show in Kotlin?

I want to create a Dialog window when I click the Floating Action Button. But, when I click the button, just appears the Toast message.
This is what I've tried so far:
recyclerView.layoutManager = LinearLayoutManager(this, RecyclerView.VERTICAL, false)
val users = ArrayList<User>()
users.add(User("John", "USA"))
val adapter = CustomAdapter(users)
recyclerView.adapter = adapter
fab.setOnClickListener {
val dialog = Dialog(this)
Toast.makeText(this, "It's working...", Toast.LENGTH_LONG).show()
dialog.requestWindowFeature(Window.FEATURE_NO_TITLE)
dialog.setContentView(R.layout.dialog_add)
dialog.setTitle("Add person")
dialog.setCancelable(false)
val nameText = dialog.findViewById(R.id.name) as EditText
val addressText = dialog.findViewById(R.id.address) as EditText
val btnAdd = dialog.findViewById(R.id.btn_ok) as Button
val btnCancel = dialog.findViewById(R.id.btn_cancel) as Button
btnAdd.setOnClickListener{
users.add(User(nameText.text.toString(), addressText.text.toString()))
adapter.notifyDataSetChanged()
dialog.dismiss()
}
btnCancel.setOnClickListener {
dialog.dismiss()
}
}
}
How can I change the code so it show the Dialog Window when I click the FAB?
UPDATE:
You guys're right! It worked just fine after I put dialog.show(). Thank you.
You forgot to invoke show() on dialog.
dialog.show()
You need to call dialog.show(). Just call it anywhere below dialog.setCancelable(false).
After create dialog , we need to call show method to show dialog on screen
Add This line after create dialog dialog.show()
Please replace or add this code
recyclerView.layoutManager = LinearLayoutManager(this, RecyclerView.VERTICAL, false)
val users = ArrayList<User>()
users.add(User("John", "USA"))
val adapter = CustomAdapter(users)
recyclerView.adapter = adapter
fab.setOnClickListener {
val dialog = Dialog(this)
Toast.makeText(this, "It's working...", Toast.LENGTH_LONG).show()
dialog.requestWindowFeature(Window.FEATURE_NO_TITLE)
dialog.setContentView(R.layout.dialog_add)
dialog.setTitle("Add person")
dialog.setCancelable(false)
val nameText = dialog.findViewById(R.id.name) as EditText
val addressText = dialog.findViewById(R.id.address) as EditText
val btnAdd = dialog.findViewById(R.id.btn_ok) as Button
val btnCancel = dialog.findViewById(R.id.btn_cancel) as Button
btnAdd.setOnClickListener{
users.add(User(nameText.text.toString(), addressText.text.toString()))
adapter.notifyDataSetChanged()
dialog.dismiss()
}
btnCancel.setOnClickListener {
dialog.dismiss()
}
//add this line
//Call show() method to show dialog
dialog.show()
}
}
You have to invoke show() like the following.
//...
dialog.setTitle("Add person")
dialog.setCancelable(false)
// ...
btnAdd.setOnClickListener{
//...
}
btnCancel.setOnClickListener {
dialog.dismiss()
}
//show dialog adding below line.
dialog.show();

Passing information between two alert dialogs

ImageView in first alert dialog opens second dialog to change an imageResource of the ImageView in the first dialog. However I don't know how to make connection between two alert dialogs
Both have different xml layouts, so I assume that in second dialog I should make a reference to the layout of the first dialog
private fun editItemDialog() {
val dialogBuilder1 = AlertDialog.Builder(this)
val inflater = this.layoutInflater
val dialogView = inflater.inflate(R.layout.edit_dialog, null)
dialogBuilder1.setView(dialogView)
var editIconButton = dialogView.findViewById<View>(R.id.editIcon) as ImageView
editIconButton.setOnClickListener{
showIconDialog()
}
dialogBuilder1.setTitle("Edit mode")
dialogBuilder1.setPositiveButton("Save") { _, _ ->
//sth
}
dialogBuilder1.setNegativeButton("Cancel") { _, _ ->
//sth
}
val b = dialogBuilder1.create()
b.show()
}
private fun showIconDialog() {
val dialogBuilder = AlertDialog.Builder(this)
val inflater = this.layoutInflater
val dialogView = inflater.inflate(R.layout.icons, null)
dialogBuilder.setView(dialogView)
//examplary two icons to select
var travelRB = dialogView.findViewById<View>(R.id.travel) as RadioButton
var travRB = dialogView.findViewById<View>(R.id.travel) as RadioButton
dialogBuilder.setTitle("Icon dialog")
dialogBuilder.setMessage("Select an icon")
dialogBuilder.setPositiveButton("Save") { _, _ ->
//here I would like to change an icon of the ImageView, for example:
editIconButton.setImageResource(R.id.travel)
dialogBuilder.setNegativeButton("Cancel") { _, _ ->
//sth
}
val b = dialogBuilder.create()
b.show()
}
You can add a callback to the second dialog
fun showIconDialog(callback : (Drawable) -> Unit) {
//code
callback.invoke(someDrawable)
}
And on the first one you just do this:
showIconDialog() { someDrawable ->
//code to change the layout src icon
}

Categories

Resources