通过第三个将一个位图合并到另一个

Posted

技术标签:

【中文标题】通过第三个将一个位图合并到另一个【英文标题】:Merge one bitmap to another via the third 【发布时间】:2021-06-16 09:05:49 【问题描述】:

我有两张图片——一张(“背面”)显示为背景,另一张(“棒”)用户拖动。 “返回”显示有一些缩放(图像视图上的 match_parent),因此实际上有 3 个图像在播放。我需要将“stick”应用到第三个(原始)图像的位置,与它显示在“背面”上的位置完全相同。我试过用矩阵来做,但手动计算偏移量更幸运,但这仍然不够,因为出现了一些奇怪的偏移量,“棒”是左边的一些像素。这甚至不是说如果图像更水平,它就不起作用。这是我的计算方法:

val stickerBitmap = stickerView.drawToBitmap().trimBorders(Color.argb(0, 0, 0, 0))
val originalBitmap = fa
var purePageView = pageView.drawToBitmap()
val displayedBitmap = pageView.drawToBitmap().trimBorders(Color.argb(0, 0, 0, 0))
var (h1, w1) = stickerView.bounds
w1 -= binding.toolbar.height + binding.pageView.marginTop
h1 -= (binding.pageView.marginStart + binding.pageView.marginEnd + (purePageView.width - displayedBitmap.width)/2)
val x = originalBitmap.height
val y = originalBitmap.width
val x1 = displayedBitmap.height
val y1 = displayedBitmap.width
val x2 = stickerBitmap.height
val y2 = stickerBitmap.width
val h = h1 * y / y1.toFloat()
val w = x * w1 / x1.toFloat()
val x3 = x2 * x / x1
val y3 = y2 * y / y1
val scaledSticker2 = Bitmap.createScaledBitmap(stickerBitmap, y3, x3, true)
val resultBitmap = Bitmap.createBitmap(
    originalBitmap.width,
    originalBitmap.height,
    Bitmap.Config.ARGB_8888
)
val resultCanvas = Canvas(resultBitmap)
val paint = Paint()
var cf = PorterDuffColorFilter(Color.argb(255,0,255,0), PorterDuff.Mode.SRC_IN)
paint.colorFilter = cf
resultCanvas.drawBitmap(originalBitmap, 0f, 0f, null)

cf = PorterDuffColorFilter(Color.argb(255,0,255,255), PorterDuff.Mode.SRC_IN)
paint.colorFilter = cf
resultCanvas.drawBitmap(scaledSticker2, h + binding.pageView.marginStart, w+abs(binding.pageView.marginTop-binding.pageView.marginBottom), paint)

cf = PorterDuffColorFilter(Color.argb(255,0,123,123), PorterDuff.Mode.SRC_IN)
paint.colorFilter = cf
resultCanvas.drawBitmap(scaledSticker2, h + binding.pageView.marginStart, w+abs(binding.pageView.marginTop-binding.pageView.marginBottom), paint)

trimBorders 的代码来自 here。可能缺少什么?有没有完全不同的方法?

【问题讨论】:

【参考方案1】:

最后,需要减去图像视图和父视图之间的任何额外空间以及视图和图像之间的图像视图内部的额外空间。我修改trimBitmap 也返回找到的图像顶部和左侧线,并缩放减法的结果。

val originalBitmap = BitmapFactory.decodeFile(
    File(
        context.filesDir,
        originalName
    ).path,
    BitmapFactory.Options().apply  inPreferredConfig = Bitmap.Config.ARGB_8888 )
val swb = IntArray(2)
val stickerBitmap = stickerView.drawToBitmap().trimBorders(Color.argb(0, 0, 0, 0), swb)
val displayedBitmap = pageView.drawToBitmap().trimBorders(Color.argb(0, 0, 0, 0))
val (w1, h1) = swb
val wB = (pageView.width - displayedBitmap.width) / 2
val hB = (pageView.height - displayedBitmap.height) / 2
val x = originalBitmap.height
val y = originalBitmap.width
val x1 = displayedBitmap.height
val y1 = displayedBitmap.width
val x2 = stickerBitmap.height
val y2 = stickerBitmap.width
val h = (h1 - (toolbar.height + pageView.marginTop + hB)) * y / y1.toFloat()
val w = x * (w1 - (wB + pageView.marginStart)) / x1.toFloat()
val x3 = x2 * x / x1
val y3 = y2 * y / y1
val scaledSticker2 = Bitmap.createScaledBitmap(stickerBitmap, y3, x3, true)
val resultBitmap = Bitmap.createBitmap(
    originalBitmap.width,
    originalBitmap.height,
    Bitmap.Config.ARGB_8888
)
val resultCanvas = Canvas(resultBitmap)

resultCanvas.drawBitmap(originalBitmap, 0f, 0f, null)
resultCanvas.drawBitmap(scaledSticker2, w, h, null)

【讨论】:

以上是关于通过第三个将一个位图合并到另一个的主要内容,如果未能解决你的问题,请参考以下文章

将一个位图复制到另一个保留透明度

在 Android 上将大型位图文件调整为缩放的输出文件

在excel中如何将第一个工作表中的数据求和汇总到另一个表中

SQL - 如何避免将三个查询合并为一个

如何把两个完全相同的mysql数据库合并到另一个数据库中

试图将三个参数从一个 php 文件传递​​到另一个