|
Hi there,
I have a dialog box (derived from CDialog), which contains an edit control.
I want to handle the esc and enter keys at the message handler of the edit control, but the esc and enter messages are being translated by accelerators and the whole dialog box closes.
How can I make the keys handled by the edit control?
Thanks for advice,
Alex
Don't try it, just do it!
|
|
|
|
|
Alexander M. wrote:
...but the esc and enter messages are being translated by accelerators and the whole dialog box closes.
See here.
"Ideas are a dime a dozen. People who put them into action are priceless." - Unknown
|
|
|
|
|
the best way is to derive a class from CEdit and handle WM_CHAR. there you can do whatever you want in response to VK_RETURN, VK_ESCAPE. also make sure that in your dialog you have handlers for OK and Cancel. In those handlers comment the part with the call of the base class:
void CBDlg::OnOK()
{
// TODO: Add extra validation here
//CDialog::OnOK();
}
Now your dialog will not exit when you press enter.
same for OnCancel..
PS: Stay away from PreTranslate... as it's design is not for this kind of use.
|
|
|
|
|
Yeah the dialog does not exit... but the CEdit does not receive a WM_CHAR message... I've already tried this, but without success.
I will check PreTranslateMessage... lets see what is possible...
Don't try it, just do it!
|
|
|
|
|
What you need to do is handle the WM_ONGETDLGCODE message for your edit control class. This message tells the dialog box procedure what keys to process for your control and which to skip.
For example:
UINT CMyEdit:OnGetDlgCode()
{
return( CEdit::OnGetDlgCode() | DLGC_WANTALLKEYS );
}
Then process in OnChar as normal.
|
|
|
|
|
Perfect answer, that was exactly what I wanted to know... thank you very much!!!
Don't try it, just do it!
|
|
|
|
|
Hey everyone, I'm a little stuck with this and this is my fist question on these boards, and any advice anyone could give would be greatly appreciated
So basically, I have these two COM components that share memory using a MapViewOfFile object... like so:
-----------------------------------------------------------------
In the "server" component:
HANDLE hBlockMap;
...
hBlockMap = CreateFileMapping((HANDLE)0xFFFFFFFF, NULL,
PAGE_READWRITE, 0,
sizeof(Block), "SharedBlockMemory");
In the "client" component:
HANDLE hBlockMap;
...
hBlockMap = ::OpenFileMapping(FILE_MAP_WRITE, FALSE, "SharedBlockMemory");
-----------------------------------------------------------------
I also have a simple "Block" object, just to test sharing data, which looks like this:
-----------------------------------------------------------------
class Block
{
public:
void Write(char* msg);
char* Read();
int getSize() { return n_size; }
Block();
~Block();
private:
BYTE* data;
int n_size;
};
and just the Write and Read methods:
void Block::Write(char* msg, int size)
{
data = new BYTE[strlen(msg) + 1];
memcpy(data, (BYTE* )msg, strlen(msg));
n_size = size;
}
char* Block::Read(int size)
{
char* result = new char[n_size + 1];
memcpy(result, (char* )data, n_size);
return result;
}
-----------------------------------------------------------------
So basically, my problem is this:
The Write and Read methods both actually "work", and by that I mean I'm not getting any wierd memory access violations... If I expand the write method to check and make sure its writing, like so,
void Block::Write(char* msg)
{
...
n_size = size;
char* check = new char[strlen(msg) + 1];
memcpy(check, (char* )data, strlen(msg));
check[strlen(msg)] = '\0';
cout << check << endl;
delete[] check;
}
It outputs the correct string. However, no matter what I seem to do, the Read method just outputs garbage... I'm completely mystified, because if I change, in the Block class, the definition of data to
BYTE data[250];
and then change my Write and Read method to deal with that accordingly, I get the correct output in the Read method. But if use BYTE* data, I just get garbage...
Am I just missing something small, maybe some syntactical error? I haven't programmed in C++ as much lately, and I wouldn't put that myself, but I'm fairly sure my code dealing with the pointers and copying memory is correct... Or is it something else, could I be using the MapViewOfFile incorrectly?
And also, here is an example of how I read from it, just to demonstrate that access to the shared memory is synchronized (using a seperate mutex)...
-----------------------------------------------------------------
class CMemoryMgr
{
public:
...
private:
Block* c_Block;
...
};
void __stdcall CMemoryMgr::TPF_PrintMessage()
{
if(::WaitForSingleObject(hBlockMutex, 5000L) == WAIT_OBJECT_0)
{
cout << c_Block->Read(c_Block->getSize());
cout << endl;
::ReleaseMutex(hBlockMutex);
}
}
-----------------------------------------------------------------
Also, the reason I want to dynamically allocate the data array is because I will be developing a customized circular buffer, and I want to be able to allow data of any reasonable size to be enqueued, so thats why I'm trying to stay away from a fixed array size.
Anyway, thank you all for reading my problem!
Like I said, any advice would be greatly appreciated
|
|
|
|
|
Is is safe to assume you did call MapViewOfFile after creating or opening the memory mapped file?
And this is the 'block' of memory you read and write to?
There is a memory mapped file sample here on CodeProject:
CMemMapFile v1.41
Interprocess communication tutorial
|
|
|
|
|
How do I do a DFT of an image using a FFT to speed things up? My code does not work but is :
int X, Y, num;
long int R;
float data[4096], scale;
RGBQUAD rgb;
num = max(pImage->GetWidth(),pImage->GetHeight());
const DWORD RGB_MAX=RGB(255,255,255);
if (!IsPowerOfTwo(num))
{
return;
}
if (dir == 1)
{
scale = num*num;
}
else scale = 1.0;
for (Y=0; Y<num; Y++)
{
for (X=0;X<=2*num-1;X+=2)
{
data[X] = data[X+1] = pImage->GetPixelGray(X/2,Y);
}
if (!fft(data,num,dir))
return;
for (X=0;X<num;X++)
{
pImage->SetPixelColor(X,Y,RGB(abs(data[X*2]),abs(data[X*2]),abs(data[X*2])));
}
}
for (X=0;X<=2*num-1;X+=2)
{
for (Y=0; Y<num; Y++)
{
R=Y*2;
data[R] = data[R+1] = pImage->GetPixelGray(X/2,Y);
}
if (!fft(data,num,dir))
return;
for (Y=0;Y<num;Y++)
{
R=Y*2;
pImage->SetPixelColor(X/2,Y,RGB(abs(data[R]),abs(data[R]),abs(data[R])));
}
}
Nothing is impossible, It's merely a matter of finding an answer to the question of HOW? ... And answering that question is usually the most difficult part of the job!!!
|
|
|
|
|
I am drawing with a CDC object as follows:
CDC example;
example.Rect ......etc and all the drawing takes place on screen
thne i attempt to convert the CDC to an enhanced Metafile:
CMetaFileDC File;
File.CreateEnhanced(&example, "path", NULL, "NAme");
File.CloseEnhanced();
The file is created but it does not contain anything on it. When i create a simple Metafile, it works fine and makes the file and shows all the drawing info. However this enhanced thing only creates an empty file that is 1 pix x 1 pix.
What am i doing wrong?
thank you
|
|
|
|
|
What code did you use to create the image list?
Don't try it, just do it!
|
|
|
|
|
Here is code that I used for create Image list
<br />
imgList.Create(16, 16, ILC_COLORDDB | ILC_MASK, 6, 1);
|
|
|
|
|
I have an SDI application that is supposed to close it self when finished. To do this it sends a
m_pMainFrame->PostMessage(WM_SYSCOMMAND, SC_CLOSE);
The application appears to stop running and it gives no errors or warnings in release or debug mode. However, task manager almost always shows the application is still in memory. Is there a more forceful way to close an app.
P.S. I have also tried combinations of SW_CLOSE and SendMessage().
Thanks
|
|
|
|
|
Hello,
MSDN says that SC_CLOSE will only close the window. What happens if you try PostQuitMessage() ?
Behind every great black man...
... is the police. - Conspiracy brother
Blog[^]
|
|
|
|
|
Thank you.
That worked nicely.
|
|
|
|
|
See here.
"Ideas are a dime a dozen. People who put them into action are priceless." - Unknown
|
|
|
|
|
Generally the method I use is to send the ID_APP_EXIT command to the main window. This will then use the same exit procedure as if the user clicked "Exit" from the File menu.
For example:
AfxGetMainWnd()->SendMessage( WM_COMMAND, ID_APP_EXIT );
|
|
|
|
|
Thank you. This is good information.
|
|
|
|
|
I think you first need to understand how the application executes and how an application terminates. It seems as though you are using MFC which hides how things work and most likely why you don't see why this doesn't terminate the application.
A process terminates when "ExitProcess" is called. Simple, right? Just as a thread terminates when "ExitThread" is called. Also pretty simple, right?
So, do you need to call ExitProcess and ExitThread in your application? No, you don't! The main thread of an application will call "ExitProcess" once you return from the "WinMain" or "main" API. There is wrapper code around this thread which will call this for you (unless you've turned this code generation off which is not likely if you are using MFC).
So, once the main thread exits the process will exit. What about threads? An individual thread will terminate also once it returns. "CreateThread" and "BeginThread" do not start a thread as your function but actually start a wrapper function which calls your threadproc. The exit code again will call "ExitThread" so you do not need to call this API yourself.
So, why isn't your application closing? Well the main thread never exited. You should nicely terminate all other threads, however the reason is that your main thread never exited. So why wouldn't it exit?
Well, you called "WM_CLOSE" and that's nice. Your window closes, but the thread didn't terminate if this is your main thread. So, what happens? You need to get the "Message Loop" to quit. The message loop looks like this generally:
while(GetMessage(...))
{
TranslateMessage(...);
DispatchMessage(...);
}
This message loop is dupliated a lot. As an example, "MessageBox" API implements it's own however these are speical. They will exit when the window goes away. The way the one above works is that it will only exit if GetMessage returns 0, which it only does when WM_QUIT is processed. How is this processed? By using PostQuitMessage(); which poses the quit message to that thread.
So, it's generally considered appropriate to call "DestroyWindow()" then in your WM_DESTROY (or in WM_CLOSE call DestroyWindow() as well, but you should handle clean up appropriately) to then call "PostQuitMessage" to exit the thread. This way you clean up properly, send the quit message so the loop exits and the thread should then exit. (Well, the message loop exits at least, doesn't mean that the thread would exit but generally there's no code after this so usually it's the case).
If this is the main thread then your application should exit. If it is not your main thread then you need to also do whatever it takes to get your main thread to exit.
If this is your main thread and it doesn't exit there could still be reasons. As an example in order for it to exit it will possibly need to grab the loader lock or even the heap lock, which could have been held by a terminating thread or have some deadlock contention with something else in your application.
The best thing to do is get the debugger fired up and find out what's going on in that case.
8bc7c0ec02c0e404c0cc0680f7018827ebee
|
|
|
|
|
Thank you.
I very much appreciate the background information.
|
|
|
|
|
I made a program and produced the exe file with visual studio 6. But when I sent the exe to another computer it couldn't work because dlls were missing. How can I know what dlls to have with the exe files in order to work and how will I find them? Isn't there an automated way to do this?
|
|
|
|
|
Use DependcyWalker. This tool is included with Visual Studio. It will show you all the dll's required by your application to run.
|
|
|
|
|
Have a look at "static linking" in Visual Studio.
If you static link then the necessary functions are included in your EXE (This also makes the EXE much bigger, but EXE size is good to impress unknowledgeable customers!)
|
|
|
|
|
No luck. I put it in: use mfc as a static library, and errors were created..
I can't seem to find a way to see what dlls are called..
I must be doing something wrong and I don't have DependcyWalker. How do they do it?..
|
|
|
|
|
Are you sure you don't have DependencyWalker ?
Look for a file called depends.exe, under
[Path to Visual Studio]\Common\Tools
Hope this helps
|
|
|
|
|