Loading bitmap from stream

G

Guest

Hi
I'm trying to load a bitmap from a stream using the appropriate constructor, but consistently get an exception of type system.ArgumentException. Loading the bitmap from file seems to also produce the same exception. There doesn't appear to be anything wrong with the bitmap, as it is viewable in MSPaint on the desktop
The lines that throw the exception are (from file)

bmImage = new Bitmap("/test.bmp")

or (from stream)
byte[] baFileBytes = foo; //fills in byte array with bitma
MemoryStream iStream = new MemoryStream(baFileBytes)
bmImage = new Bitmap(tempStream)

Any idea why this exception is being thrown? Is there a restriction on the bitmap types that can be loaded
Thanks
Adam
 
A

Alex Yakhnin [MVP]

What device is that?

--
--
Alex Yakhnin .NET CF MVP
www.intelliprog.com | www.opennetcf.org

Adam said:
Hi,
I'm trying to load a bitmap from a stream using the appropriate
constructor, but consistently get an exception of type
system.ArgumentException. Loading the bitmap from file seems to also produce
the same exception. There doesn't appear to be anything wrong with the
bitmap, as it is viewable in MSPaint on the desktop.
The lines that throw the exception are (from file):

bmImage = new Bitmap("/test.bmp");

or (from stream):
byte[] baFileBytes = foo; //fills in byte array with bitmap
MemoryStream iStream = new MemoryStream(baFileBytes);
bmImage = new Bitmap(tempStream);

Any idea why this exception is being thrown? Is there a restriction on the
bitmap types that can be loaded?
 
G

Guest

Device is PocketPC 2003 on hp iPaq, but exact same problem also arises on PPC 2003 emulator and PPC 2003 on dell axim
adam
 
G

Guest

I have made some progress on this
The reason that the bitmap was not loading was that it was 16 bits per pixel rather than 24 bits per pixel. It appears that whilst the compact framework stores bitmaps (drawn within cf application as graphics) in memory as 16bpp, it cannot read in this format. This exposes my main issue, as i am trying to load a bitmap into an html control, from a stream
I currently create a new bitmap from the stream (which works if it is 24bpp), access the underlying DIBSECTION and fill the hBitmap from this in to an INLINEIMAGEINFO struct that I then send in a message to the HTML control. However, this is not producing a result (no image or red cross is shown in the control)
Does anyone know if there are restrictions on the format (esp. in terms of bits per pixel) of the hBitmap that must be passed in the INLINEIMAGEINFO struct
Am i referencing this hBitmap correctly

Thanks
Ada

Code sample is (also uses OpenNETCF.WinAPI.Core library from OpenNETCF.org)

