Results 1 to 15 of 15

Thread: Alpha Blending (Resolved & Updated)

  1. #1

    Thread Starter
    Lively Member
    Join Date
    Mar 2001
    Location
    Wisconsin
    Posts
    64

    Post Alpha Blending (Resolved & Updated)

    I was looking for a way to alpha blend a form (translucency, ie see-tru, not transparency) but was unable to find actual code that I thought worthy; so I made my own. It's kind of slow (calculating and drawing 38,912 pixels (152x256) takes an average of 3,305+-13ms using the Point method of 2 source PictureBoxes and 1 destination PictureBox) but it gives the desired effect. It's like stitching two images together. Attatched is my sample program that I am working on. It allows you to choose two source images (.bmp's) and create a third alpha blended picture with adjustable transparency. As I mentioned before, the code works good, but somewhat slowly (without drawing it takes 1,370+-2ms for 38,912 pixels (152x256) using the Point method). Take a look and tell me what you think.

    Another reason for this test is because I have WinME and I can't use SetLayeredWindowAttributes. This code does not make the form translucent but it is a step in the right direction (I feel). I am also wondering if using GetBitmapBits and SetBitmapBits could cut down the calculation and drawing times. If you come up with any improvements, please let me know so I can utilize them and improve my process.

    PS - If you do reply, do not e-mail me. My Hotmail Junk Filter is on exclusive (no one in my Contacts or Safe List gets to my Inbox) and Immediate Deletion (anything going to go to my Junk Mail folder is immediately deleted) so I will not recieve your e-mail. Either post a reply or send a Private Message.

    Attatchment deleted
    Last edited by lnelsestuen; Nov 6th, 2002 at 01:47 AM.

  2. #2
    Ex-Super Mod'rater Electroman's Avatar
    Join Date
    Sep 2000
    Location
    Newcastle, England
    Posts
    4,349
    Using the point as Pset method is the slowest method second is SetPixelV and GetPixel then its SetPixel and GetPixel and The fastest method would be to use a pointer. I have to say sorry for keep posting this but it quite simply is 10 -15 times faster.
    I made a well commented Example which your welcome to download from http://www.Electroman.co.uk/VBExampl...xelEditing.zip it explains how to use a pointer to edit a picture Pixel by Pixel in a byte array. I belive to Alpha blend the formula is:
    VB Code:
    1. FinalPixel = (AlphaValue * (Source + 256 - Destination)) / 256 + Destination - AlphaValue
    Source, Destination + FinalPixel are each the colors for each pixel.
    When your thread has been resolved please edit the original post in the thread ()
    and amend "-[RESOLVED]-" to the end of the title and change the icon to , Thank you.

    When posting Code use the [VBCode]Code Here[/VBCode] tags to be able to use the code highlighting.

  3. #3

    Thread Starter
    Lively Member
    Join Date
    Mar 2001
    Location
    Wisconsin
    Posts
    64
    I found a (somewhat) successful way using GetBitmapBits and SetBitmapBits takes an average of 14+-0ms (slightly faster than PSet) to calculate and draw the alpha blended picture. The problem is, if you are viewing the BMP Bits picture and switch to another window (one that covers up the alpha blended picture) and back, it displays the portion of the window that covered it up. My PictureBoxes have AutoRedraw=True and I use the Picture property to display the alpha blended result. Why am I getting this wierd "ghosting?" Attatched is the updated sample program with the BMP Bits feature.

    I belive to Alpha blend the formula is:
    I am using formulas from the MSDN in the description of the BLENDFUNCTION type which are as follows:
    • Dst.Red=Src1.Red*ConstantAlpha+(1-ConstantAlpha)*Src2.Red
    • Dst.Green=Src1.Green*ConstantAlpha+(1-ConstantAlpha)*Src2.Green
    • Dst.Blue=Src1.Blue*ConstantAlpha+(1-ConstantAlpha)*Src2.Blue

    where ConstantAlpha is the transparency percentage (as a decimal, ie 50% transparency=50/100=.5)
    As I mentioned in my first post, these formulas do work. And using the GetBitmapBits and SetBitmapBits gives HUGE TIME IMPROVEMENT, but I get the wierd "ghosting" when switching to another window.
    Any suggestions?

    Attatchment deleted
    Last edited by lnelsestuen; Nov 6th, 2002 at 01:42 AM.

  4. #4
    Good Ol' Platypus Sastraxi's Avatar
    Join Date
    Jan 2000
    Location
    Ontario, Canada
    Posts
    5,134
    If you are developing for Win2k/XP, these have partial blending functions built in. And when you get focus, use the Refresh method of your pictureboxes.
    All contents of the above post that aren't somebody elses are mine, not the property of some media corporation.
    (Just a heads-up)

  5. #5

    Thread Starter
    Lively Member
    Join Date
    Mar 2001
    Location
    Wisconsin
    Posts
    64
    Originally posted by Sastraxi
    If you are developing for Win2k/XP, these have partial blending functions built in. And when you get focus, use the Refresh method of your pictureboxes.
    As I mentioned in my first post, I have WinME so the blending functions (ie SetLayeredWindowAttributes) are not available.

  6. #6
    Good Ol' Platypus Sastraxi's Avatar
    Join Date
    Jan 2000
    Location
    Ontario, Canada
    Posts
    5,134
    Sorry, didn't see that. Did the refresh bit help with the applications over your form problem?
    All contents of the above post that aren't somebody elses are mine, not the property of some media corporation.
    (Just a heads-up)

  7. #7

    Thread Starter
    Lively Member
    Join Date
    Mar 2001
    Location
    Wisconsin
    Posts
    64
    No. I found some major underlying problems. Technically my code for the GetBitmapBits and SetBitmapBits actually doesn't work. One major problem is that the bitmaps aren't the same size and therefore the algorithm combines bits that shouldn't be combined. Major tweaking to be done. Thanks anyway.

    You can still check out the attatchment from my first post to see the working code using the Point & PSet methods. Like I said, it's slow, but it actually works.

  8. #8
    Addicted Member jmiller's Avatar
    Join Date
    Jul 2002
    Location
    University of Michigan
    Posts
    238
    i'm not sure if this works with ME, but there is an api function called AlphaBlend

  9. #9

    Thread Starter
    Lively Member
    Join Date
    Mar 2001
    Location
    Wisconsin
    Posts
    64
    Originally posted by jmiller
    i'm not sure if this works with ME, but there is an api function called AlphaBlend
    Accroding to AllAPI.net 's API-Guide, it is available on WinME (and according to MS Visual Studio's Dependency Viewer, it is there). I tried it once and couldn't get it to work, but I didn't play with it much. It might work, but I didn't take the time to debug my simple test. Thanks for reminding me, though. I forgot about it but I think I will play with it for a while.

  10. #10
    Good Ol' Platypus Sastraxi's Avatar
    Join Date
    Jan 2000
    Location
    Ontario, Canada
    Posts
    5,134
    You have to jam in a complicated struct. Go to allapi.net and look around there, and it'll show you how to return the pointer to the struct to the function (blendparams I think).
    All contents of the above post that aren't somebody elses are mine, not the property of some media corporation.
    (Just a heads-up)

  11. #11
    Addicted Member jmiller's Avatar
    Join Date
    Jul 2002
    Location
    University of Michigan
    Posts
    238
    i've used it once, based on the example used in allapi.net's tutorial, and got it to work, and i think the UDT has just four items, but you have to convert it to a long using another API (CopyMemory, i think). otherwise, its parameters are fairly similar to bitblt, if you know that one

  12. #12
    Good Ol' Platypus Sastraxi's Avatar
    Join Date
    Jan 2000
    Location
    Ontario, Canada
    Posts
    5,134
    Yes, that's right, not VarPtr but CopyMemory... Anyway, it's very fast, once you have it you shouldn't have any troubles..
    All contents of the above post that aren't somebody elses are mine, not the property of some media corporation.
    (Just a heads-up)

  13. #13

    Thread Starter
    Lively Member
    Join Date
    Mar 2001
    Location
    Wisconsin
    Posts
    64

    Talking IT WORKS! IT WORKS!

    GOT IT TO WORK. I used the same example from API-Guide (they actually use RtlMoveMemory, basically the same as CopyMemory). The reason I couldn't get it to work before is because of the ByRef argument:
    VB Code:
    1. Private Declare Function AlphaBlend Lib "msimg32.dll" (ByVal hdc As Long, _
    2.   ByVal lInt As Long, ByVal lInt As Long, ByVal lInt As Long, ByVal lInt As Long, _
    3.   ByVal hdc As Long, ByVal lInt As Long, ByVal lInt As Long, ByVal lInt As Long, _
    4.   ByVal lInt As Long, [B]ByRef BLENDFUNCT As BLENDFUNCTION[/B]) As Long
    5. 'examining the API-Guide example, they use the declaration
    6. Private Declare Function AlphaBlend Lib "msimg32.dll" (ByVal hdc As Long, _
    7.   ByVal lInt As Long, ByVal lInt As Long, ByVal lInt As Long, ByVal lInt As Long, _
    8.   ByVal hdc As Long, ByVal lInt As Long, ByVal lInt As Long, ByVal lInt As Long, _
    9.   ByVal lInt As Long, [B]ByVal BLENDFUNCT As Long[/B]) As Long
    Apparently the AlphaBlend function does not work with ByRef BLENDFUNCT. I don't know why, but I know that when I changed my declaration (and used RtlMoveMemory to copy the BLENDFUNCTION parameters to a long) that the AlphaBlend function works. I made a different program to test AlphaBlend (which now works) and TransparentBlt. It's a pretty bare program, but now I know (and you can find out) how to use it.
    The code isn't commented, but I think most of you should be able to figure it out. If you have a question, just post it.
    Attached Files Attached Files
    Last edited by lnelsestuen; Nov 6th, 2002 at 02:22 AM.

  14. #14

    Thread Starter
    Lively Member
    Join Date
    Mar 2001
    Location
    Wisconsin
    Posts
    64

    Wink PS

    I deleted the previous attatchments because they were junk and didn't need to be wasting space on the server. Also, when I was debugging my algorithms using Get/SetBitmapBits, I found that it was (at first) actually only calculating 1 or 2 pixels, not the entire picture. When it was finally calculating the full picture, it took about half a second to do, but as I mentioned in an earlier post, it was combining bits that shouldn't have been combined, so the picture looked a little funky. If you are still interested in the Point/PSet methods I described (for understanding how alpha blending works, what it is, etc), just give me a hollar.

  15. #15
    Good Ol' Platypus Sastraxi's Avatar
    Join Date
    Jan 2000
    Location
    Ontario, Canada
    Posts
    5,134
    I was looking at your alphablending algorithm and i must give you a 'tut, tut' for that. You see, there's a much faster way of doing it:
    VB Code:
    1. TempR = (aRGB.R * CLng(sRGB.R + 256 - dRGB.R)) / 256 + dRGB.R - aRGB.R
    2.             TempG = (aRGB.G * CLng(sRGB.G + 256 - dRGB.G)) / 256 + dRGB.G - aRGB.G
    3.             TempB = (aRGB.B * CLng(sRGB.B + 256 - dRGB.B)) / 256 + dRGB.B - aRGB.B
    aRGB is the alpha (0 to 255), sRGB is the source (0 to 255), and dRGB is the destination (0 to 255). Doing it this way works much faster because there is only one division and it never uses floating point numbers.
    All contents of the above post that aren't somebody elses are mine, not the property of some media corporation.
    (Just a heads-up)

Posting Permissions

  • You may not post new threads
  • You may not post replies
  • You may not post attachments
  • You may not edit your posts
  •  



Click Here to Expand Forum to Full Width