viewgrop测量

参考博文地址 添加链接描述

import android.content.Context
import android.graphics.Rect
import android.util.AttributeSet
import android.util.Log
import android.view.ViewGroup

public class MyViewGrop @JvmOverloads constructor
    (context: Context, attrs: AttributeSet? = null, defStyleAttr: Int = 0)
    :ViewGroup(context,attrs,defStyleAttr) {

    private var listRect= mutableListOf<Rect>()

    override fun onMeasure(widthMeasureSpec: Int, heightMeasureSpec: Int) {
        super.onMeasure(widthMeasureSpec, heightMeasureSpec)
        //用了多好宽高
        var widthused=0
        var  heightused=0
        //每一行用了多少宽高
        var linewidthused=0
        var lineheight=0

        //取出自己的宽度限制
        var widthMode = MeasureSpec.getMode(widthMeasureSpec)
        var widthSize = MeasureSpec.getSize(widthMeasureSpec)

        if (listRect.isEmpty()) {
            for (index in 0 until childCount) {
                Log.e("TAG","初始化:"+index)
                listRect.add(Rect())
            }
        }

        for ( index in 0 until childCount){
            val childView = getChildAt(index)


            measureChildWithMargins(childView,widthMeasureSpec,0,heightMeasureSpec,heightused)
            //如果算出来的 宽度 比自己的宽度还大那就要重新测量 准备换行
            if (widthMode!=MeasureSpec.UNSPECIFIED&&linewidthused+childView.measuredWidth>widthSize){
                //既然是重新测量了 那显然 每行已经用掉的宽度就是0了
                linewidthused = 0
                //计算已经用了多少高度了 因为既然换行了 heightUsed 就要增加了
                heightused +=lineheight

                measureChildWithMargins(childView,widthMeasureSpec,0,heightMeasureSpec,heightused)
            }
            val rect = listRect[index]
            //起点的left和top 很好理解 就是 这一行 已经用了多少 你就从这个位置开 layout
            rect.set(linewidthused,heightused,
                linewidthused+childView.measuredWidth,heightused+childView.measuredHeight)
            //每一行已经用的 当然是加上这个child的宽度
            linewidthused += childView.measuredWidth
            //计算一下最大宽度 到时候自己要用
            widthused=Math.max(linewidthused,widthused)
            //每一行的高度 就等于这一行里面 高度最大的那个view
            lineheight= Math.max(lineheight, childView.measuredHeight)

        }
        //子view 都算出来了 那我自己也肯定就算出来了吧
        val measureWidth = widthused
        val measureHeight = (heightused + lineheight)
        //算完了以后 直接调用这个方法 到这里测量就全部结束了
        setMeasuredDimension(measureWidth, measureHeight)

    }




    override fun onLayout(p0: Boolean, p1: Int, p2: Int, p3: Int, p4: Int) {
        if (listRect.isNotEmpty()) {
            for (index in 0 until childCount step 1) {
                val child = getChildAt(index)
                val childBounds = listRect[index]
                child.layout(
                    childBounds.left,
                    childBounds.top,
                    childBounds.right,
                    childBounds.bottom
                )
            }
        }
    }





    override fun generateLayoutParams(attrs: AttributeSet?): LayoutParams {
        return MarginLayoutParams(context,attrs)
    }


}
  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值