LayerDrawable:这可以更有效地完成吗?

时间:2015-01-28 00:29:22

标签: android bitmap layerdrawable bitmapdrawable

我有ImageView,全宽和宽:高= 3:1,我们称之为1200 x 400.我想在Drawable中显示两个ImageView,这两者都只在运行时知道。其中一个drawables应根据“center-crop”放入ImageView(假设drawable有宽度:height> 3,这意味着宽度适合并且顶部和底部裁剪),另一个应该按照自定义因素进行居中和缩放。

我有一些代码可以做到这一点,但对我来说似乎不必要的复杂;当我从Bitmap创建新的LayerDrawable,然后从BitmapDrawable创建BitmapDrawable时,我才能按需要工作,并在LayerDrawable上再次设置所需的边界虽然我已经在LayerDrawable设置了边界 - 但是如果我不执行额外的步骤,那些边界就会被忽略。我更倾向于生成.setImageDrawable(),以便我可以在LayerDrawable中使用它,但我不知道如何使用它。如果我尝试Android会做什么对我没有任何意义。我做错了什么?

这就是我double divide(int k, int n) { return ((double)k)/n; } int verticalPaddingForHorizontalFit(int viewWidth, int viewHeight, int drawableWidth, int drawableHeight){ // you want to draw a drawable into a view, with an exact match in the width. Then either [1] or [2] // [1] the view is taller than the drawable (i.e., height/width bigger for the view) // --> method result is positive, // and gives the amount of padding top and bottom // [2] the drawable is taller // --> method result is negative, // and gives (minus) the amount that needs to be clipped from top and bottom // such that the drawable is vertically centered double viewAspect = divide(viewHeight, viewWidth ); double drawableAspect = divide(drawableHeight, drawableWidth); return (int)Math.round(0.5 * viewWidth * (viewAspect - drawableAspect)); } int[] paddingWhenCenteredAt(int viewWidth, int viewHeight, int drawableWidth, int drawableHeight, double drawableScale, int centerX, int centerY){ // scale the drawable with drawableScale, and put it into the view // such that the center of the drawable has coordinates (centerX, centerY) // return the padding needed as array of left, top, right, bottom, in that order // negative values indicating clipping instead of padding double w = drawableScale * drawableWidth; double h = drawableScale * drawableHeight; double left = centerX - 0.5*w; double right = viewWidth - (centerX + 0.5*w); double top = centerY - 0.5*h; double bottom = viewHeight - (centerY + 0.5*h); return new int[]{(int)Math.round(left), (int)Math.round(top), (int)Math.round(right), (int)Math.round(bottom)}; } LayerDrawable makeLayerDrawable(Resources r, int outputWidth, int outputHeight, Bitmap bm1, Bitmap bm2){ Drawable[] layers = new Drawable[2]; BitmapDrawable bmd1 = new BitmapDrawable(r, bm1); int width1 = bmd1.getIntrinsicWidth(); int height1 = bmd1.getIntrinsicHeight(); layers[0] = bmd1; BitmapDrawable bmd2 = new BitmapDrawable(r, bm2); int width2 = bmd2.getIntrinsicWidth(); int height2 = bmd2.getIntrinsicHeight(); layers[1] = bmd2; LayerDrawable result = new LayerDrawable(layers); int vPad = verticalPaddingForHorizontalFit(outputWidth, outputHeight, width1, height1); result.setLayerInset(0, 0, vPad, 0, vPad); int[] ltrb = paddingWhenCenteredAt(outputWidth, outputHeight, width2, height2, 0.5, outputWidth/2, outputHeight/2); result.setLayerInset(1, ltrb[0], ltrb[1], ltrb[2], ltrb[3]); result.setBounds(0, 0, outputWidth, outputHeight); return result; }

的方式
LayerDrawable

(我测试了Bitmap bm1 2400 x 1200像素和Bitmap bm2 800 x 300像素。)

现在,如果我只使用那个 myImageView.setImageDrawable(layd); ,就像这样

ImageView

LayoutParameters将没有所需的大小(高度更改。)如果我再次使用 LayerDrawable layd = makeLayerDrawable(r, outputWidth, outputHeight, bm1, bm2); Bitmap b = Bitmap.createBitmap(outputWidth, outputHeight, Bitmap.Config.ARGB_8888); Canvas canvas = new Canvas(b); layd.draw(canvas); BitmapDrawable result = new BitmapDrawable(getResources(), b); result.setBounds(0, 0, outputWidth, outputHeight); myImageView.setImageDrawable(result); 设置布局,我可以阻止它,但是,然后,drawables没有正确显示。相反,我这样做

{{1}}

它有效。

Here是github上的完整代码

1 个答案:

答案 0 :(得分:0)

我会考虑编写你自己的Drawable类,这看起来并不那么难。只需从Drawable扩展并覆盖draw(),您可以执行与剪切代码中相同的计算,只需绘制到具有所需宽高比的分层(堆叠)位图。 Canvas.drawBitmap()似乎适用于您的问题。