|
I can't claim to be anything like an expert - I was having a semi-educated guess! I have used mainly SDK-level graphics - SetDIBitsToDevice() - as well as a DirectDraw library supplied by a frame grabber supplier.
But some more on my ideas . . .
Do you know what rate your application actually displays the bitmaps? Is it possible that within a single vertical blanking period, you actually try to display both bitmaps? That might give the appearance you describe.
According to the Microsoft DirectDraw documentation, it should be sufficient to do something like:
while not finished<br />
WaitForVerticalBlank(. . . DDWAITVB_BLOCKBEGIN . . .)<br />
displayBitmap1<br />
WaitForVerticalBlank(. . . DDWAITVB_BLOCKBEGIN . . .)<br />
displayBitmap2<br />
endWhile
What I have seen by profiling is that the DirectDraw functions return control to the application almost instantaneously, so if WaitForVerticalBlank(. . . DDWAITVB_BLOCKBEGIN . . .) actually returns if you are IN the vertical blanking period, not just at the START of the vertical blanking period, multiple bitmaps may be displayed in the same vertical blanking period.
It may thus be necessary to sit in a loop like this:
while not finished<br />
WaitForVerticalBlank(. . . DDWAITVB_BLOCKBEGIN . . .)<br />
displayBitmap1<br />
WaitForVerticalBlank(. . . DDWAITVB_BLOCKEND . . .)<br />
WaitForVerticalBlank(. . . DDWAITVB_BLOCKBEGIN . . .)<br />
displayBitmap2<br />
WaitForVerticalBlank(. . . DDWAITVB_BLOCKEND . . .)<br />
endWhile
Of course, Microsoft documentation may be correct, in which case explicitly waiting for the end of vertical blanking is not necessary.
I hope this makes sense.
|
|
|
|
|
Norman (and all), Many thanks for your help, I have just managed to solve the problem and the images update flicker free and in synch at a rate of around 30Hz. I found I didn't use the WaitFor(...BLOCKEND...) call as it worked fine with just the (...BLOCKBEGIN). One thing I notice is that the WaitFor functions usually take at least 2 frames worth of timne to respond, which is starnge since I thought they should return after a single frame, but tis a small niggle! Any thoughts though?
Thanks again for your help - the past few weeks have been a struggle to say the least and this site's help has been superb!
best wishes
NICK
|
|
|
|
|
I use :
Visual C++ 6.0
Windows 2000
MsChart Active X
I want :
When I click on the chart I want a lengend(box or what MsChart purpose) with the value of the point. Please help me.
P.S. I'm French and not verry good in English lol.
Thank You see ya
|
|
|
|
|
Hi,
I'm learning about the Doc/View method of programming and making an application. It seems to me that the only way you modify your document is either from the OnOpenDocument() and Serialize() and I have no idea how these get called in the CApp object. What if I wanted to update the document when some function gets called in one of my own objects?
How is the document normaly modified? Do you override Serialize in your app class and then since theApp is global your other objects can access and call it? Do you somehow get the CDocument (by calling something like CFrameWnd::GetActiveDocument())?
What I'm trying to do is have an object that outputs some information to a file. When this object is done I want the CDocument to be updated to point to a different file or something.
Thanks.
|
|
|
|
|
budric@mailinator.com wrote:
...OnOpenDocument() and Serialize() and I have no idea how these get called in the CApp object.
OnOpenDocument() is called by the framework as part of the File/Open command. Serialize() is called indirectly from within OnOpenDocument() .
budric@mailinator.com wrote:
What if I wanted to update the document when some function gets called in one of my own objects?
No problem. Your document has various member variables that can be updated whenever necessary. For instance, my document might have an int member variable called m_nAge . I might prompt the user for their birthdate, and calculate their current age into the m_nAge variable. I would then call SetModifiedFlag(TRUE) to indicate that the document has been changed. Now if I close the application, the framework will check to see if the document has changed and if it so, will prompt me to save it.
Start with something very simple. Create an SDI application using AppWizard. Base the view off of CFormView . Using the resource editor, add a few edit controls (e.g., name , address , ZIP ) to the view. Add corresponding variables to the document (e.g., name and address would be CString , while ZIP would be an int ). Modify the document's Serialize() method to load and store those variables accordingly. Add three edit control variables to the view. In the view's OnUpdate() method, call the GetDocument() method to get a pointer to the associated document. Now call each edit control's SetWindowText() method using the variables from the document. Make sense?
"When I was born I was so surprised that I didn't talk for a year and a half." - Gracie Allen
|
|
|
|
|
That makese sense. However the application I'm currently thinking of doesn't quite work like that. I have a camera class which I wrote that controls a digital camera remotely. I allow the user to release the shutter and the image gets copied to hard disk. Now I would like to display this image after the shutter gets pressed. I do that by overriding the OnDraw() in the View. What made sense to me was to somehow update the document to reflect the recent image change, and the view would then get the document's image and display it. So the onOpen and OnSave will not be used at all. Of course I don't even need to use the document. I can store the image path/image in the global variable which you can see from OnDraw() but I want to see if there's a better design.
The problem is that the camera object has no access to the CDocument to update it and tell it that the image has changed...or at least in a direct way. So is this kind of design not done? Or do you get the reference to the CDocument by doing something like calling CFrameWnd::GetActiveDocument().
|
|
|
|
|
budric@mailinator.com wrote:
So the onOpen and OnSave will not be used at all.
Possible. See my last comment.
budric@mailinator.com wrote:
Of course I don't even need to use the document.
But the flow will be much easier if you do.
budric@mailinator.com wrote:
The problem is that the camera object has no access to the CDocument to update it and tell it that the image has changed...or at least in a direct way.
Does the application sit idle until the user interacts with the camera itself? The part of the application that copies the image to disk needs to send a message to the document indicating that a new image is ready. The document would then load the image file like any other file. Does this sound correct?
"When I was born I was so surprised that I didn't talk for a year and a half." - Gracie Allen
|
|
|
|
|
Yes that is correct. What's the best way to send the message to the document after the function is done saving?
|
|
|
|
|
budric@mailinator.com wrote:
What's the best way to send the message to the document after the function is done saving?
By using SendMessage() . Put the message handler in the document class.
"When I was born I was so surprised that I didn't talk for a year and a half." - Gracie Allen
|
|
|
|
|
should I send the message? The document doesn't have a handle, but SendMessage requires a windows handle.
Thanks.
|
|
|
|
|
See if this article sheds any light on MFC's message/command routing.
"When I was born I was so surprised that I didn't talk for a year and a half." - Gracie Allen
|
|
|
|
|
for your patience and help.
|
|
|
|
|
How do you add the controls you mentioned to the view? From the book/tutorials I've read it only shows how to add controls to the dialogs.
|
|
|
|
|
Like I mentioned, you have to have a CFormView -based view.
"When I was born I was so surprised that I didn't talk for a year and a half." - Gracie Allen
|
|
|
|
|
I am trying to write a whole lot of data into a file using serialize. When I use CString It is writing anempty string. ANy help would be appreciated. Following is the Code.
if(ar.IsStoring())
{
ar << (COLORREF) m_clrMapColor;
ar << (int) m_nMapNo;
ar << (CString)m_strName;
int ShapeListCount = m_ShapeList.GetCount();
ar << (int)ShapeListCount;
POSITION pos = m_ShapeList.GetHeadPosition();
for (int j = 0; j < m_ShapeList.GetCount(); j++)
{
CShape* shape = (CShape*)m_ShapeList.GetNext(pos);
shape->Serialize(ar);
}
endfor
}
endif
|
|
|
|
|
Have you verified that m_strName is non-empty at the point of serialization?
"When I was born I was so surprised that I didn't talk for a year and a half." - Gracie Allen
|
|
|
|
|
Thanks for your help.
The string is not empty. I tried ar.WriteString and ar.ReadString instead. But I am getting a set of new problems.
|
|
|
|
|
It is reading the string with an extra space and the next int is not getting the value that was stored.
|
|
|
|
|
Got it. I had to include ar.WriteString( "\n" ) after writing the string. Now it is working fine. Thanks for the help.
|
|
|
|
|
Why would you need a '\n' character to be serialized after the CString object?
"When I was born I was so surprised that I didn't talk for a year and a half." - Gracie Allen
|
|
|
|
|
Something is wrong other than in the code snippet you've provided. Try this. Create a dummy SDI application. Add a CString variable to the document class, and assign it a value in the document's constructor. Modify the Serialize() method to write that variable to the archive. Run the app and then close it. When asked for a file to save to, pick something that you don't mind overwriting. Now open that file as binary using Visual Studio. Do you see the correct value?
"When I was born I was so surprised that I didn't talk for a year and a half." - Gracie Allen
|
|
|
|
|
When I did what you suggested I did see the string in the file. I am not sure what is going on. COuld you please explain. One more thing, I can overwrite a file, but am unable to create new files. Would greatly appreciate any help.
|
|
|
|
|
TUMB wrote:
When I did what you suggested I did see the string in the file. I am not sure what is going on. COuld you please explain.
Go ahead and add a few more member variables (e.g., int, float) to the document class. Then modify the Serialize() method to load and store these new variables. To more closely mimic what your original application was doing, put the CString variable in between the other two.
"When I was born I was so surprised that I didn't talk for a year and a half." - Gracie Allen
|
|
|
|
|
I did the following
void CEX1Doc::Serialize(CArchive& ar)
{
if (ar.IsStoring())
{
// TODO: add storing code here
ar << m_nInt;
ar << strName;
ar << fFloat;
}
else
{
// TODO: add loading code here
ar >> m_nInt;
ar >> strName;
ar >> fFloat;
}
}
When I view the file in Notepad, I see the string but the rest are only boxes. Thanks for being so patient. This is the first time I am using Serialize to save Data. AS you said there is something wrong with the code. It can only save on an existing file, but if I enter a new FileName, It is giving me the following error.
filecore.cpp
Line 238
Thanks once again for all the help
|
|
|
|
|
TUMB wrote:
When I view the file in Notepad...
Notepad is a poor choice for viewing serialized (i.e., binary) files. Use Visual Studio instead.
TUMB wrote:
but if I enter a new FileName, It is giving me the following error.
filecore.cpp
Line 238
Have you looked at line 238 of FileCore.cpp?
I know why the assertion itself fires, but I don't know why the file has not been opened at that point. I dummied up an SDI application just now and it worked fine. The only additional thing I added that was not mentioned before is a call to SetModifiedFlag(TRUE) inside if the OnNewDocument() method (right before the return statement). Something like:
CMyDoc::CMyDoc()
{
m_nAge = 26;
m_strName = "Crow, David";
m_dPay = 12.34;
}
BOOL CMyDoc::OnNewDocument()
{
if (!CDocument::OnNewDocument())
return FALSE;
SetModifiedFlag(TRUE);
return TRUE;
}
void CMyDoc::Serialize(CArchive& ar)
{
if (ar.IsStoring())
{
ar << m_nAge;
ar << m_strName;
ar << m_dPay;
}
else
{
ar >> m_nAge;
ar >> m_strName;
ar >> m_dPay;
}
} Run this as is. Close the application. When prompted, enter a filename. Comment out the initialization in the document's constructor. Set a breakpoint in the Serialize() method. Run the code again. The three variables should hold assigned the contents of the file. Yes?
"When I was born I was so surprised that I didn't talk for a year and a half." - Gracie Allen
|
|
|
|