Pre-Honeycomb (Android 3), each Activity was registered to handle button clicks via the onClick
tag in a Layout\'s XML:
android:onClick=\"m
Adding to Blundell's answer,
If you have more fragments, with plenty of onClicks:
Activity:
Fragment someFragment1 = (Fragment)getFragmentManager().findFragmentByTag("someFragment1 ");
Fragment someFragment2 = (Fragment)getFragmentManager().findFragmentByTag("someFragment2 ");
Fragment someFragment3 = (Fragment)getFragmentManager().findFragmentByTag("someFragment3 ");
...onCreate etc instantiating your fragments
public void myClickMethod(View v){
if (someFragment1.isVisible()) {
someFragment1.myClickMethod(v);
}else if(someFragment2.isVisible()){
someFragment2.myClickMethod(v);
}else if(someFragment3.isVisible()){
someFragment3.myClickMethod(v);
}
}
In Your Fragment:
public void myClickMethod(View v){
switch(v.getid()){
// Just like you were doing
}
}
I would rather go for the click handling in code than using the onClick
attribute in XML when working with fragments.
This becomes even easier when migrating your activities to fragments. You can just call the click handler (previously set to android:onClick
in XML) directly from each case
block.
findViewById(R.id.button_login).setOnClickListener(clickListener);
...
OnClickListener clickListener = new OnClickListener() {
@Override
public void onClick(final View v) {
switch(v.getId()) {
case R.id.button_login:
// Which is supposed to be called automatically in your
// activity, which has now changed to a fragment.
onLoginClick(v);
break;
case R.id.button_logout:
...
}
}
}
When it comes to handling clicks in fragments, this looks simpler to me than android:onClick
.
You might want to consider using EventBus for decoupled events .. You can listen for events very easily. You can also make sure the event is being received on the ui thread (instead of calling runOnUiThread.. for yourself for every event subscription)
https://github.com/greenrobot/EventBus
from Github:
Android optimized event bus that simplifies communication between Activities, Fragments, Threads, Services, etc. Less code, better quality
I prefer using the following solution for handling onClick events. This works for Activity and Fragments as well.
public class StartFragment extends Fragment implements OnClickListener{
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container,
Bundle savedInstanceState) {
View v = inflater.inflate(R.layout.fragment_start, container, false);
Button b = (Button) v.findViewById(R.id.StartButton);
b.setOnClickListener(this);
return v;
}
@Override
public void onClick(View v) {
switch (v.getId()) {
case R.id.StartButton:
...
break;
}
}
}
As I see answers they're somehow old. Recently Google introduce DataBinding which is much easier to handle onClick or assigning in your xml.
Here is good example which you can see how to handle this :
<?xml version="1.0" encoding="utf-8"?>
<layout xmlns:android="http://schemas.android.com/apk/res/android">
<data>
<variable name="handlers" type="com.example.Handlers"/>
<variable name="user" type="com.example.User"/>
</data>
<LinearLayout
android:orientation="vertical"
android:layout_width="match_parent"
android:layout_height="match_parent">
<TextView android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@{user.firstName}"
android:onClick="@{user.isFriend ? handlers.onClickFriend : handlers.onClickEnemy}"/>
<TextView android:layout_width="wrap_content"
android:layout_height="wrap_content"
android:text="@{user.lastName}"
android:onClick="@{user.isFriend ? handlers.onClickFriend : handlers.onClickEnemy}"/>
</LinearLayout>
</layout>
There is also very nice tutorial about DataBinding you can find it Here.
Best solution IMHO:
in fragment:
protected void addClick(int id) {
try {
getView().findViewById(id).setOnClickListener(this);
} catch (Exception e) {
e.printStackTrace();
}
}
public void onClick(View v) {
if (v.getId()==R.id.myButton) {
onMyButtonClick(v);
}
}
then in Fragment's onViewStateRestored:
addClick(R.id.myButton);