Android 绘制视图和所有视图';孩子们

Android 绘制视图和所有视图';孩子们,android,android-canvas,android-view,Android,Android Canvas,Android View,我正在尝试对视图组应用视觉效果。我的想法是抓取视图组的位图,将其缩小,再将其向上展开,然后在视图组上绘制,使其具有块状、低质量的效果 我已经掌握了使用此代码的大部分方法: public class Blocker { private static final float RESAMPLE_QUALITY = 0.66f; // less than 1, lower = worse quality public static void block(Canvas canvas,

我正在尝试对视图组应用视觉效果。我的想法是抓取视图组的位图,将其缩小,再将其向上展开,然后在视图组上绘制,使其具有块状、低质量的效果

我已经掌握了使用此代码的大部分方法:

public class Blocker {

    private static final float RESAMPLE_QUALITY = 0.66f; // less than 1, lower = worse quality


    public static void block(Canvas canvas, Bitmap bitmap_old) {
        block(canvas, bitmap_old, RESAMPLE_QUALITY);
    }


    public static void block(Canvas canvas, Bitmap bitmap_old, float quality) {
        Bitmap bitmap_new = Bitmap.createScaledBitmap(bitmap_old, Math.round(bitmap_old.getWidth() * RESAMPLE_QUALITY), Math.round(bitmap_old.getHeight() * RESAMPLE_QUALITY), true);
        Rect from = new Rect(0, 0, bitmap_new.getWidth(), bitmap_new.getHeight());
        RectF to = new RectF(0, 0, bitmap_old.getWidth(), bitmap_old.getHeight());
        canvas.drawBitmap(bitmap_new, from, to, null);
    }
}
我只需在画布上传递一个需要放大和缩小的位图,效果很好

public class BlockedLinearLayout extends LinearLayout {

    private static final String TAG = BlockedLinearLayout.class.getSimpleName();


    public BlockedLinearLayout(Context context, AttributeSet attrs) {
        super(context, attrs);
        applyCustomAttributes(context, attrs);
        setup();
    }


    public BlockedLinearLayout(Context context) {
        super(context);
        setup();
    }


    private void setup() {
        this.setDrawingCacheEnabled(true);
    }


    @Override
    public void draw(Canvas canvas) {
        super.draw(canvas);
        // block(canvas); If I call this here, it works but no updates
    }


    @Override
    public void onDraw(Canvas canvas) {
        // block(canvas); If I call this here, draws behind children, still no updates
    }

    private void block(Canvas canvas) {
        Blocker.block(canvas, this.getDrawingCache());
    }
}
我遇到的问题是在我的视图组中。如果在视图组的绘制中运行块方法,它将绘制所有内容,但不会在子视图更改时更新。我用Log跟踪函数调用,draw方法似乎正在运行,但没有任何变化

我还尝试在onDraw中实现这一点。这会在所有子视图后面绘制位图,并且它们也不会更新

有人能解释一下我将如何解决这个问题吗?

试试这个:

@Override
protected void dispatchDraw(Canvas canvas) {
    // call block() here if you want to draw behind children
    super.dispatchDraw(canvas);
    // call block() here if you want to draw over children
}
并调用destroyDrawingCache(),然后在每次更改子项时都调用buildDrawingCache()。

Draw()
方法将非常适合您


我现在试着做一个圆形的计数时间视图,当时间流逝时,视图会缩小角度。用于覆盖个人资料照片(圆形照片)。

谢谢您的建议。不幸的是,这适用于在所有子对象之上进行绘制,但是如果在初始绘制之后更新子对象,则不会更新视图。例如,我有一个线性布局,有一个文本视图,从1开始,每秒递增。我可以看到数字在计数,但linearlayout只是用1绘制,然后没有更改。请尝试调用destroyDrawingCache(),然后在每次更改子项时调用buildDrawingCache()。谢谢!这似乎很有效。我将对它进行一些讨论,但是您知道是否有任何方法可以从父视图中检测子视图的更改吗?我希望能够让父视图自动处理它的所有子视图的更改,而不是每次我做某件事时显式地告诉父视图组重新设置。嗯。。。我觉得您必须重写您孩子的invalidate(),并通知viewGroup重新创建其缓存。