Die anderen haben bereits gesagt, dass Methoden in onClick in Aktivitäten und nicht in Fragmenten gesucht werden. Dennoch, wenn Sie es wirklich wollen, es ist möglich.
Grundsätzlich hat jede Ansicht ein Tag (wahrscheinlich null). Wir setzen das Tag der Stammansicht auf das Fragment, das diese Ansicht aufgeblasen hat. Anschließend können Sie ganz einfach die übergeordneten Elemente der Ansicht durchsuchen und das Fragment mit der angeklickten Schaltfläche abrufen. Jetzt ermitteln wir den Methodennamen und verwenden Reflection, um dieselbe Methode aus dem abgerufenen Fragment aufzurufen. Einfach!
in einer Klasse, die erweitert Fragment
:
@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
View rootView = inflater.inflate(R.layout.fragment_id, container, false);
OnClickFragments.registerTagFragment(rootView, this); // <========== !!!!!
return rootView;
}
public void onButtonSomething(View v) {
Log.d("~~~","~~~ MyFragment.onButtonSomething");
// whatever
}
Alle Aktivitäten werden von derselben ButtonHandlingActivity abgeleitet:
public class PageListActivity extends ButtonHandlingActivity
ButtonHandlingActivity.java:
public class ButtonHandlingActivity extends Activity {
public void onButtonSomething(View v) {
OnClickFragments.invokeFragmentButtonHandlerNoExc(v);
//or, if you want to handle exceptions:
// try {
// OnClickFragments.invokeFragmentButtonHandler(v);
// } catch ...
}
}
Es müssen Methoden für alle xml onClick-Handler definiert werden.
com / example / customandroid / OnClickFragments.java:
package com.example.customandroid;
import java.lang.reflect.InvocationTargetException;
import java.lang.reflect.Method;
import android.app.Fragment;
import android.view.View;
public abstract class OnClickFragments {
public static class FragmentHolder {
Fragment fragment;
public FragmentHolder(Fragment fragment) {
this.fragment = fragment;
}
}
public static Fragment getTagFragment(View view) {
for (View v = view; v != null; v = (v.getParent() instanceof View) ? (View)v.getParent() : null) {
Object tag = v.getTag();
if (tag != null && tag instanceof FragmentHolder) {
return ((FragmentHolder)tag).fragment;
}
}
return null;
}
public static String getCallingMethodName(int callsAbove) {
Exception e = new Exception();
e.fillInStackTrace();
String methodName = e.getStackTrace()[callsAbove+1].getMethodName();
return methodName;
}
public static void invokeFragmentButtonHandler(View v, int callsAbove) throws IllegalAccessException, IllegalArgumentException, InvocationTargetException, NoSuchMethodException {
String methodName = getCallingMethodName(callsAbove+1);
Fragment f = OnClickFragments.getTagFragment(v);
Method m = f.getClass().getMethod(methodName, new Class[] { View.class });
m.invoke(f, v);
}
public static void invokeFragmentButtonHandler(View v) throws IllegalAccessException, IllegalArgumentException, InvocationTargetException, NoSuchMethodException {
invokeFragmentButtonHandler(v,1);
}
public static void invokeFragmentButtonHandlerNoExc(View v) {
try {
invokeFragmentButtonHandler(v,1);
} catch (NoSuchMethodException e) {
e.printStackTrace();
} catch (IllegalAccessException e) {
e.printStackTrace();
} catch (IllegalArgumentException e) {
e.printStackTrace();
} catch (InvocationTargetException e) {
e.printStackTrace();
}
}
public static void registerTagFragment(View rootView, Fragment fragment) {
rootView.setTag(new FragmentHolder(fragment));
}
}
Und das nächste Abenteuer wird die Verschleierung sein ...
PS
Es ist natürlich an Sie , Ihre Anwendung so zu gestalten, dass die Daten im leben Modell anstatt in Aktivitäten oder Fragmenten (die Controller aus dem MVC , Model-View-Controller - Sicht). Die Ansicht ist das, was Sie über XML definieren, sowie die benutzerdefinierten Ansichtsklassen (wenn Sie sie definieren, verwenden die meisten Benutzer nur das, was bereits vorhanden ist). Eine Faustregel: Wenn einige Daten die Bildschirmumdrehung definitiv überleben müssen, gehören sie zum Modell .