Qt: showMaximized() not working in Windows - c++

I am opening a file in my application (in Windows) by double-clicking it. I am passing the file name as received through argument to my open logic. There I am calling showMaximized(), but it is not getting picked up. The window that opens up is not maximized and defaultly located at the top-left corner of the screen.
Note that all this logic flow is through main() and hence showMaximized() is probably getting called before the event loop starts. Is this stopping the showMaximized() to work properly? If yes, how to solve this?
I also tried using QTimer::singleShot(0,...,...) (so as to let the event loop start) but this has even stopped the launching of the non-maximized screen.
PS: In Mac the screen is getting maximized as there it happens through event (QEvent::FileOpen)

Simplest workaround is use resize(800,600) before using showMaximized(). I have similar error in Qt 5.7.0 on Windows 8.1.

My answer is late but I write it in case it helps someone.
I am experimenting the same problem on Windows 11 with PyQt 6.
Initially I used the solution proposed by Vasilyev Eugene but it fails in some cases.
The best solution that I found was to use sigleShot with 1000ms of delay:
QtCore.QTimer.singleShot(1000, self.showMaximized)
The time is almost imperceptible to the final user, and you can experiment with lower values, except 0 apparently.
This solution is for PyQt but it is also applicable for Qt.

So on Windows I used a timer in the Application Windows.
I know it is smoehow ugly, but it works...
ApplicationWindow {
Timer {
id: fullscreenTimer
interval: 1000; running: false; repeat: false;
onTriggered: root.showFullScreen();
}
Component.onCompleted: {
fullscreenTimer.start();
}
}

The very first time a process calls ShowWindow, the show command is ignored and uses the command provided in the STARTUPINFO structure (which should correspond with the nCmdShow parameter in WinMain).
http://msdn.microsoft.com/en-us/library/windows/desktop/ms633548%28v=vs.85%29.aspx
This surprising behavior has a tendency to manifest itself in problems like the one you describe. You may be able to resolve it by simply issuing QT's showMaximized call twice if you don't want to use any Win32 API calls directly.

Related

Propper way to deinitialize GTK

I'm writing a c++ application that creates a GTK3 window at some point, while also running X11 code in other places.
For the pure X11 part i'm using XOpenDisplay() to open a display.
Running the X11 part and opening a GTK window afterwards works fine. Also running the X11 part multiple times is no problem as i release the display there using XCloseDisplay.
The problem i'm facing occurs when i try to run the X11 code after gtk has been initialized (to be more specific, calling XOpenDisplay() after the gtk initialization).
I'm suspecting that after running gtk_init() the display is never being released, even after gtk_main_quit().
I didn't find anything about deinitialization in the gtk3 documentation. Is there any way to propperly deinitialize gtk or free the display in another way?
The solution was completely unrelated. I was setting the DISPLAY environment variable twice by accident. Apparently gtk can handle this but XOpenDisplay crashes.
I have added a test to only set it once, now everything works. Perhaps gtk does propperly deinitialize after gtk_main_quit()

How can I hide the mouse cursor?

I wanna ask if someone can provide me a c++ code in which I can hide/show the pointer of the mouse when pressing a specific key..
I found several codes written for only TURBO C++, none of which can be compiled and run using dev c++ or even visual c++..
I tried running the codes I found in Dev C++ but I only get lots of errors and incompatibilities..
I also found several articles that says I can use the function ShowCursor but it just wouldn't work..
In fact hiding the cursor can turn out to be quite a task, depending on what you want to achive. If you're programming a GUI-application using the WinAPI it is pretty easy.
Just calling ShowCursor(false); once might turn out not to work in some cases though, since the ShowCursor function only "sets an internal display counter". The cursor is displayed until this counter is smaller than 0 (see msdn on it). You could try something like this:
while(ShowCursor(false)>=0);
to ensure the counter gets below 0.
This will however only hide the cursor inside your applications window, if you're using newer Windows versions like Windows 7. Hiding the cursor all over the system could turn out to be a lot more difficult.
If you are programming a console application ShowCursor won't show any effect as far as I've tested it. Using the following code:
while(ShowCursor(false)>=0);
std::cout<<ShowCursor(false)<<std::endl;
std::cout<<ShowCursor(true)<<std::endl;
we can see, that the counter definitely is below 0, but still the cursor is displayed. I haven't come up with a solution to this so far.
If you look at the documentation for the SetCursor function, setting the cursor to a NULL handle (e.g SetCursor(NULL)) will remove the cursor from the screen.

What function is called when Alt-Enter is pressed?

