|
Since I was programming in Turbo C++ for 2 years, I guss I know how to write a class without the Helps of the Wizard.
How ever in MFC it could make a life more easier.
|
|
|
|
|
What is the MFC 6.0 equivalent of the dir.h calls
_findfirst, _finddata, etc.
They don't work so well any more.
|
|
|
|
|
|
_findfirst is in io.h! I don't know what dir.h is!
INTP
"The more help VB provides VB programmers, the more miserable your life as a C++ programmer becomes."
Andrew W. Troelsen
|
|
|
|
|
Hi Guys,
I am using a Dialog resource template to create a dialog and load that dialog using the function
DialogBox(hMod, (LPCTSTR)IDD_ABOUTBOX, hWnd, (DLGPROC)About);
The WndProc is like this, What i am trying to do here is to load all the BMP files one by one in to a window when the user clicks the button 'Next' or 'Previous'.
I Tried different techniques, but when i click next the Window is not repainted. The cod for the WndProc is shown below
LRESULT CALLBACK About(HWND hDlg, UINT message, WPARAM wParam, LPARAM lParam)
{
int i = 0;
int nPos = 0;
switch (message)
{
//HDC hDC, MemDCExercising;
//PAINTSTRUCT Ps;
//HBITMAP bmpExercising;
//HWND ctrl, hwndItem;
//RECT rect;
char szDirectory[256];
WIN32_FIND_DATA FindFileData;
HANDLE hFind;
case WM_INITDIALOG:
GetCurrentDirectory(256, szDirectory);
sprintf(szDirectory,"%s\\debug\\*.bmp",szDirectory);
//finding the first file
hFind = FindFirstFile(szDirectory, &FindFileData);
if (hFind != INVALID_HANDLE_VALUE) {
sprintf(allFiles[i++],"%s", FindFileData.cFileName);
//Finding all the bmp files
while(FindNextFile (hFind,&FindFileData)) {
sprintf(allFiles[i++],"%s", FindFileData.cFileName);
}
totalFiles = i; //Total bmp files
} else { //if there are no BMP files then disable all bot h buttons
//EnableWindow(GetDlgItem(hDlg, IDC_PREVIOUS_IMAGE), FALSE);
EnableWindow(GetDlgItem(hDlg, IDC_NEXT_IMAGE), FALSE);
}
EnableWindow(GetDlgItem(hDlg, IDC_PREVIOUS_IMAGE), FALSE);
return TRUE;
case WM_COMMAND:
if (LOWORD(wParam) == IDOK || LOWORD(wParam) == IDCANCEL)
{
EndDialog(hDlg, LOWORD(wParam));
return TRUE;
}
if (LOWORD(wParam) == IDC_NEXT_IMAGE) {
currentFile ++;
EnableWindow(GetDlgItem(hDlg, IDC_PREVIOUS_IMAGE), TRUE);
//RedrawWindow(hDlg, NULL, NULL, RDW_ERASE);
//InvalidateRect (GetDlgItem(hDlg, IDC_CANVAS), NULL, FALSE);
if(currentFile>=totalFiles-1) { //if all the files has been viewed then disable next button
EnableWindow(GetDlgItem(hDlg, IDC_NEXT_IMAGE), FALSE);
}
//hwndItem = (HWND) GetDlgItem(hDlg,IDC_CANVAS);
//repaintWindow(hDlg);
//nPos = SendMessage( hDlg, WM_PAINT, 0, 0 );
//InvalidateRect (hDlg, NULL, TRUE);
UpdateWindow (hDlg);
//RedrawWindow(hDlg, NULL, NULL, RDW_INTERNALPAINT);
}
if (LOWORD(wParam) == IDC_PREVIOUS_IMAGE) {
currentFile --;
EnableWindow(GetDlgItem(hDlg, IDC_NEXT_IMAGE), TRUE);
//RedrawWindow(hDlg, NULL, NULL, RDW_ERASE);
//InvalidateRect (GetDlgItem(hDlg, IDC_CANVAS), NULL, FALSE);
if(currentFile<=0) { //if all the files has been viewed then disable next button
currentFile = 0;
EnableWindow(GetDlgItem(hDlg, IDC_PREVIOUS_IMAGE), FALSE);
}
//hwndItem = (HWND) GetDlgItem(hDlg,IDC_CANVAS);
//repaintWindow(hDlg);
//nPos = SendMessage( hDlg, WM_PAINT, 0, 0 );
//InvalidateRect (hDlg, NULL, TRUE);
//RedrawWindow(hDlg, NULL, NULL, RDW_INTERNALPAINT);
UpdateWindow (hDlg);
}
return TRUE;
break;
case WM_DESTROY:
PostQuitMessage (WM_QUIT);
break;
case WM_PAINT:
/*ctrl = GetDlgItem(hDlg, IDC_CANVAS);
hDC = BeginPaint(ctrl, &Ps);
// Load the bitmap from the resource
//bmpExercising = LoadBitmap(hInst, MAKEINTRESOURCE(IDB_BITMAP1));
//Load bitmap from a file
bmpExercising = (HBITMAP)LoadImage(
hInst, // handle to instance
allFiles[currentFile], // image to load
IMAGE_BITMAP, // image type
0, // desired width
0, // desired height
LR_LOADFROMFILE// load options
);
//GetBitmapDimensionEx (bmpExercising, bmpSize);
// Create a memory device compatible with the above DC variable
MemDCExercising = CreateCompatibleDC(hDC);
// Select the new bitmap
SelectObject(MemDCExercising, bmpExercising);
GetWindowRect(ctrl,&rect); // Copy the bits from the memory DC into the current dc
StretchBlt(hDC, 0, 0, rect.right - rect.left,
rect.bottom - rect.top,
MemDCExercising, 0, 0,200,
200, SRCCOPY);
// Restore the old bitmap
DeleteDC(MemDCExercising);
DeleteObject(bmpExercising);
EndPaint(ctrl, &Ps);
//UpdateWindow(GetDlgItem(hwnd, IDD_DIALOG_BOX));
//return FALSE;
*/
repaintWindow(hDlg);
break;
//Initilize the dialog
//default:
// return DefWindowProc(hDlg, message, wParam, lParam);
}
return FALSE;
}
void repaintWindow (HWND hDlg) {
HDC hDC, MemDCExercising;
PAINTSTRUCT Ps;
HBITMAP bmpExercising;
HWND ctrl;//, hwndItem;
RECT rect;
ctrl = GetDlgItem(hDlg, IDC_CANVAS);
hDC = BeginPaint(ctrl, &Ps);
// Load the bitmap from the resource
//bmpExercising = LoadBitmap(hInst, MAKEINTRESOURCE(IDB_BITMAP1));
//Load bitmap from a file
bmpExercising = (HBITMAP)LoadImage(
hInst, // handle to instance
allFiles[currentFile], // image to load
IMAGE_BITMAP, // image type
0, // desired width
0, // desired height
LR_LOADFROMFILE// load options
);
//GetBitmapDimensionEx (bmpExercising, bmpSize);
// Create a memory device compatible with the above DC variable
MemDCExercising = CreateCompatibleDC(hDC);
// Select the new bitmap
SelectObject(MemDCExercising, bmpExercising);
GetWindowRect(ctrl,&rect); // Copy the bits from the memory DC into the current dc
StretchBlt(hDC, 0, 0, rect.right - rect.left,
rect.bottom - rect.top,
MemDCExercising, 0, 0,200,
200, SRCCOPY);
// Restore the old bitmap
DeleteDC(MemDCExercising);
DeleteObject(bmpExercising);
EndPaint(ctrl, &Ps);
//UpdateWindow(GetDlgItem(hwnd, IDD_DIALOG_BOX));
//return FALSE;
}
Please help me.
Thanking in Advance,
Jobby
|
|
|
|
|
(FIRST) I am getting used to seeing stuff like this, but it does not change the fact that it should not compile:
switch (message)
{
char szDirectory[256];
WIN32_FIND_DATA FindFileData;
HANDLE hFind;
...
...
}
(SECOND) I'm too tired for this right now!
(THIRD) Ask me how; when I'm asleep (It's that simple).
INTP
"The more help VB provides VB programmers, the more miserable your life as a C++ programmer becomes."
Andrew W. Troelsen
|
|
|
|
|
Thanks Mr.Shaw, but that dosen't help....
|
|
|
|
|
Don't bother, i fixed the problem.
|
|
|
|
|
The application I am working on, call it Main, starts up another executable, call it Sub, and the two share an event. The event is created in Main before Sub starts, and then opened in Sub. The problem I am having in debugging them is that if Main hasn't reset the event, Sub freezes the computer, to the point where the only way I can recover is to power-down. The freeze happens here:
<br />
while (WaitForSingleObject(hAcquireActive, 100)==WAIT_OBJECT_0)<br />
{<br />
Sleep(1000);<br />
}<br />
I tried something slightly different by creating an event to use in place of the Sleep, but it freezes the computer in the same way.
That code is:
<br />
HANDLE waitForeverEvent;<br />
waitForeverEvent = CreateEvent(NULL, FALSE, FALSE, "forever");<br />
while (WaitForSingleObject(hAcquireActive, 100)==WAIT_OBJECT_0)<br />
{<br />
WaitForSingleObject(waitForeverEvent, 1000);<br />
}<br />
Environment is : Windows XP Professional, Visual Studio 2003.
Any explanation for why the computer is freezing, and/or a better way to wait for the hAcquireActive event to be reset while I am debugging?
Thanks.
|
|
|
|
|
|
Thank you for finding that.
Somewhat, but the same thing happens when running a release version outside of Debug.
I am looking into the possibility that it is a bus problem caused by one of the cards in the system.
|
|
|
|
|
Jack,
Turned out to be bad hotlink receiver card. Thanks again for your help.
|
|
|
|
|
Now that was SERIOUSY cool to know. Thanks a ton
|
|
|
|
|
What happens in your main program AFTER the while loop?
Since you only check for WAIT_OBJECT_0, if the hAcquireActive is not signaled within 100ms then your wait will return with WAIT_TIMEOUT and oyu will not enter your while loop.
Could this be your problem?
|
|
|
|
|
Blake,
Good thinking, based on the amount of code I posted. I probably should have put more of the preceding code. The way the 2 interact, the Sub code - which is the one that was hanging on the sleep - has just set the event and checked that it is indeed set. Then comes the code I posted which is waiting for it to be reset by Main. If it has been reset, then there is no need to go into the loop.
During the debugging process, I took main out of the picture - created the event in Sub - and added some other lines inside the loop to guarantee things were for sure freezing on the Sleep or WaitForSingleObject, and they were.
The problem turned out to be a bad hotlink receiver card. It was replaced and now the problem is gone. The specifics of why it manifested that way I don't know. Since it works now, move on ...
In hindsight, since it was freezing to the extent the system had to be powered down, I might have more quickly ruled out that it was a coding problem.
Thanks for your help.
|
|
|
|
|
I don't see how this got to be a problem, but I'm trying to read a bitmap file data in a raw fashion, byte by byte. I'm dealing with 8-bit images and therefore my data starts at 0x436 (1078 bytes from the beginning of the file). I'm trying to read the file in 64-byte chunks using file pointers. I've used fseek to position the data read pointer at the start of the data properly and it starts to read fine. When it gets to byte 62, that's when the problems begin. I have a variable that's set by ftell to tell me the file position which I interpret it to be the byte offset from the start of the file. Before the problem, the characters are fine and the file position is where it should be. Once it hits byte 62, the characters it gets are different from what it should be and the file position reads 5175 instead of 1141 for byte 63.
Here's 96 bytes of what I'm trying to read from:
1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E
1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1D 1D 1C 1C 1B 1D 1C 1B 1B 1A 1D
1D 1B 1B 1B 1B 1B 1C 1D 1B 1C 1C 1D 1D 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E
Here's the result, I've bolded the bytes that are different:
1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E
1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1D 1D 1C 1C 1B 1D 1C 1B 1B 1E 1E
1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E 1E
The 1E's at the end of the snip are probably 1E's from somewhere else, the picture I'm reading is of a very white moon on a very black background. Any help would be greatly appreciated because this is an annoying problem.
edit: I was using fgetc to get a char (cast into a BYTE), but I tried using fscanf but the behavior is still the same, quite strange.
|
|
|
|
|
I traced through the read and here's what I found...
In the file pointer structure, there is a _ptr and a _cnt variable. When I open a file, the system seems to read in a chunk into memory and position _ptr at the front of it. As I read, the _ptr advances through the memory, and _cnt counts down to stop the read at the end of the chunk. When _cnt reaches zero, that may be a signal to the system to grab more data. Upon the signal, a new chunk of data overwrites the old data in the same memory area to save space, _cnt is reset to the amount of data it read in and _ptr points back to the beginning.
That sounds reasonable to me, however the data it reads in is very incorrect after the first block. I have the same file open in a hex editor and it's fine so the data is not corrupt. In the meantime, I may (relucantly) try a different method of reading a file, like iostream instead of file pointers but this is just disappointing to me. If anyone can say "it's because of X. Add "this statement;" and it'll work like a champ, I'll buy you a pint.
|
|
|
|
|
All I've seen from this post and the original, is that you are making it too complicated.
What you are describing, of course, makes since for buffered file I/O. Since reading a sector at a time is more effiecient than reading a character at a time.
You can read all the file data into a single buffer, to simplify manipulation.
Note: If you read an entire .bmp into a buffer, eccentualy, you end up with a DIB.
INTP
"The more help VB provides VB programmers, the more miserable your life as a C++ programmer becomes."
Andrew W. Troelsen
|
|
|
|
|
How is it too complicated? I want to position the file pointer at a location (0x436, 1078 bytes from the beginning of the file) and then read the rest of the file, sound like quite the ordinary task (with some argument attributed to file positioning). I can't perform this task because the data it pushes onto me isn't the data I have in the file. Am I wrong in the fact that the file pointer is not working correctly? Shouldn't it keep reading the file, not skip around some and then read past the end of the file and return FF's? I don't want to read the entire bitmap file, only the data portion.
|
|
|
|
|
LighthouseJ wrote:
How is it too complicated?
You've were talking about reading a structured file one byte at a time. Which impilies you need to decipher those bytes (complicated, may be need for cross platfom).
Now:
You've been talking about reading a bitmap file and you are assuming that there will be data at 1078 to be read. If the file is realy an .bmp file, then you need to read the file header to determine where the bitmap data is and (for safey) what format the data is stored in.
LighthouseJ wrote:
Am I wrong in the fact that the file pointer is not working correctly?
I would bet good money that the answer is YES!
LighthouseJ wrote:
I don't want to read the entire bitmap file, only the data portion.
The entire file is the data portion!
BUT: I assmue by 'data portion' you mean the bitmap data bytes:
1) Open file.
2) Read BITMAPFILEHEADER (header).
3) Check that it is a .bmp file type. (header.bfType == 0x4D42)
4) Seek start of header (probably beginning of file).
5) Seek offset header.bfOffBits. (data offset from beginning of header)
6) Read data.
The above will work, but the moment the bitmap type is changed, yout code will fall apart.
INTP
"The more help VB provides VB programmers, the more miserable your life as a C++ programmer becomes."
Andrew W. Troelsen
|
|
|
|
|
John R. Shaw wrote:
You've were talking about reading a structured file one byte at a time. Which impilies you need to decipher those bytes (complicated, may be need for cross platfom).
It's not that bad. For instance if I need to get the bitmap type, the "BM", I read in a character into a short, then shift the bits left 8-bits, then logically or that variable with the next character. When I read in an integer (4-bytes), I call the previous statement twice, and shifting by 16 bits in between the two calls. I do read in both headers and jump to that location (0x436) but every single 8-bit bitmap file always begins data at that same address so in the interest of simplifying the explanation, I just said I would always go to that byte offset.
John R. Shaw wrote:
... the moment the bitmap type is changed, yout code will fall apart.
I have conditionals in the right places to make sure the file that's read is of the right type, bit depth, size, etc....
Of course, all of this you've brought up is a non-issue because I have no problems reading the bitmap headers, only when I get to that particular location.
I looked at another reply from rateep and he pointed out the problem with a very concise on-topic response to my problem and it fixed my problems.
|
|
|
|
|
Show us your code and we might be able to help...
Ryan "Punctuality is only a virtue for those who aren't smart enough to think of good excuses for being late" John Nichol "Point Of Impact"
|
|
|
|
|
Well, it's kind of spread out, but I can put the relevant parts back together. I have a class that doles out the data to the function I'm trying to use it in. It's pretty standard file pointer things and I've used file pointers exclusively in the past on countless programs.
Here's some code snips:
CBitmapFile::CBitmapFile(CString fileName) {<br />
bmpFP = fopen((LPCTSTR)fileName, "r");
Where bmpFP is a member variable in CBitmapFile.
Here's the function that I call to get data:
BYTE CBitmapFile::GetNextByte() {<br />
BYTE data;<br />
data = getc(bmpFP);<br />
nBytesRead++;<br />
nVerticalPosition++;<br />
nCurrentPosition = ftell(bmpFP);<br />
return data;<br />
}
I used fscanf, I'm trying to use file streams now but even after I include ifstream, fstream or anything else to try, the compiler still doesn't know what ifstream is even though I can hover the cursor over it and then start to use it and VS brings up that little class object list as I type.
Here's where I actually use the function. At this time I am only spitting the data back into another file for debug purposes but I'll eventually put the data into a CByteArray and then transmit it.
FILE * outFP = fopen("debug.dat", "w");<br />
for (int i=0; i<PacketSize; i++) {<br />
byte = BitmapFileReader->GetNextByte();<br />
fprintf(outFP, "%c", byte);<br />
}
PacketSize will almost always be 64. That for loop is inside a larger loop to keep going until it's created every packet. It's real simple, I can change functions to read the data, but I still get the same irregularities.
|
|
|
|
|
hmmm.....i dunno if thiz will help.....tis JUST a guezz.....
u see when the command that u have given
bmpFP = fopen((LPCTSTR)fileName, "r");
FILE * outFP = fopen("debug.dat", "w");
both of openz in the text mode.....u have to specfy as.....
bmpFP = fopen((LPCTSTR)fileName, "rb");
FILE * outFP = fopen("debug.dat", "wb");
becoz when it openz in text mode certain characters are not accepted by the fopen(read the documentation relating that)for example i had done thiz encrypting code on a file,when opened in text mode and when ever it encounters the 26(ascii) value it(foperationz exit like as though end of file has reached!) stopz!basically i didnt know why....but then after a long search just by putting a "b" solved my prob!
ps:i dunno if thiz will help(might sound real stupid though,but could be the cause!)even i read filez using the basic file operationz.....itz fun though it can get hectic at timez.....
cheerz.....
"faith, hope, love remain, these three.....; but the greatest of these is love" -1 Corinthians 13:13
|
|
|
|
|
You're now my new best friend.
I was looking into ifstream as a replacement to file pointers and ran across an option to change to a binary mode which is what I wanted but I never got it to fly. However, you pointed out that I can do that within file pointers which is mindlessly easy and simple fix. Although the file pointer irregularities are still puzzling why it did what it did, it now doesn't do that anymore with the binary mode used. You made my day, thanks a lot.
|
|
|
|
|