Thread: Find Dialog

  1. #1
    Registered User
    Join Date
    Aug 2004
    Location
    San Diego, CA
    Posts
    313

    Find Dialog

    I've initalized a Find dialog box in my program with these settings:

    Code:
    ZeroMemory(&fr, sizeof(fr));
    	fr.lStructSize = sizeof(fr);
    	fr.hwndOwner = hWnd;
    	fr.lpstrFindWhat = FindStr;
    	fr.wFindWhatLen = 255;
    	fr.Flags = FR_DOWN | FR_NOMATCHCASE | FR_NOWHOLEWORD;
    					
    hFind = FindText(&fr);
    Now, I'm completely lost. Where do I handle messages sent from this dialog box?

    Edit: I've tried to hook the dialog box, but when I do, all the controls appear smack in the middle of my edit box and my entire program hangs.
    Last edited by Lithorien; 04-22-2005 at 08:59 PM.

  2. #2
    Registered User
    Join Date
    Aug 2004
    Location
    San Diego, CA
    Posts
    313
    Ok, I have the hook procedure working.. sort of.

    Code:
    UINT_PTR CALLBACK FindHook(HWND hFind, UINT dMsg, WPARAM wParam, LPARAM lParam)
    {
    	switch (dMsg) // Process the window's messages.
    	{
    		case WM_INITDIALOG:
    			lpfr = (LPFINDREPLACE)lParam; // Get pointer to FINDREPLACE structure from lParam.
    		
    			ShowWindow(hFind, SW_SHOWNORMAL); 
    			UpdateWindow(hFind);
    		break;
    		
    		case WM_COMMAND:
    			switch (lpfr->Flags)
    			{
    				case FR_DIALOGTERM:
    					hFind = NULL; 
    				break;
    				
    				case FR_FINDNEXT:
    				{
    					LPSTR temp = lpfr->lpstrFindWhat;
    					
    					int length = GetWindowTextLength(GetDlgItem(hWnd, ID_EDIT));
    								
    					if (length > 0)
    					{
    						char *edit = new char[length + 1];
    						
    						GetDlgItemText(hWnd, ID_EDIT, edit, length+1);
    						
    						delete [] edit;
    					}
    				}
    				break;
    			}
    		break;
    	}
    			
    	return(0);
    }
    This code crashes the program no matter what I do to it EXCEPT commenting out FR_FINDNEXT. Why?
    Last edited by Lithorien; 04-23-2005 at 10:00 AM.

  3. #3
    Registered User
    Join Date
    Dec 2004
    Posts
    73
    Check MSDN's stuff, you're answer could lie there.
    FRHookProc
    Section on Common Windows Dialog Boxes

  4. #4
    Registered User
    Join Date
    Aug 2004
    Location
    San Diego, CA
    Posts
    313
    Quote Originally Posted by ElWhapo
    Check MSDN's stuff, you're answer could lie there.
    FRHookProc
    Section on Common Windows Dialog Boxes
    I've been making heavy use of the MSDN, and those aren't unfamiliar links.. it'd be nice if I could just get information about the FR_FINDNEXT message, even.

    Thank you, though.

  5. #5
    train spotter
    Join Date
    Aug 2001
    Location
    near a computer
    Posts
    3,868
    is this a typo?

    GetDlgItemText(hWnd, ID_EDIT, edit, length+1);



    otherwise where exactly does it crash? (set a break point and step thru)
    "Man alone suffers so excruciatingly in the world that he was compelled to invent laughter."
    Friedrich Nietzsche

    "I spent a lot of my money on booze, birds and fast cars......the rest I squandered."
    George Best

    "If you are going through hell....keep going."
    Winston Churchill

  6. #6
    Yes, my avatar is stolen anonytmouse's Avatar
    Join Date
    Dec 2002
    Posts
    2,544
    You don't want to use a hook procedure. The hook procedure can be used to customise the find dialog. The actual find messages are sent to the window identified by hwndOwner. Using a find dialog is a three step process:
    1. Register the FINDMSGSTRING at application startup.
    2. Call the FindText function with appropriate parameters.
    3. Handle the registered find message in the window procedure belonging to hwndOwner.

    I have some old code that demonstrates:
    Code:
    // Global variables.
    HWND g_hFndDlg;          // Handle for the find dialog
    UINT g_uFindReplaceMsg;  // Message identifier for FINDMSGSTRING
    
    
    // Initialization code. Put this at application startup.
    // Register message for findDlg
    g_uFindReplaceMsg = RegisterWindowMessage(FINDMSGSTRING);
    
    
    // Call this function to show the find dialog.
    BOOL FindDlg(BOOL replace, HWND hwndOwner) 
    {
    	// These have to be static (or global) as the
    	// dialog uses them after the function is finished
    	static FINDREPLACE frSearch;
    	static TCHAR       findBuffer[256];
    	static TCHAR       replaceBuffer[256];
    
    	if (g_hFndDlg)
    	{
    		// Find dialog is already open, just activate it...
    		SetActiveWindow(g_hFndDlg);
    
    	 	// Set find next button focus
    		SetFocus( GetDlgItem(g_hFndDlg, 1) );
    
    		return TRUE;
    	}
    
    	ZeroMemory( &frSearch, sizeof(frSearch) );
    
    	frSearch.lStructSize      = sizeof(frSearch);
    	frSearch.hwndOwner        = hwndOwner;
    	frSearch.Flags            = FR_HIDEWHOLEWORD | FR_HIDEUPDOWN;
    	frSearch.lpstrFindWhat    = findBuffer;
    	frSearch.lpstrReplaceWith = replaceBuffer;
    	frSearch.wFindWhatLen     = sizeof(findBuffer)    / sizeof(findBuffer[0]);
    	frSearch.wReplaceWithLen  = sizeof(replaceBuffer) / sizeof(replaceBuffer[0]);
    
    	// This function is duel use. It will show the replace or find dialogs
    	// depending on the replace argument...
    	if (replace)
    		g_hFndDlg = ReplaceText(&frSearch);
    	else
    		g_hFndDlg = FindText(&frSearch);
    
    	// Set find next button focus
    	SetFocus( GetDlgItem(g_hFndDlg,1) );
    
    	return TRUE;
    }
    
    
    // This is a mock-up of the hwndOwner window procedure...
    static LRESULT CALLBACK DialogFunc(HWND hwndDlg, UINT msg, WPARAM wParam, LPARAM lParam)
    {
    	switch (msg)
    	{
    		// Handle other messages here...
    	}
    
    
    	if (msg == g_uFindReplaceMsg)
    	{
    		// Message from find dialog box
    		pFind = (LPFINDREPLACE) lParam;
    
    		// If the FR_DIALOGTERM flag is set,
    		// invalidate the handle identifying the dialog box.
    		if (pFind->Flags & FR_DIALOGTERM)
    		{
    			g_hFndDlg = NULL;
    			return 0;
    		}
    		else if (pFind->Flags & FR_FINDNEXT)
    		{
    			// Just find instance of the word
    			SearchText(pFind); // You provide this function.
    		}
    		else if (pFind->Flags & FR_REPLACE)
    		{
    			// Delete if you don't need the replace dialog.
    			// Replace selection if it equals findWhat, then find next instance.
    			ReplaceWord( pFind, FALSE ); // You provide this function.
    		}
    		else if (pFind->Flags & FR_REPLACEALL)
    		{
    			// Delete if you don't need the replace dialog.
    			// Replace all words from end of selection. replaceAllMode set to TRUE.
    			ReplaceWord( pFind, TRUE ); // You provide this function.
    		}
    
    		return 0;
    	}
    
    	// return DefWindowProc(), etc...
    }
    The code uses global variables which means you can have only one find dialog open at one time (which is recommended anyway). I'm sure it could be done without globals. The code implements find and replace dialogs as most of the code is shared. Delete the orange code if you only need a find dialog.
    Last edited by anonytmouse; 04-26-2005 at 02:17 AM.

  7. #7
    Registered User
    Join Date
    Aug 2004
    Location
    San Diego, CA
    Posts
    313
    Thanks!

    Much more efficient than what I hacked out.

Popular pages Recent additions subscribe to a feed

Similar Threads

  1. Have a new dialog replace another one
    By axr0284 in forum Windows Programming
    Replies: 6
    Last Post: 03-10-2006, 05:23 PM
  2. Dialog problem
    By Sucur in forum C++ Programming
    Replies: 0
    Last Post: 07-20-2005, 05:22 PM
  3. Edit controls of a dialog from another dialog...
    By Snake in forum Windows Programming
    Replies: 9
    Last Post: 07-01-2005, 02:18 PM
  4. how to set this dialog to this
    By stallion in forum Windows Programming
    Replies: 3
    Last Post: 01-31-2003, 05:19 PM
  5. SDI Menu App - MSVC 6
    By Unregistered in forum Windows Programming
    Replies: 7
    Last Post: 10-16-2001, 09:59 PM