I have a game app that has the ability to go fullscreen and back to windowed when Alt-Enter is pressed. However, when it goes fullscreen, I get the following warning from DirectX:
DXGI Warning: IDXGISwapChain::Present: Fullscreen presentation inefficiencies incurred due to application not using IDXGISwapChain::ResizeBuffers appropriately, specifying a DXGI_MODE_DESC not available in IDXGIOutput::GetDisplayModeList, or not using DXGI_SWAP_CHAIN_FLAG_ALLOW_MODE_SWITCH.
I've already ruled out the second two possibilities through testing, so I know the only reasons left for the warning to pop up are either IDXGISwapChain::ResizeBuffers isn't being used right, or Windows is just bugged. Since I can't debug the 2nd possibility, I'm sticking with the ResizeBuffers problem. To debug this, I want to look at what happens when Alt-Enter is pressed going from windowed to fullscreen. However, the app does not seem to be calling my ResizeDXGIBuffers method; in fact, it seems that Alt-Enter is embedded into windows or DirectX somewhere, and I don't know how to find the chain of function calls that go off when it is pressed. EDIT: When my method is put in the WM_ACTIVATEAPP handler, it is called, but this is not what i meant. If i take it out of that message handler, the window STILL goes to fullscreen, even though I am not calling any functions to make the window fullscreen myself. So Alt+Enter must be automatically calling some internal function to do this.
So that is my question: Does anyone know what function is called by windows and/or DirectX 11 when Alt-Enter is pressed?
EDIT: As the tags for this question say, I am using DirectX 11 on a Windows machine. Specifically, Windows 7 64-bit.
EDIT 2: I now completely eat the Alt+Enter keystroke and manually store the state of Alt+Enter being pressed so that I know for certain only my code is being called. The warning I spoke of above persists, however. I am following the MSDN best practices as well, so I don't know where to go from here.
Try handling the WM_ACTIVATEAPP message.
I do not know which framework you use to create your windows, so I can't tell how to concretely handle this message.
After looking at the MSDN best practices page and re-working my code to reflect all of the practices described, the warning has disappeared. I hope this helps anyone else that has the same problem.
Also, thanks to Hans Passant for the link. I already fixed it by the time you posted it, but thanks anyways.

Is it possible to embed a command prompt in a win32 app?

In linux and when installing packages etc. There are some installers that have a progress bar and a dos window which shows the files being extracted etc. How can i add this window to my C++ Win32 programs so that i can have it showing the tasks im doing? I cannot find any documentation on MSDN.
Question: How can i add a console window (if that's what its called, sure looks like one) in my program to show the details of the task at hand being done?
Here is a window with what i am asking.. (personal info so I erased the details. :]
You cannot embed a real console window inside another window (although a windowed process can have a separate console window). While it looks like a console window / command prompt, it is just a matter of appearances. What you want to do is create a sub-window/control with similar characteristics as a console window and then redirect the console output from the application(s) being run to append to that sub-window. For more information on how to do redirect the console output in Windows, see http://support.microsoft.com/kb/190351.
That "dos window" is a regular edit control: CreateWindow(ES_MULTILINE, EDIT, ...
However, it has the font set to a fixed-width one (Looks like courier). This is done by sending WM_SETFONT to the edit control.
#user995048 says "You cannot embed a real console window inside another window". But "cannot" is a strong word! I can run an entire virtualized computer in a window if I wish. :) So one can quite reasonably intuit that there are ways of doing what you say.
Sure, it is true that what you've seen are almost certainly cases of output redirection into a custom widget, designed to mimic the simple appearance of a terminal. However...if you want to embed one application's window inside another, there are things you can look into which might fit. Cooperative methods exist like GtkPlug, for instance:
http://developer.gnome.org/gtk/2.24/GtkPlug.html
To actually capture a not-designed-to-cooperate app's window and throw it in your app would be trickier. But possible, just as screen captures and virtual machines are possible. Probably best to avoid that sort of thing unless there's really a cause for it, though...
Try this
http://www.codeguru.com/cpp/misc/misc/article.php/c277/
link. I think the solution provided is what you need.
I tried it many years ago and it worked. I have not tried it in newer versions of windows though.

MFC Edit Box - Multiple Characters per Keystroke?

I am trying to create a simple dialog in MFC using Visual C++. My problem is that when I get the dialog on the screen and try to type in an Edit Box field, if I type the letter 'a' once, it appears in the edit box as 'aaaaaaaaaaa' (that's 12 a's). Furthermore, if I try to navigate around in the box using the arrow keys, the carat moves 12 characters at a time.
It's not just a display error, as the output from the editbox is still "aaaaaaaaaaaa".
I'd post code, but there's really none to post. I added the edit box using the Toolbox in Visual Studio and assigned a variable to it in my class so this isn't any sort of special edit box.
If anyone has any thoughts as to what might be happening it would be greatly appreciated. Unfortunately, I don't know where to begin.
Thank as always.
To debug this, add PreTranslateMessage function to your dialog, and see exactly how many times the keydown is being processed.
BOOL DialogName::PreTranslateMessage(MSG* pMsg)
{
if(pMsg->message==WM_KEYDOWN)
{
// TODO: see what is going on here
return TRUE; //do not dispatch this message, so keydown will have no effect
}
return CDialog::PreTranslateMessage(pMsg);
}
Are you capturing any events such as WM_KEYUP in your PreTranslateMessage() function or anywhere else in your app ?
If you have overridden the default handling for keyboard events, it might cause the symptoms you are seeing.
For some reason this brings back vague memories of early struggles with MFC. Have you looked for mutual recursion at all? I was forever doing something in one bit of the app that sent a message (unbeknown to me) that was picked up by another method that called the first method...
My guess is it's one of those smack the forehead ones; it gives me this nagging sense of deja vu that I can't make concrete.
If it's mutual recursion you should be able to see it in the call stack, if you can find the right place for a break point.
Is this happening for a fresh project, or can you recreate this problem in a fresh project?
It'll help discern whether it's something you've done in your code, or your install.
I installed service pack 2 in my WinXp 64 OS and the problem get solved for me :)