RecyclerView Onclick(调用非静态方法)

时间:2015-05-27 16:35:26

标签: java android static onclick android-recyclerview

我遇到了关于将OnItemClickListener设置为我的RecyclerView项目的问题。我尝试按照Android Studio的RecyclerView示例中描述的方式设置监听器。因此,在我的RecyclerView的ViewHolder类中设置了一个监听器。

public class ProgramViewHolder extends RecyclerView.ViewHolder {
    protected TextView vName;
    protected ImageView vProgramImage;

    public ProgramViewHolder(View v) {
        super(v);
        vName = (TextView) v.findViewById(R.id.programName);
        vProgramImage = (ImageView) v.findViewById(R.id.programImage);

        v.setOnClickListener(new View.OnClickListener() {
            @Override
            public void onClick(View v) {
                // HERE PROBLEM !! 
                MainActivity.openSettings(1);
            }
        });
    }
}

现在我想调用我的MainActivity openSettings(int)的方法来加载片段:

public void openSettings(int layoutId) {
    settingsFragment setFrag = new settingsFragment();

    Bundle information = new Bundle();
    information.putInt("layoutId", layoutId);

    setFrag.setArguments(information);
    getFragmentManager().beginTransaction()
            .replace(R.id.fragmentContainer, setFrag)
            .commit();
}

但是现在出了问题。当我尝试编译时,它说"非静态方法' openSettings(int)'不能从静态上下文中引用。" 我完全不明白这个错误。为什么它是一个静态的上下文? ProgramViewHolder类不会声明为静态。

最重要的部分:我该如何解决?我想为RecyclerView的每个项目设置一个OnClickListener,并调用MainActivity的公共方法。

非常感谢你,花时间来帮助我。

2 个答案:

答案 0 :(得分:5)

并不是ProgramViewHolder是静态的,而是因为尝试从静态上下文调用您的活动(您没有调用活动的特定实例)。

您应该做的是将活动传递到您的recyclerViewAdapter,以便您可以访问它。

例如

MainActivity mainActivity;
public CustomRecyclerViewAdapter(MainActivity mainActivity) {
    this.mainActivity = mainActivity;
}

从MainActivity创建recyclerViewAdapter CustomRecyclerView recyclerViewAdapter = new CustomRecyclerViewAdapter(this); recyclerViewAdapter.setAdapter(recyclerViewAdapter);

然后您应该能够像这样访问您的方法 mainActivity.openSettings(1);

如果您有任何问题,请告诉我

//修改

以下是如何从bindViewHolder设置onClick。由于RecyclerView“循环”数据的方式,您希望在此处设置任何onClickListeners。例如,如果每一行都应对单击执行不同的操作,则需要确保单击侦听器绑定到特定行。在onBindViewHolder中创建它可以确保这一点。如果您希望整行可以单击,而不是内部元素,只需创建一个填充整行的外部视图。然后将onClickListener绑定到该。

// Replace the contents of a view (invoked by the layout manager)
@Override
public void onBindViewHolder(ViewHolder holder, int position) {
    // - get element from your dataset at this position
    // - replace the contents of the view with that element

    ProgramViewHolder programViewHolder = (ProgramViewHolder) holder;
    programViewHolder.vName.setOnClicklistener(new View.OnClickListener() {
        @Override
        public void onClick(View v) {
            mainActivity.openSettings(1);
        }
    });

}

答案 1 :(得分:1)

如果您有gp <- delete_layers(gp, match_type = "GeomLabel" & label = "A") 个活动包含recyclerView,则只需执行以下操作:

context

您可以将其放在your_view_holder.v.setOnClickListener(new View.OnClickListener() { @Override public void onClick(View v) { // HERE SOLUTION!! ((MainActivity)context).openSettings(1); } });

如何获取上下文:

在Adapter的构造函数中创建上下文的另一个参数,并在实例化Adapter之后通过活动传递上下文。

为什么要传递上下文:

我建议您始终传递上下文并将其分配给任何适配器的变量,因为这是您在使用适配器时不时需要的内容,因此不必每次都使用替代方法来保存上下文,只需保存一次即可

相关问题