Re: How to display a DIB or draw it into a Bitmap

Tech-Archive recommends: Repair Windows Errors & Optimize Windows Performance




"Michael Phillips, Jr." <mphillips53@xxxxxxxxxxxxxxx> wrote in message
news:OS$lKHxyHHA.1072@xxxxxxxxxxxxxxxxxxxxxxx
Make sense to you?

Yes.

When you marshal between managed and unmanaged code this type of alignment
issue can easily cause you headaches.

The correct calculation of the offset for .bfOffBits is important. I
have seen code on the internet that doesn't even look at it.
It assumes that the structures are laid out one after the other with the
bitmap's bits following the structures, which is not necessarily correct.

Isn't that what I'm doing unless BiCompression=BI_BITFIELDS?
Is that when it is not correct?

If you want to use memory mapped files for very large bitmaps and pass a
hSection to a memory mapped file
and dwOffset for the bits to CreateDIBSection, the documentation states
that the dwOffset passed must be located
on a DWORD boundary.
I read that.


If you do not align on a DWORD boundary, the bits would be located at an
offset that is off by 2 bytes.
CreateDIBSection would fail!

For a 16bpp, 24bpp or 32bpp bitmap:
BITMAPFILEHEADER 14 bytes
BITMAPINFOHEADER 40 bytes
bits <---------------------54 this offset is off by two.
bits<----------------------56 this offset is aligned on a DWORD boundary.

I'm sorry, I can't follow this. Isn't 14 and 54 the correct values.
And my bfOffBits points to a location not on a DWORD boundary.

I think "bits <---------------------54 " means bfOffBits contains 54.
Right?

Then containing 56 does point to a DWORD boundary.
But 56 is the wrong value.

Guess I'm confused.






If you loaded a bitmap that was aligned this way and did not check the
.bfOffBits offset,
CreateDIBSection would fail!

The moral to the above is assume nothing. Always check!

While searching the Internet I noticed that you have been helping people
for years!

I am happy to provide assistance.


" active" <activeNOSPAM@xxxxxxxxxx> wrote in message
news:%23x%23Mv$vyHHA.748@xxxxxxxxxxxxxxxxxxxxxxx
I changed the code below to
BmH.bfOffBits = Marshal.SizeOf(BmH) + CInt(BiSize)

When checking I noticed that Marshal.SizeOf(BmH) returned 16!

So to the structure I added:
<StructLayout(LayoutKind.Sequential, Pack:=2)> _

which fixed it (to 14).

But raised the question how come it worked with 16?

I guess the reason why it worked with 16 is because I wrote the items to
the stream, one at a time rather than writing the structure.

But if the structures were the correct size and bfOffBits pointed wrong,
I believe the first 2 bytes of the data would be skipped over.



Make sense to you?



While searching the Internet I noticed that you have been helping people
for years!

Thanks, took a while for this loop to converge

BTW Even though Visual Basic compiler specifies Sequential layout for
value types, it would not accept Pack without Sequential being
explicitly included in the statement.




"Michael Phillips, Jr." <mphillips53@xxxxxxxxxxxxxxx> wrote in message
news:eJJjviuyHHA.464@xxxxxxxxxxxxxxxxxxxxxxx
BmH.bfOffBits = CInt(14 + BiSize)

It is not a good practice to hard code a structure's size(e.g.,
BITMAPFILEHEADER).

You can never be sure that the structure will always compile to that
size(i.e., 14 bytes) unless you lay it out explicitly(i.e., byte align)
or that Microsoft will not change the structure.

Other than that, I recommend that you test your code with other
applications that place/retrieve DIBs on the clipboard(e.g., Office,
Paint, Photoshop, etc.)
You can use the free clipboard viewer as a comparison to demonstrate
that your code get's the expected result. The other applications can be
used to test
whether or not the Dibs that your save as a file can be opened and
displayed properly.

" active" <activeNOSPAM@xxxxxxxxxx> wrote in message
news:O$YHNbtyHHA.1212@xxxxxxxxxxxxxxxxxxxxxxx
The code below is hopefully a mapping of comments by Michael Phillips,
Jr.

Michael, do you agree it is OK.

If so, I'd suggest that someone with a vb.net site copy it and also
find Michael's post relating to putting/retrieving a palette on/from
the clipboard.

Both examples are complete and do not appear anywhere else. It would be
nice to save them!


Thanks again to Michael!

'Offset, in bytes, from the BITMAPFILEHEADER structure to the bitmap
bits

BmH.bfOffBits = Marshal.SizeOf(BmH) + CInt(BiSize)

If BiBitCount <= 8 Then

If BiClrUsed = 0 Then

'If biClrUsed = 0 then the bitmap uses the maximum number of
colors

BmH.bfOffBits += 4 * (1 << BiBitCount) 'color size * max colors

Else

BmH.bfOffBits += 4 * CInt(BiClrUsed) 'color size * NColors

End If

ElseIf BiBitCount = 24 Then

'no palette so add nothing here

Else 'must be (BiBitCount = 16 Or BiBitCount = 32)

If BiCompression = BI_BITFIELDS Then

BmH.bfOffBits += 12 '3 RGB doubleword masks

Else

'no masks so add nothing here

End If

End If

BmH.bfSize = CInt(BmH.bfOffBits + DibClipboardStream.Length) ' size of
file











.



Relevant Pages

  • Re: How to display a DIB or draw it into a Bitmap
    ... The correct calculation of the offset for .bfOffBits is important. ... If you want to use memory mapped files for very large bitmaps and pass a ... If you loaded a bitmap that was aligned this way and did not check the ...
    (microsoft.public.dotnet.languages.vb)
  • Re: How to display a DIB or draw it into a Bitmap
    ... Alignment on a DWORD boundary is only an issue if you ... want to use memory mapped bitmap files. ... The correct calculation of the offset for .bfOffBits is important. ...
    (microsoft.public.dotnet.languages.vb)
  • Re: How to display a DIB or draw it into a Bitmap
    ... you want to use memory mapped bitmap files. ... alignment issue can easily cause you headaches. ... The correct calculation of the offset for .bfOffBits is important. ...
    (microsoft.public.dotnet.languages.vb)
  • Re: CreateDIBSection with file mapping
    ... >>> I am creating a bitmap with CreateDIBSection, ... >> Here you don't specify the offset to the bits. ...
    (microsoft.public.win32.programmer.gdi)
  • Re: CreateDIBSection with file mapping
    ... I am creating a bitmap with CreateDIBSection, when I draw the bitmap some part of the bitmap from right is drawn on the left. ... OFSTRUCT ofstruct; HANDLE hfile=OpenFile; ... Here you don't specify the offset to the bits. ...
    (microsoft.public.win32.programmer.gdi)