是否有可能使ListView水平?我使用图库视图完成了此操作,但所选项目会自动出现在屏幕的中心。我不希望选中的项目位于我点击的同一位置。我该如何纠正这个问题?我的想法是用水平滚动来设置ListView。分享你的想法?


当前回答

这有点(非常)晚了,但我把它贴出来,以防以后有人来看。

在Android L预览版的支持库中,有一个RecyclerView,它完全是你想要的。

现在,你只能通过L预览SDK获得它,你需要将你的minSdk设置为L。但是你可以将所有必要的文件复制到你的项目中,并以这种方式使用它们,直到L正式发布。

你可以在这里下载预览文档。

警告:回收器视图的API可能会改变,它可能有bug。

更新

水平列表视图的源代码是:

LinearLayoutManager layoutManager
    = new LinearLayoutManager(this, LinearLayoutManager.HORIZONTAL, false);

RecyclerView myList = findViewById(R.id.my_recycler_view);
myList.setLayoutManager(layoutManager);

其他回答

你总是可以创建你的textviews等动态和设置你的onclicklistener,就像你会做一个适配器

我在我的项目中使用了水平列表视图链接,我得到了很好的结果。我最初使用devsmart库,但它给了我一些问题。所以使用水平列表视图链接的最佳方式,因为它恢复了我的问题,而且我最近在谷歌PlayStore上使用这个库推出了我的应用程序,并得到了用户的良好响应。所以我建议你使用上面提到的相同的库来水平显示listview。享受:)

这不是一个很好的答案,但是如何使用水平滚动视图呢?

我的解决方案是简单地使用ViewPager小部件。它不像Gallery那样中心锁定,并且有一个用于循环视图的内置功能(如ListView)。你可能会看到类似的方法在谷歌播放应用程序,每当你处理水平滚动列表。

你只需要扩展PagerAdapter并在那里执行一些调整:

public class MyPagerAdapter extends PagerAdapter {

    private Context mContext;

    public MyPagerAdapter(Context context) {
        this.mContext = context;
    }

    // As per docs, you may use views as key objects directly 
    // if they aren't too complex
    @Override
    public Object instantiateItem(ViewGroup container, int position) {
        LayoutInflater inflater = LayoutInflater.from(mContext);
        View view = inflater.inflate(R.layout.item, null);
        container.addView(view);
        return view;
    }

    @Override
    public void destroyItem(ViewGroup container, int position, Object object) {
        container.removeView((View) object);
    }

    @Override
    public int getCount() {
        return 10;
    }

    @Override
    public boolean isViewFromObject(View view, Object object) {
        return view == object;
    }

    // Important: page takes all available width by default,
    // so let's override this method to fit 5 pages within single screen
    @Override
    public float getPageWidth(int position) {
        return 0.2f;
    }
}

因此,你将拥有一个带有适配器的水平滚动小部件,如下所示:

@Paul回答链接到一个伟大的解决方案,但代码不允许对项目的孩子使用onClickListeners(回调函数永远不会被调用)。我一直在努力寻找一个解决方案,我决定在这里张贴你需要修改的代码(以防有人需要它)。

而不是重写dispatchTouchEvent重写onTouchEvent。使用dispatchTouchEvent的相同代码并删除方法(您可以在这里阅读两者之间的区别http://developer.android.com/guide/topics/ui/ui-events.html#EventHandlers)

@Override
public boolean onTouchEvent(MotionEvent event) {
    boolean handled = mGesture.onTouchEvent(event);
    return handled;
}

然后,添加下面的代码,它将决定从子项中窃取事件,并将其交给我们的onTouchEvent,或让它由它们处理。

@Override
public boolean onInterceptTouchEvent(MotionEvent ev) {
    switch( ev.getActionMasked() ){
        case MotionEvent.ACTION_DOWN:
             mInitialX = ev.getX();
             mInitialY = ev.getY();             
             return false;
        case MotionEvent.ACTION_MOVE:
             float deltaX = Math.abs(ev.getX() - mInitialX);
             float deltaY = Math.abs(ev.getY() - mInitialY);
             return ( deltaX > 5 || deltaY > 5 );
        default:
             return super.onInterceptTouchEvent(ev);
    }
}

最后,不要忘记在你的类中声明变量:

private float mInitialX;
private float mInitialY;