static CallThunk m_ct
protected virtual int OnNotifyMessage(ref Message m

int iRetval = 0
HtmlViewMessage hvm
NmHdr hdr = NmHdr.GetStruct(m.LParam)
switch (hdr.code

case NM_INLINE_IMAGE
hvm = HtmlViewMessage.GetStruct(m.LParam)
string target = hvm.target.Substring(7, hvm.target.Length - 7);//strip "file://" from star
if(true)//image needs handlin

tr

//load image represented by hvm.targe
using( FileStream fsFileHandle = File.Open(target, System.IO.FileMode.Open)

FileStream tempStream = new FileStream("/test.bmp", System.IO.FileMode.Open)
bmImage = new Bitmap(tempStream); //or new Bitmap("/test.bmp")

if(bmImage==null

throw new Exception("Image failed to load.")

else //image successfully loade

InMemoryBitmap imb = new InMemoryBitmap()
// Get required Win32 callback
if ( m_ct == null

IntPtr hMod = Core.GetModuleHandle("mscoree1_0")
if ( hMod == IntPtr.Zero

throw new Exception("Failed to get at hBitmap object.");

IntPtr pfn = Core.GetProcAddress(hMod, "NSLHandle_Reference")
m_ct = new CallThunk(pfn, 2)


// Extract internal data into InMemoryBitmap object
IntPtr pObj = m_ct.Call(new int[] { 0x11, Image.GetHowFromImage(bmImage).ToInt32() } )
pObj = new IntPtr( Marshal.ReadInt32(pObj) )
Marshal.PtrToStructure(pObj, imb)
imgInfo.dwCookie = hvm.dwCookieFlags
imgInfo.iOrigHeight = imb.cx;//widt
imgInfo.iOrigWidth = imb.cy;//heigh
imgInfo.hBitmap = imb.hBitmap
imgInfo.bOwnBitmap = false;//instructs htmlview to make own cop
SendMessage(_hwnd, (uint)DTM_SETIMAGE, (uint)0, ref imgInfo)


catch(Exception ex

SendMessageLong(_hwnd, (IntPtr)DTM_IMAGEFAIL, (IntPtr)0, (IntPtr)(hvm.dwCookieFlags >> 8))

iRetval = -1

els

iRetval = 0; //default: let control handle i

break

return iRetval


private class InMemoryBitma

internal uint dword1
public IntPtr hMemoryDC
internal uint dword2
internal uint dword3
internal uint dword4
internal uint dword5
internal uint dword6
public IntPtr hBitmap
public int cx
public int cy


internal struct InlineImageInf

internal UInt32 dwCookie
internal int iOrigHeight
internal int iOrigWidth
internal IntPtr hBitmap
internal bool bOwnBitmap
}
 
G

Geoff Schwab [MSFT]

Hi Adam,

I have used 16 bpp bitmaps successfully but I think there is a bit of a
trick to it. The "standards" on 16 bpp bitmaps are a bit ambiguous and I
believe that only 555 RGB formatted bitmaps are supported even though these
are technically supposed to be described as 15 bpp - according to some
standards I have seen. I think you also have to have compression set to 0
even though you would think that there should be a bitmaks description.

Take a look at the following sample, it creates and loads 16 bpp bitmaps.
Not that the DIB section bmps are treated differently and actually do have a
compression setting:

Saving a Control Image to a Bitmap File
http://msdn.microsoft.com/library/en-us/dnnetcomp/html/scibf.asp

--
Geoff Schwab
Program Manager
Excell Data Corporation
http://msdn.com/mobility
http://msdn.microsoft.com/mobility/prodtechinfo/devtools/netcf/FAQ/default.aspx

This posting is provided "AS IS" with no warranties, and confers no rights.

adam said:
I have made some progress on this:
The reason that the bitmap was not loading was that it was 16 bits per
pixel rather than 24 bits per pixel. It appears that whilst the compact
framework stores bitmaps (drawn within cf application as graphics) in memory
as 16bpp, it cannot read in this format. This exposes my main issue, as i am
trying to load a bitmap into an html control, from a stream.
I currently create a new bitmap from the stream (which works if it is
24bpp), access the underlying DIBSECTION and fill the hBitmap from this in
to an INLINEIMAGEINFO struct that I then send in a message to the HTML
control. However, this is not producing a result (no image or red cross is
shown in the control).
Does anyone know if there are restrictions on the format (esp. in terms of
bits per pixel) of the hBitmap that must be passed in the INLINEIMAGEINFO
struct?
Am i referencing this hBitmap correctly?

Thanks,
Adam

Code sample is (also uses OpenNETCF.WinAPI.Core library from OpenNETCF.org):

static CallThunk m_ct;
protected virtual int OnNotifyMessage(ref Message m)
{
int iRetval = 0;
HtmlViewMessage hvm;
NmHdr hdr = NmHdr.GetStruct(m.LParam);
switch (hdr.code)
{
case NM_INLINE_IMAGE:
hvm = HtmlViewMessage.GetStruct(m.LParam);
string target = hvm.target.Substring(7, hvm.target.Length - 7);//strip "file://" from start
if(true)//image needs handling
{
try
{
//load image represented by hvm.target
using( FileStream fsFileHandle = File.Open(target, System.IO.FileMode.Open) )
{
FileStream tempStream = new FileStream("/test.bmp", System.IO.FileMode.Open);
bmImage = new Bitmap(tempStream); //or new Bitmap("/test.bmp");
}
if(bmImage==null)
{
throw new Exception("Image failed to load.");
}
else //image successfully loaded
{
InMemoryBitmap imb = new InMemoryBitmap();
// Get required Win32 callback.
if ( m_ct == null )
{
IntPtr hMod = Core.GetModuleHandle("mscoree1_0");
if ( hMod == IntPtr.Zero )
{
throw new Exception("Failed to get at hBitmap object.");
}
IntPtr pfn = Core.GetProcAddress(hMod, "NSLHandle_Reference");
m_ct = new CallThunk(pfn, 2);
}

// Extract internal data into InMemoryBitmap object.
IntPtr pObj = m_ct.Call(new int[] { 0x11,
Image.GetHowFromImage(bmImage).ToInt32() } );
pObj = new IntPtr( Marshal.ReadInt32(pObj) );
Marshal.PtrToStructure(pObj, imb);
imgInfo.dwCookie = hvm.dwCookieFlags;
imgInfo.iOrigHeight = imb.cx;//width
imgInfo.iOrigWidth = imb.cy;//height
imgInfo.hBitmap = imb.hBitmap;
imgInfo.bOwnBitmap = false;//instructs htmlview to make own copy
SendMessage(_hwnd, (uint)DTM_SETIMAGE, (uint)0, ref imgInfo);
}
}
catch(Exception ex)
{
SendMessageLong(_hwnd, (IntPtr)DTM_IMAGEFAIL, (IntPtr)0,
(IntPtr)(hvm.dwCookieFlags >> 8));
 

Ask a Question

Want to reply to this thread or ask your own question?

You'll need to choose a username for the site, which only take a couple of moments. After that, you can post your question and our members will help you out.

Ask a Question

Top