To all Win32 professionals. Let's say we have completed existing application with window. The task is to write another application with (my) window. My window must always align its left edge to existing window right edge while user moves existing window across the screen (my window not allowed to move by user).
Precondition: a) Existing window can not be subclassed b) Windows hooks are not a case.
Yes, looks right. I'd not asked this question if it not become a problem. Forgot to say that OS is Vista 2, application is IE. I try to make an application that follows IE main window, align it edge. Subclassing of IE not allowed, and SetWindowsHook not works correctly under regular user (when user have admin privileges application works normally). Such way as all of you talking about works under Windows prior to Vista.
And looks like there is no trivial way to solve this task. Thank you all.
I think you can't without a hook. SetWindowLong allows you to set a WndProc, but this won't work if the window belongs to a different application.
If you dont want/cant subclass or set global hooks, you can look into the following:
Implement your code in a DLL
Call CreateRemoteThread on LoadLibrary's address and your DLL's name to inject your DLL into the target process
In the DLL's DllMain, you can SetWindowHook just on the thread that owns the window. This is a local hook and doesn't require special privileges and is very nice to the system.
In your hook function, process WM_WINDOWPOSCHANGED on the main window's HWND and adjust your window accordingly.
Related
I have a shell extension that needs to reload its configuration when a specific window message (custom message registered with RegisterWindowMessage) is broadcasted by another application.
I tried several approaches to intercept the message:
Installing a window subclass callback on a window of Windows Explorer, using SetWindowSubclass. This works on Window 7, but not on Windows 8, because apparently DllMain is not called on the main thread, and SetWindowSubclass doesn't work from another thread. This is mentioned in the documentation:
You cannot use the subclassing helper functions to subclass a window across threads
Installing a hook for CALLWNDPROC, using SetWindowsHookEx. Because I don't want to slow down the whole system, I install the hook for a specific thread only (the explorer's main thread). This works on Windows 8, but not on Windows 7... I suspect this is because I'm hooking on the wrong thread, but I'm not sure. And anyway, this approach seems overly intrusive.
Creating a message-only window to handle the message. This doesn't work at all, because message-only windows don't receive broadcasted messages.
Is there a reliable way to receive a window message in a shell extension?
A window message initially seemed to be the easiest way to notify the shell extension, but if you think another mechanism would be more appropriate, I'm open to suggestions.
Create a hidden window and listen for the message in its window procedure.
Register a window class that has default values for all the fields apart from the window procedure and class name. You don't need to specify anything else in the window class since the window will never be visible.
When you create the window, pass 0 for the window style. Specifically exclude WS_VISIBLE.
Pass 0 for the WndParent when you create the window. This will make it a top level window and so eligible to receive broadcast messages.
I need to write application A, which intercepts the WM_ACTIVATE message to a window of application B in order to prevent B from becoming top-most application.
Is it possible to do this without DLL injection (add a hook on that message, process and "neutralize" it with a series of WinAPI calls) ?
I think this is what you're after:
LockSetForegroundWindow
http://msdn.microsoft.com/en-us/library/windows/desktop/ms633532(v=vs.85).aspx
Remarks
The system automatically enables calls to SetForegroundWindow if the user presses the ALT key or takes some action that causes the system itself to change the foreground window (for example, clicking a background window).
This function is provided so applications can prevent other applications from making a foreground change that can interrupt its interaction with the user.
Just don't forget to unlock :)
Edit:
Try SetWinEventHook as described here:
Is there Windows system event on active window changed?
Then when the unwanted window comes to the front you can send it to the background.
So, I have a dialog based application using pure WinAPI. There is a main dialog, and then multiple other dialogs that are toolwindows. These toolwindows are meant to free-float around, the user can drag them, hide them, and show them, but they have no taskbar entry. This is what I intended, but the problem is, when I switch from the main window to a different application, then click on the taskbar entry for the main window, the main window will show up, but the toolwindows will not. They stay hidden behind the main window and sometimes windows of other applications, and you cannot use them until you move all of the top-most windows and hunt down the toolwindow.
So, what I'm trying to do to work around this is, when the user restores the window from being minimized, I want to enumerate through all of the tool windows and bring them to the front, maybe by calling SetActiveWindow().
But what message gets sent when the window is restored? I was thinking WM_SHOW, or WM_RESTORE, but they don't exist.
Another question, and if you answer this the first question is irrelevant because I will no longer need to use that workaround: Is there a better method of bringing all tool-windows to the front?
Give the tool windows the WS_POPUP style (and not WS_OVERLAPPED), and make the main window their parent (strictly it is their owner window). That way the tool windows will remain on top of the main window. This may (or may not) be what you want.
The naive answer to the question is to listen to WM_SIZE and respond to a wParam value of SIZE_RESTORED.
The other obvious possibility is to make all the tool windows be owned by the main window. So long as you are happy for the tool windows always to be on top of the main window, this will solve your problem. The owned windows will be hidden when the owner is minimized, and re-shown when the owner is restored.
Learn more about ownership in the MSDN topic on Window Features.
I am debugging an application which, in its message loop, calls IsDialogMessage(). Occasionally, IsDialogMessage() never returns (where never is an interval greater than 1 hour). Based on the symbols for user32.dll available from Microsoft's symbol server, it appears to be stuck in GetNextDlgGroupItem() (or an internal variant of the same), iterating over some set of windows.
The application is multithreaded and frequently receives notification of external events, which arrive as DCOM calls. I suspect that such a call is handled incorrectly in a way that corrupts some window state. If I can learn what sort of state corruption might cause an infinite loop in IsDialogMessage(), I think I will be more easily able to identify the source of the corruption.
I know this is old, but answering for posterity since no one here mentioned it.
More than likely what is going on is trouble with the windows manager determining where to forward a message. If you have a hierarchy of windows, as you probably do, then you need to ensure that non-top-level windows that contain controls themselves must have the WS_EX_CONTROLPARENT style set. If it is a dialog, you use the DS_CONTROL style. The presence of these flags modify the behavior of IsDialogMessage; they identify a window as having its own controls which can receive focus and handle tab order, etc, rather than just being a control itself.
For example, if you have a main frame window, which has a child window with WS_EX_CONTROLPARENT, which has a child window without WS_EX_CONTROLPARENT, which has a child window that has focus, and you hit TAB, you will likely encounter an infinite loop at the same place you mention.
Setting the second child's extended style to include WS_EX_CONTROLPARENT will resolve the issue.
Are you maybe disabling controls (using ::EnableWindow()) without checking first whether that control has the focus? If yes, then the focus gets lost and GetNextDlgGroupItem() gets confused.
Another reason this can happen is if you reparent a modeless dialog. At least this can happen with wxWidgets...
I've made some investigation, trying to answer this question. But only in situation, when parent window is in native MFC project and child is a managed C# Windows Forms. If you have such situation, then you may try 3 resolutions:
Run MFC dialog message loop on Windows Forms side. Here is more info: Integrate Windows Forms Into Your MFC Applications Through C++ Interop
Create 2 threads: one for Windows Forms dialog and one for native dialog. Here you can create dialog in Windows Forms, then with SetParent() set it's parent to native dialog. But be ware: if you add TabControl to Windows Forms, than hang with "IsDialogMessage() never return" will occur.
Make a wrapper for Windows Forms dialog to use in native project. For ex., wrapper may be WPF, see here: Windows Form as child window of an unmanaged app
I've taken information mostly from: http://msdn.microsoft.com/en-us/library/ms229600.aspx
And the temporary cure can be to change focus behavior. For example, disable them, or SetFocus() to parent or child windows only. But I strongly recommend to investigate the real reason, why IsDialogMessage() never return in your case.
I need to understand the differences between windows main/mdi/child/dialogs.... how win32 messages should be propagated... why some messages are present in one type and not other...
There is reference information available here on the MSDN website. If you want more of an introduction or tutorial, then Charles Petzold's book Programming Windows is excellent.
Main window
The application's top window. It is flagged as the process main window and this information can be readily accessed by calling processes with the appropriate permission.
MDI (Multiple document interface) window
This is, typically, in an application main window and it contains a set of MDI Children. This is mostly a window class integrated with Win32 API. I believe it's not treated differently by the operating system as any other window class. Those are becoming extinct in favor of multiple SDI windows (Word 2007).
Child
This is a child window of any other window. Its position, visibility and mostly everything is dependent on the parent window. The children send notifications to their parents. A notification is a specific kind of window message.
Dialog
Dialogs provides easy child creation and input handling based on what 95% of dialogs need. Dialog functions in the API let you create a window and its children using compiled templates in the PE file (.exe). The message handling is also slightly different since you are working mostly with notifications from children.
The main difference with dialogs is when you are using a modal one. The creation call will block until the user closes the dialog. This can make UI updating a little tricky in some situations.
Im not a windows developer, but heres what I understand:
main window - toplevel container which you can active/see in the taskbar.
dialog - little box locking (if modal) your window, not seeable in the taskbar. Mostly used to display message to the user.
mdi (Multiple Document Interface) - Not directly a window but more a simple container for storing child windows. Each child window can be maximized/minimized/closed inside this container, but you wont find any of these in the taskbar.
http://en.wikipedia.org/wiki/Multiple_document_interface