在Fragment中从FragmentPagerAdapter设置单击处理程序

时间:2013-11-15 21:14:20

标签: android android-fragments

我喜欢在FragmentPagerAdapter的每个片段上设置一个点击监听器。问题是Fragment是在getItem()中创建的静态。我找不到创建后访问片段视图的解决方案来设置点击监听器。我可以直接在片段中设置单击侦听器,但是我如何从适配器调用抽象单击侦听器?

public class ProfilePicPagerAdapter extends FragmentPagerAdapter implements ViewPager.OnPageChangeListener {

private static final String TAG = ProfilePicPagerAdapter.class.getSimpleName();
private PicLinearLayout cur = null;
private PicLinearLayout next = null;
private Context context;
private FragmentManager fm;
private ViewPager pager;
private float scale;
private String[] pics;
private PicListener listener;

private int PAGES = 1;
private int FIRST_PAGE = 0;

// You can choose a bigger number for LOOPS, but you know, nobody will fling
// more than 1000 times just in order to test your "infinite" ViewPager :D 
public final static int LOOPS = 1; 

public final static float BIG_SCALE = 1.0f;
public final static float SMALL_SCALE = 0.7f;
public final static float DIFF_SCALE = BIG_SCALE - SMALL_SCALE;

public ProfilePicPagerAdapter(Context context, ViewPager pager, String[] pics, int initItem, FragmentManager fm) {
    super(fm);
    this.fm = fm;
    this.pager = pager;
    this.context = context;
    this.pics = pics;
    PAGES = pics.length;
    FIRST_PAGE = initItem;
}

public void setOnPicClickListener(PicListener l) {
    this.listener = l;
    if(listener != null) {
        listener.OnSelect(FIRST_PAGE);
    }
}

@Override
public Fragment getItem(int position) 
{
    // make the first pager bigger than others
    if (position == FIRST_PAGE)
        scale = BIG_SCALE;      
    else
        scale = SMALL_SCALE;

    position = position % PAGES;
    return ProfilePicFragment.newInstance(context, position, pics[position], scale);
}

@Override
public int getCount()
{       
    return PAGES * LOOPS;
}

...

private String getFragmentTag(int position) {
    return "android:switcher:" + pager.getId() + ":" + position;
}

public static abstract class PicListener {

    public abstract void OnClick(int position);
    public abstract void OnSelect(int position);

}




public class ProfilePicFragment extends Fragment {

public static Fragment newInstance(Context context, int pos, String pic, float scale)
{
    Bundle b = new Bundle();
    b.putInt("pos", pos);
    b.putFloat("scale", scale);
    b.putString("pic", pic);
    return Fragment.instantiate(context, ProfilePicFragment.class.getName(), b);
}

@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
    if (container == null) {
        return null;
    }

    LinearLayout l = (LinearLayout) inflater.inflate(R.layout.item_profile_pic, container, false);

    int pos = this.getArguments().getInt("pos");
    String pic = this.getArguments().getString("pic");

    ImageView imageView = (ImageView) l.findViewById(R.id.profile_pic);

     // load image
    ...

    return l;
}

1 个答案:

答案 0 :(得分:3)

尝试这样的事情:

public class ProfilePicPagerAdapter extends FragmentPagerAdapter implements ViewPager.OnPageChangeListener {

private static final String TAG = ProfilePicPagerAdapter.class.getSimpleName();
private PicLinearLayout cur = null;
private PicLinearLayout next = null;
private Context context;
private FragmentManager fm;
private ViewPager pager;
private float scale;
private String[] pics;
private PicListener listener;

private int PAGES = 1;
private int FIRST_PAGE = 0;

// You can choose a bigger number for LOOPS, but you know, nobody will fling
// more than 1000 times just in order to test your "infinite" ViewPager :D 
public final static int LOOPS = 1; 

public final static float BIG_SCALE = 1.0f;
public final static float SMALL_SCALE = 0.7f;
public final static float DIFF_SCALE = BIG_SCALE - SMALL_SCALE;

public ProfilePicPagerAdapter(Context context, ViewPager pager, String[] pics, int initItem, FragmentManager fm) {
    super(fm);
    this.fm = fm;
    this.pager = pager;
    this.context = context;
    this.pics = pics;
    PAGES = pics.length;
    FIRST_PAGE = initItem;
}

@Override
public Fragment getItem(int position) 
{
    // make the first pager bigger than others
    if (position == FIRST_PAGE)
        scale = BIG_SCALE;      
    else
        scale = SMALL_SCALE;

    position = position % PAGES;


    return ProfilePicFragment.newInstance(context, position, pics[position], scale, new PicListener() {

        @Override
        public void OnSelect(int position) {
            Log.d(TAG, "Pic at position: " + position + " selected");
        }

        @Override
        public void OnClick(int position) {
            Log.d(TAG, "Pic at position: " + position + " clicked");            
        }
    });
}

@Override
public int getCount()
{       
    return PAGES * LOOPS;
}

...

private String getFragmentTag(int position) {
    return "android:switcher:" + pager.getId() + ":" + position;
}

public interface PicListener {

    public void OnClick(int position);
    public void OnSelect(int position);

}




public class ProfilePicFragment extends Fragment {

private static PicListener mListener;
public static Fragment newInstance(Context context, int pos, String pic, float scale, PicListener listener)
{

    mListener = listener;
    Bundle b = new Bundle();
    b.putInt("pos", pos);
    b.putFloat("scale", scale);
    b.putString("pic", pic);
    return Fragment.instantiate(context, ProfilePicFragment.class.getName(), b);
}

@Override
public View onCreateView(LayoutInflater inflater, ViewGroup container, Bundle savedInstanceState) {
    if (container == null) {
        return null;
    }

    LinearLayout l = (LinearLayout) inflater.inflate(R.layout.item_profile_pic, container, false);

    int pos = this.getArguments().getInt("pos");
    String pic = this.getArguments().getString("pic");

    ImageView imageView = (ImageView) l.findViewById(R.id.profile_pic);


    imageView.setOnClickListener(new OnClickListener() {

        @Override
        public void onClick(View v) {
            if(mListener != null) {
                mListener.OnSelect(pos);
                mListener.OnClick(pos);
            }
        }
    })

     // load image
    ...

    return l;
}

我仍然不清楚为什么你想要回调你的适配器。