Re: How to display a DIB or draw it into a Bitmap
- From: " active" <activeNOSPAM@xxxxxxxxxx>
- Date: Fri, 20 Jul 2007 18:49:04 -0400
"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 aI read that.
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.
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 = Marshal.SizeOf(BmH) + CInt(BiSize)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
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
.
- Follow-Ups:
- Re: How to display a DIB or draw it into a Bitmap
- From: Michael Phillips, Jr.
- Re: How to display a DIB or draw it into a Bitmap
- References:
- How to display a DIB or draw it into a Bitmap
- From: active
- Re: How to display a DIB or draw it into a Bitmap
- From: Michael Phillips, Jr.
- Re: How to display a DIB or draw it into a Bitmap
- From: active
- Re: How to display a DIB or draw it into a Bitmap
- From: Michael Phillips, Jr.
- Re: How to display a DIB or draw it into a Bitmap
- From: Michael Phillips, Jr.
- Re: How to display a DIB or draw it into a Bitmap
- From: active
- Re: How to display a DIB or draw it into a Bitmap
- From: Michael Phillips, Jr.
- Re: How to display a DIB or draw it into a Bitmap
- From: active
- Re: How to display a DIB or draw it into a Bitmap
- From: Michael Phillips, Jr.
- Re: How to display a DIB or draw it into a Bitmap
- From: active
- Re: How to display a DIB or draw it into a Bitmap
- From: active
- Re: How to display a DIB or draw it into a Bitmap
- From: Michael Phillips, Jr.
- Re: How to display a DIB or draw it into a Bitmap
- From: active
- Re: How to display a DIB or draw it into a Bitmap
- From: Michael Phillips, Jr.
- How to display a DIB or draw it into a Bitmap
- Prev by Date: RE: VB Union with byte array problem
- Next by Date: Re: Questions about StructLayout Pack values
- Previous by thread: Re: How to display a DIB or draw it into a Bitmap
- Next by thread: Re: How to display a DIB or draw it into a Bitmap
- Index(es):
Relevant Pages
|