Re: OpenClipboard
- From: Joseph M. Newcomer <newcomer@xxxxxxxxxxxx>
- Date: Sat, 10 Jun 2006 01:54:38 -0400
See below...
On 8 Jun 2006 11:30:42 -0700, "Martin" <mrbiancu@xxxxxxxxx> wrote:
Hi, I have the following code:******
BOOL CVideo::CaptureFrame()
{
HBITMAP m_hBmp = NULL;
CBitmap m_bmp; //bitmap object
WHAT IS THIS NONSENSE???? YOU ARE DECLARING LOCAL VARIABLES AND NAMING THEM AS IF THEY
ARE CLASS MEMBER VARIABLES!!!!!! NEVER, NEVER, EVER DO SOMETHING THIS DUMB AND EXPECT
PEOPLE TO UNDERSTAND WHAT YOU ARE DOING!!! YOU HAVE VIOLATED FUNDAMENTAL NAMING
CONVENTIONS HERE!!!! NO WONDER YOUR CODE DOESN'T WORK!!!! If you don't understand what
the naming conventions mean, DON'T USE THEM!!!!!!!
*******
****
capGrabFrame(hWndC); // macro that sample a single frame from the
// camera.
capEditCopy(hWndC);
EmptyClipboard();// simple macro that edit a copy of the frame.
OpenClipboard();
// m_hBmp is a Handle to Bitmap.
m_hBmp = (HBITMAP)::GetClipboardData(CF_BITMAP);
CloseClipboard();
m_bmp.Detach(); //cleaning the bitmap.
m_bmp.Attach(m_hBmp); //connecting the bitmap throw the handle.
return true;
}
I call this function when i want to capture a frame. But, when I call
OpenClipboar, an assertion failure window is pop out, and the program
fails.
"AN assertion failure"? Give me a break! There is a VERY SPECIFIC ASSERTION FAILURE. IT
IDENTIFIES A FILE, A LINE OF CODE IN THAT FILE, AND THAT LINE OF CODE, WHEN EXAMINED, SAYS
SOMETHING ABOUT WHAT WAS BEING TESTED!!!!!!!!!
When reporting a bug, you have to REPORT the bug, not give a vague handwave about "my
program didn't work".
And what nonsense is "and the program fails"? No, it doesn't "fail" when there is an
assertion failure; it gives you an option of termination, an option of ignoring the error,
or an option of entering the debugger. None of these constitute "failure" by any stretch
of the imagination. If you choose to exit the program, that isn't a "failure", that is an
explicit request you made to exit the program!
By the way, I checked: the only reason OpenClipboard might have an assertion failure is if
the m_hWnd does not refer to a window. So if the m_hWnd isn't a window, your bug is
obvious. Fix it. You could have discovered this yourself in seconds just by entering the
debugger and looking at the code! Or you could have done what I just did, which was to
actually read the code of OpenClipboard, which would likewise make the error obvious. So
the question is why is this window handle invalid? You have to solve that first!
The code as shown makes no sense whatsoever, because you call EmptyClipboard before you
call OpenClipboard, while the documentation of EmptyClipboard very clearly states "Before
calling EmptyClipboard, an application must open the clipboard by calling the
OpenClipboard function".
Now, I have to admit that the documentation of capEditCopy/WM_CAP_EDIT_COPY, sets a new
low even by Microsoft's standards. It says it copies the contents of the video frame
buffer to the clipboard, but it doesn't mention what format it is in; so it is not clear
why you are assuming that it is in CF_BITMAP format. Did you verify this somehow? Did
you try using EnumClipboardFormats to see what formats were available?
UINT fmt = 0;
while(TRUE)
{
fmt = ::EnumClipboardFormags(fmt);
ASSERT(fmt != CF_BITMAP);
if(fmt == 0)
break;
}
and with the debugger you can see if there is a CF_BITMAP format (fmt == 2) or as I've
shown above, you'll take an ASSERT if there *is* a CF_BITMAP format. This would be a
quick test to see if there is any CF_BITMAP data actually in the clipboard after you have
done the capEditCopy operation. If there isn't, it is your responsibility to take
whatever format is there and convert it to bitmap format (probably GDI+ would be a place
to start looking in case it has something to convert whatever format is there to a bitmap,
or poke around on some of the places like www.codeproject.com)
By the way, capEditCopy is not a "simple macro that edits a copy of the frame", it is very
specifically described as a macro that makes a copy of the frame buffer data to the
clipboard; no editing appears to be involved. So your comments are also confusing and
misleading.
After opening the clipboard, you GetClipboardData of CF_BITMAP type, presumably after you
have emptied the clipboard, so if the code were rewritten to do the open/empty in the
correct order, GetClipboardData would return nothing meaningful. And because of the
inadequate documentation, it is not clear there would actually be any CF_BITMAP data in
the clipboard anyway.
But assuming you are trying to retrieve clipboard data, you DIDN'T CHECK TO SEE IF YOU GOT
A VALID VALUE! That is, you did not actually see if a bitmap was retrieved! So you have
no idea if m_hBmp is or is not NULL, which *might* explain an assertion failure later, and
would be perhaps obvious if you had actually reported what "an" assertion failure actually
was and where it occurred!
Then you wrote
m_bmp.Attach(m_hBmp);
You appear to be binding the HBITMAP to a member variable, which means that it might be
deleted, which is probably a Bad Idea, given that the clipboard still owns it. But due to
an obvious gross misunderstanding of the Microsoft conventions, you used "m_" TO NAME A
LOCAL VARIABLE!!!! Please, please, please do the world a favor, and if you are totally
clueless about what these naming conventions mean, DO NOT USE THEM!!!!!! They only make
your code unreadable and unmaintainable. And probably contribute to the fact that your
code is out-and-out WRONG!
When you bind the HBITMAP to a local variable, it is destroyed when the scope exits, thus
destroying the HBITMAP bitmap which is supposed to be owned by the clipboard!!!!!
Overall, the code appears to be incorrect, incomplete, and badly commented; and
unbelievably poorly written because of the gross misuse of naming conventions.
The code might be moderately salvageable, but I fail to see the correlation with the above
code and the code below. One is attempting to save something to the clipboard in some
unspecified format, the other is saving something to a file (why are you writing files in
the root directory?) in a very well specified format, even if it is not the format you
said you wanted.
****
Can anybody please explain why the OpenClipboard function fails?Joseph M. Newcomer [MVP]
I want to save a .bmp file. I could save a avi frame using the
following statements:
capFileSetCaptureFile(hWndC, "c:\\myCapturedFrame");
capCaptureSingleFrameOpen(hWndC);
capCaptureSingleFrame(hWndC);
capCaptureSingleFrameClose(hWndC);
but that pice of code generates an myCaptureFrame.avi, but I need a
.bmp file.
Thanks for your time.
email: newcomer@xxxxxxxxxxxx
Web: http://www.flounder.com
MVP Tips: http://www.flounder.com/mvp_tips.htm
.
- References:
- OpenClipboard
- From: Martin
- OpenClipboard
- Prev by Date: Re: Good design
- Next by Date: Re: How to convert CString object to data type?
- Previous by thread: OpenClipboard
- Next by thread: Re: Accessing data from Excel spread***
- Index(es):