Home > Blockchain >  Kotlin: Buttons inside a fragment needed to be clicked twice before starting the activity. How can I
Kotlin: Buttons inside a fragment needed to be clicked twice before starting the activity. How can I

Time:12-06

newbie here! I'm having a hard time learning the life cycle of fragments and I'm stuck in this problem. If I run this on the emu, the fragment is showing on the activity but the button inside the fragment needs to be clicked twice to run the destination activity.

FragmentSetting.kt:

    class FragmentSetting : Fragment(), View.OnClickListener {
    override fun onCreate(savedInstanceState: Bundle?) {
        super.onCreate(savedInstanceState)
        }

    override fun onCreateView(
        inflater: LayoutInflater,
        container: ViewGroup?,
        savedInstanceState: Bundle?
    ): View? {
        val view: View = inflater!!.inflate(R.layout.fragment_main_setting, container, false)
        val btnLogout: Button = view.findViewById(R.id.btn_logout)
        val btnArticle: Button = view.findViewById(R.id.btn_art)
        btnLogout.setOnClickListener(this)
        btnArticle.setOnClickListener(this)
        return view
    }

    companion object {
        fun newInstance(): FragmentSetting {
            return FragmentSetting()
        }
    }

    override fun onClick(v: View?) {
        when (v?.id) {
            R.id.btn_logout -> {
                btn_logout.setOnClickListener {
                    Toast.makeText(getContext(), "Signed Out.", Toast.LENGTH_SHORT).show()
                    FirebaseAuth.getInstance().signOut()
                    val intent = Intent(activity, SignInActivity::class.java)
                    startActivity(intent)
                }
            }

            R.id.btn_art -> {
                btn_art.setOnClickListener {
                    Toast.makeText(getContext(), "Hello World", Toast.LENGTH_SHORT).show()
                    val intent = Intent(activity, ArticleActivity::class.java)
                    startActivity(intent)
                }
            }
        }
    }
}

CodePudding user response:

You are setting the Fragment class itself as the listener to both buttons when the view is created. That would be an acceptable place to do it.

However, your listener function doesn't perform your desired action of your button. Instead, it is setting a new listener for each button. So the first time they are clicked, they get their new listener. It is only in that inner secondary listener that you are going to another activity, so that's why it's taking two clicks.

You need to directly do your action instead of wrapping the action inside setting another listener. By the way, the view passed to a click listener is never null, so you can remove the ?'s.

override fun onClick(v: View) {
    when (v.id) {
        R.id.btn_logout -> {
            Toast.makeText(getContext(), "Signed Out.", Toast.LENGTH_SHORT).show()
            FirebaseAuth.getInstance().signOut()
            val intent = Intent(activity, SignInActivity::class.java)
            startActivity(intent)
        }
        R.id.btn_art -> {
            Toast.makeText(getContext(), "Hello World", Toast.LENGTH_SHORT).show()
            val intent = Intent(activity, ArticleActivity::class.java)
            startActivity(intent)
        }
    }
}

CodePudding user response:

there are two different things number one if you are implement View.OnClickListener interface so defiantly you use onclick call back method they will fire every time when ever you click it mean in onclick method execute piece code write in onclick method so in your current code first click they will set setOnclicklistener and then next time you click then it will work as per expected.
so simple is that you directly execute code with in curls braces don't need to set setOnClickListener. For Example :

R.id.btn_art -> { Toast.makeText(getContext(), "Hello World", Toast.LENGTH_SHORT).show() val intent = Intent(activity, ArticleActivity::class.java) startActivity(intent) }

second thing is that you set setOnClickOnClickListenre in your onCreateView and don't implement clicklistenere. For Example:

btn_logout.setOnClickListener { Toast.makeText(getContext(), "Signed Out.", Toast.LENGTH_SHORT).show() FirebaseAuth.getInstance().signOut() val intent = Intent(activity, SignInActivity::class.java) startActivity(intent) }

but they best practice you can handle click listener in onclick method as per view architecture.

  • Related