0

I'm trying to instantiate a large number (~600) onclick listeners for a large grid of buttons. I've created a function that stores the id's of each square in a list called squareList, in which each square is assigned a string value id (sq000, sq001, sq002)

I'd like to create a for loop that pulls the id of each square and then creates an onClicklistener, sort of like:

fun createSquareListeners(listOfSquares: MutableList<String>)
{
    for(square in listOfSquares)
    {
       square.setOnClickListener{ //Do Something}
    }
}

The other way I thought of implementing this was to write a single onClick function, and attach it to each button in the xml file, but I'm not really sure what's possible as I'm quite new to Kotlin/Java

6 Answers 6

2

why not just set an on item listener on the entire grid layout and then have a listener for inside of that like

gridView.setOnItemClickListener(object:OnItemClickListener() {
   fun onItemClick(parent:AdapterView<*>, v:View,
              position:Int, id:Long) {
      // DO something
   }
})

this way you wouldn't need to have the id's of everything inside the grid view then you could just change where you going basted on the position:Int clicked inside of the grid view or am i not understanding what your trying to do?

Sign up to request clarification or add additional context in comments.

Comments

1

You do not need a new ClickListener object for every button. Just make ONE click listener instance (have your activity implement it or make a new class for it or use an anonymous class). You can pass that instance into your button's setOnClickListener method. You can tell which button was clicked by using view.getId() method and comparing it against your button id's.

1 Comment

This sounds like it might work for me, but I'm so damn new at this that I'll have to do some research. I'm mostly experienced in C/C++/C# programming for microcontrollers, so I'm just getting a grasp of Java/Kotlin syntax and flow. I'll report back and let you know how it goes, thanks!
0

I'm not sure if I understood right but you can try to encapsulate the id and the listener in a Square object.

Something like this:

class Square(context: Context?, id: String) : Button(context) {

    override fun setOnClickListener(l: OnClickListener?) {
        super.setOnClickListener(l)
        //TODO: use your id to something
    }
}

You will have to change your listOfSquares to be a MutableList<Square>.

Comments

0

If each button needs to have the same functionality in its setOnClickListener, then this is what you can do.

listOf(listOfSquares).forEach {
            it?.setOnClickListener {
               // Do something
        }
}

Comments

0

One of the direct method to achieve this would be by creating one funtion to be called on click event for all the buttons and inside the function you can identify the button pressed by getting its id and using a when operator to perform different operations in different button clicks.

inside the layout add the add Button like this:-

<LinearLayout xmlns:android="http://schemas.android.com/apk/res/android"
xmlns:app="http://schemas.android.com/apk/res-auto"
xmlns:tools="http://schemas.android.com/tools"
android:layout_width="match_parent"
android:layout_height="match_parent"
tools:context=".MainActivity">

<Button
    android:id="@+id/button"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:text="Button"
    android:onClick="toastMe"
    tools:layout_editor_absoluteX="95dp"
    tools:layout_editor_absoluteY="216dp" />
<Button
    android:id="@+id/button2"
    android:layout_width="wrap_content"
    android:layout_height="wrap_content"
    android:text="Button"
    android:onClick="toastMe"
    tools:layout_editor_absoluteX="95dp"
    tools:layout_editor_absoluteY="216dp" />

  </LinearLayout>

and inside you kotlin code , put your function like the following:-

 fun toastMe(view : View) {
   when (view.id) {
       R.id.button -> print("x == 1")
       R.id.button2 -> print("x == 2")
       else -> { // Note the block
           print("x is neither 1 nor 2")
       }
   }

when replaces the switch operator of java language.

Comments

-2

You can listen onClick on your activity

class MyActivity:Activity(), OnClickListener {
  fun onClick(v:View) {
    R.id.Button1
    run({
      //...
      break })
    R.id.Button2
    run({
      //..
      break })
  }
}

If you plan to change some behavior according to ID's, you don't need the case here. Extend the Button class as GridButton and make sure that the class type is GridButton by

if (obj is C)
{
  //your code
}

5 Comments

I don't think this is a feasible implementation at all. The number of click listeners to be added is enormous. Do you intend on writing manual when statement for ~600 grid items?
There is only one listener, the activity on the top level. Could you tell, what will do with each of the buttons? Adding such amount of button would be very slow.
Long time ago, I used this technique with a private member each extended button to correctly function.
I agree. Your implementation makes it so that instead of applying numerous click listeners, only a single listener will suffice. But, you would have to apply 'n' number of cases in your when statement. In this particular instance, ~600. Not a good implementation. However, if the number of objects click able are limited, I believe this is quite alright. As for your thought of adding those many buttons being slow, yes, I agree. Going with a gridlayout would be better.
Overload the button class so that let do their work and this eliminate the when case as I told. That is object orientation, right.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.