127

是否可以调用Activityfrom中定义的方法ListAdapter

(我想在行中创建一个Buttonlist's当单击此按钮时,它应该执行在相应活动中定义的方法。我尝试onClickListener在我的设置中设置ListAdapter但我不知道如何调用此方法,它的路径是什么。 ..)

当我使用时,Activity.this.method()我收到以下错误:

No enclosing instance of the type Activity is accessible in scope

任何的想法 ?

4

9 回答 9

319

是的你可以。

在适配器中添加一个新字段:

private Context mContext;

在适配器构造函数中添加以下代码:

public AdapterName(......, Context context) {
  //your code.
  this.mContext = context;
}

在 Adapter 的 getView(...) 中:

Button btn = (Button) convertView.findViewById(yourButtonId);
btn.setOnClickListener(new Button.OnClickListener() {
  @Override
  public void onClick(View v) {
    if (mContext instanceof YourActivityName) {
      ((YourActivityName)mContext).yourDesiredMethod();
    }
  }
});

在您看到代码、活动等的地方替换为您自己的类名。

如果您需要将同一适配器用于多个活动,则:

创建接口

public interface IMethodCaller {
    void yourDesiredMethod();
}

在您需要具有此方法调用功能的活动中实现此接口。

然后在 Adapter getView() 中,调用如下:

Button btn = (Button) convertView.findViewById(yourButtonId);
btn.setOnClickListener(new Button.OnClickListener() {
    @Override
    public void onClick(View v) {
        if (mContext instanceof IMethodCaller) {
            ((IMethodCaller) mContext).yourDesiredMethod();
        }
    }
});

你完成了。如果您需要将此适配器用于不需要此调用机制的活动,则代码将不会执行(如果检查失败)。

于 2012-08-27T13:00:18.097 回答
137

你可以这样做:

声明接口:

public interface MyInterface{
    public void foo();
}

让您的 Activity 实施它:

    public class MyActivity extends Activity implements MyInterface{
        public void foo(){
            //do stuff
        }
        
        public onCreate(){
            //your code
            MyAdapter adapter = new MyAdapter(this); //this will work as your 
                                                     //MyInterface listener
        }
    }

然后将您的活动传递给 ListAdater:

public MyAdapter extends BaseAdater{
    private MyInterface listener;

    public MyAdapter(MyInterface listener){
        this.listener = listener;
    }
}

在适配器中的某个地方,当您需要调用该 Activity 方法时:

listener.foo();
于 2012-08-27T13:02:42.347 回答
75

原来的:

我理解当前的答案,但需要一个更清楚的例子。这是我使用Adapter(RecyclerView.Adapter) 和Activity.

在您的活动中:

这将实现interface我们在Adapter. 在此示例中,当用户单击RecyclerView.

public class MyActivity extends Activity implements AdapterCallback {

    private MyAdapter myAdapter;

    @Override
    public void onMethodCallback() {
       // do something
    }

    @Override
    protected void onCreate(@Nullable Bundle savedInstanceState) {
        super.onCreate(savedInstanceState);

        myAdapter = new MyAdapter(this);
    }
}

在您的适配器中:

在 中Activity,我们启动了我们的Adapter并将其作为参数传递给构造函数。这将启动我们interface的回调方法。你可以看到我们使用我们的回调方法来处理用户点击。

public class MyAdapter extends RecyclerView.Adapter<MyAdapter.ViewHolder> {

    private AdapterCallback adapterCallback;

    public MyAdapter(Context context) {
        try {
            adapterCallback = ((AdapterCallback) context);
        } catch (ClassCastException e) {
            throw new ClassCastException("Activity must implement AdapterCallback.", e);
        }
    }

    @Override
    public void onBindViewHolder(MyAdapter.ViewHolder viewHolder, int position) {
        // simple example, call interface here
        // not complete
        viewHolder.itemView.setOnClickListener(new OnClickListener() {
            @Override
            public void onClick(View view) {
                try {
                    adapterCallback.onMethodCallback();
                } catch (ClassCastException e) {
                   // do something
                }
            }
        });
    }

    public static interface AdapterCallback {
        void onMethodCallback();
    }
}
于 2014-12-31T05:54:07.810 回答
16

基本而简单。

在您的适配器中只需使用它。

((YourParentClass) context).functionToRun();

于 2015-12-28T09:09:56.413 回答
8

对于科特林:

在您的适配器中,只需调用

(context as Your_Activity_Name).yourMethod()
于 2018-07-01T10:58:30.387 回答
7

另一种方法是::

在您的适配器中编写一个方法,比如说 public void callBack(){}。

现在,在活动中为适配器创建对象时,会覆盖此方法。当您调用适配器中的方法时,将调用覆盖方法。

Myadapter adapter = new Myadapter() {
  @Override
  public void callBack() {
    // dosomething
  }
};
于 2015-05-20T09:21:13.543 回答
1

在 Kotlin 中,现在有一种使用 lambda 函数的更简洁的方法,不需要接口:

class MyAdapter(val adapterOnClick: (Any) -> Unit) {
    fun setItem(item: Any) {
        myButton.setOnClickListener { adapterOnClick(item) }
    }
}

class MyActivity {
    override fun onCreate(savedInstanceState: Bundle?) {
        var myAdapter = MyAdapter { item -> doOnClick(item) }
    }


    fun doOnClick(item: Any) {

    }
}
于 2020-06-12T10:51:30.923 回答
0
if (parent.getContext() instanceof yourActivity) {
  //execute code
}

如果具有从您的方法GroupView请求视图的 Activity 是,则此条件将使您能够执行某些操作getView()adapteryourActivity

注意:parent是 GroupView

于 2017-05-26T10:44:39.400 回答
0

对于 kotlin,您可以执行以下操作:

if(context is MainActivity){ context.functionToCall(values) }

于 2021-06-17T13:08:52.540 回答