android - ListView:在滚动条顶部显示固定标题(或使用 dispatchDraw 在另一个顶部绘制 View )

标签 android android-layout listview android-listview

我正在努力实现可以在 StickyListHeaders 上看到的这种效果的示例应用程序:

基本上,我需要在 ListView 顶部但在其滚动条下方显示一个单一、静态、固定 标题 View 。我不需要任何与章节或字母索引或类似内容相关的内容。

我无法根据 StickyListHeaders 的源代码弄清楚如何执行此操作.我尝试子类化 ListView 并覆盖 dispatchDraw() ,如下所示:

protected void dispatchDraw(Canvas canvas)
{
    View view = LayoutInflater.from(getContext()).inflate(R.layout.header, this, false);
    drawChild(canvas, view, getDrawingTime());
    super.dispatchDraw(canvas);
}

但是不行,没有绘制表头。

最佳答案

回答我自己的问题。这个 ListView 子类能够做我想做的事。列表的第一个元素可以固定调用 showFixedHeader():

import android.content.Context;
import android.graphics.Canvas;
import android.util.AttributeSet;
import android.view.View;
import android.widget.ListAdapter;
import android.widget.ListView;

public class FixedHeaderListView extends ListView
{
    private View fixedHeader = null;
    private boolean fixedHeaderLayoutDone = false;
    private boolean showFixedHeader = true;

    @SuppressWarnings("unused")
    public FixedHeaderListView(Context context)
    {
        super(context);
    }

    @SuppressWarnings("unused")
    public FixedHeaderListView(Context context, AttributeSet attrs)
    {
        super(context, attrs);
    }

    @SuppressWarnings("unused")
    public FixedHeaderListView(Context context, AttributeSet attrs, int defStyle)
    {
        super(context, attrs, defStyle);
    }

    public void showFixedHeader(boolean show)
    {
        this.showFixedHeader = show;
        requestLayout(); // Will cause layoutChildren() and dispatchDraw() to be called
    }

    @Override
    protected void layoutChildren()
    {
        super.layoutChildren();

        if (!fixedHeaderLayoutDone)
        {
            ListAdapter adapter = getAdapter();
            if (adapter != null && adapter.getCount() > 0)
            {
                // Layout the first item in the adapter's data set as the fixed header
                fixedHeader = adapter.getView(0, null, this);
                if (fixedHeader != null)
                {
                    // Measure and layout

                    LayoutParams layoutParams = (LayoutParams)fixedHeader.getLayoutParams();
                    if (layoutParams == null)
                    {
                        layoutParams = new LayoutParams(LayoutParams.MATCH_PARENT, LayoutParams.WRAP_CONTENT);
                    }

                    int heightMode = MeasureSpec.getMode(layoutParams.height);
                    if (heightMode == MeasureSpec.UNSPECIFIED)
                    {
                        heightMode = MeasureSpec.EXACTLY;
                    }

                    int heightSize = MeasureSpec.getSize(layoutParams.height);
                    int maxHeight = getHeight() - getListPaddingTop() - getListPaddingBottom();
                    if (heightSize > maxHeight)
                    {
                        heightSize = maxHeight;
                    }

                    int widthSpec = MeasureSpec.makeMeasureSpec(getWidth() - getListPaddingLeft() - getListPaddingRight(), MeasureSpec.EXACTLY);
                    int heightSpec = MeasureSpec.makeMeasureSpec(heightSize, heightMode);
                    fixedHeader.measure(widthSpec, heightSpec);
                    fixedHeader.layout(0, 0, fixedHeader.getMeasuredWidth(), fixedHeader.getMeasuredHeight());

                    // Flag as layout done
                    fixedHeaderLayoutDone = true;
                }
            }
        }
    }


    @Override @SuppressWarnings("NullableProblems")
    protected void dispatchDraw(Canvas canvas)
    {
        super.dispatchDraw(canvas);

        if (fixedHeader != null && showFixedHeader)
        {
            drawChild(canvas, fixedHeader, getDrawingTime());
        }
    }

}

它没有经过严格测试,但它是一个很好的起点。

关于android - ListView:在滚动条顶部显示固定标题(或使用 dispatchDraw 在另一个顶部绘制 View ),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/23371208/

相关文章:

android - 如何将图像保存到外部存储器而不是保存在内部

java - Android 应用程序上的特殊字符

java - 使用 Android 应用程序将数据保留在 Azure 中时出现安全错误

android - 一次读取所有行

android onDestroy 仅在 vd 上工作正常

android - 在 android 的 CalendarView 小部件中更改选定日期的颜色

android - ScrollView diorders 并移除 relativelayout 的内容

android child view 没有按下状态

android - 如何在 Android 的 ListView 中延迟加载图像

android - 从 fragment 中的 sqlite 动态设置复选框