B4J Question Remove background png

angel_

Well-Known Member
Licensed User
Longtime User
How can I remove the white background from an image? I have tried this but it doesn't work:

B4X:
Private Sub Button1_Click
    Dim efecto As BitmapCreatorEffects
    efecto.Initialize
    
    Dim bmp As B4XBitmap = xui.LoadBitmap(File.DirAssets, "test0.png")
    Dim bmp_transparent As B4XBitmap = efecto.ReplaceColor(bmp, xui.Color_White, xui.Color_Transparent, False)
    
    xui.SetDataFolder("test_img")
    Dim Out As OutputStream
    Out = File.OpenOutput(xui.DefaultFolder, "bmp_transparent.png", False)
    bmp_transparent.WriteToStream(Out, 100, "PNG")
End Sub
 

Attachments

  • Project.zip
    22.2 KB · Views: 166
Solution
Besides this, I fear there is a bug in the ReplaceColor Sub in the B4XBitmapEffects library, because, despite what is drawn, the final saved file has no alpha replacement at all (always keeps the original)

Original (as I understand it, it has a bug)
B4X:
'Replaces OldColor with NewColor.
'KeepAlphaLevel - If true then the alpha level of the source color is kept.
Public Sub ReplaceColor (bmp As B4XBitmap, OldColor As Int, NewColor As Int, KeepAlphaLevel As Boolean) As B4XBitmap
    Dim bc As BitmapCreator = CreateBC(bmp)
    Dim oldargb, newargb, a As ARGBColor
    bc.ColorToARGB(OldColor, oldargb)
    bc.ColorToARGB(NewColor, newargb)
    For x = 0 To bc.mWidth - 1
        For y = 0 To bc.mHeight - 1
            bc.GetARGB(x, y, a)...

klaus

Expert
Licensed User
Longtime User
The problem is that in B4J drawing with a transparent color does nothing.
The only way, I know, is with a Canvas or B4XCanvas and Canvas.ClearRect.
In the attached project I added a Panel as a B4XView and a B4XCanvas.
First clearing the background and the using BitmapCreator.
I do not know if these does exist a more efficient was to do it.
Be aware that this works only of the background color is exactly white.
If any of the three RGB colors has value different from 255 it will be copied even if it looks like white.
You could eventually add a threshold.

Tested with B4J and B4A.

1640093846361.png
 

Attachments

  • RemoveBackground.zip
    55.2 KB · Views: 185
Last edited:
Upvote 0

JordiCP

Expert
Licensed User
Longtime User
Besides this, I fear there is a bug in the ReplaceColor Sub in the B4XBitmapEffects library, because, despite what is drawn, the final saved file has no alpha replacement at all (always keeps the original)

Original (as I understand it, it has a bug)
B4X:
'Replaces OldColor with NewColor.
'KeepAlphaLevel - If true then the alpha level of the source color is kept.
Public Sub ReplaceColor (bmp As B4XBitmap, OldColor As Int, NewColor As Int, KeepAlphaLevel As Boolean) As B4XBitmap
    Dim bc As BitmapCreator = CreateBC(bmp)
    Dim oldargb, newargb, a As ARGBColor
    bc.ColorToARGB(OldColor, oldargb)
    bc.ColorToARGB(NewColor, newargb)
    For x = 0 To bc.mWidth - 1
        For y = 0 To bc.mHeight - 1
            bc.GetARGB(x, y, a)
            If (KeepAlphaLevel Or a.a = oldargb.a) And a.r = oldargb.r And a.g = oldargb.g And a.b = oldargb.b Then   '<-- This is incorrect
                newargb.a = a.a
                bc.SetARGB(x, y, newargb)
            End If
        Next
    Next
    Return bc.Bitmap
End Sub


Correct version (add it to your project and call ReplaceColor2 in the project instead of efecto.ReplaceColor)
B4X:
'Replaces OldColor with NewColor.
'KeepAlphaLevel - If true then the alpha level of the source color is kept.
Public Sub ReplaceColor2 (bmp As B4XBitmap, OldColor As Int, NewColor As Int, KeepAlphaLevel As Boolean) As B4XBitmap
    Dim bc As BitmapCreator = efecto.CreateBC(bmp)
    Dim oldargb, newargb, a As ARGBColor
    bc.ColorToARGB(OldColor, oldargb)
    bc.ColorToARGB(NewColor, newargb)
    For x = 0 To bc.mWidth - 1
        For y = 0 To bc.mHeight - 1
            bc.GetARGB(x, y, a)
            If a.a = oldargb.a And a.r = oldargb.r And a.g = oldargb.g And a.b = oldargb.b Then    '<-- correct version
                If KeepAlphaLevel Then newargb.a = a.a
                bc.SetARGB(x, y, newargb)
            End If
        Next
    Next
    Return bc.Bitmap
End Sub
 
Upvote 0
Solution

angel_

Well-Known Member
Licensed User
Longtime User
Many thanks to both of you, they work very well, is there a way to better define the edges?

Captura.JPG
 
Upvote 0
Top