Transparent UI / hidden UI after BringToForeground - c++

I am programming in C++ using Qt (on Windows), I have a GUI application that can be run on the command line so that users can schedule it to be run using Scheduled Tasks.
Everything was working fine (I think), except when a user tried to schedule the task with the "run when user is logged on or not" option is checked. In this instance the application would run fine, but not pop up the GUI.
I thought maybe my problem was similar to this: https://serverfault.com/questions/101671/scheduled-tasks-w-gui-issue
I thought I found the issue because my GetProcID call was returning a list of ProcessId's and I was only using the first one it returned, which caused some issues. That process ID was then passed to BringToForeground.
After this change it now brings up a transparent, or non-existent other than the application icon on some machines (basically every test except my 3 machines that can debug). Works exactly as required on my test machines.
The application works well if the GUI app is already running and you make the same call on the command line (it passes the call to that process to run). The app also works fine in normal UI mode, (no command line params passed)
EDIT:
Does anyone have any ideas what might cause this? I am thinking it has something to do with the app not starting on the correct Desktop, but don't have a ton of experience with those and have no idea where to even begin.
EDIT 2: Only seem to have the issue when it is run remotely, or through virtualization. (still confirming if this is truly the case)

Related

How to write a Windows application that doesn't immediately release control to the calling application

I am writing a small application (.exe) that does some tasks and then returns an exit status. It is meant to be run regularly from another application (which I have no control over) that uses the status code to determine further action.
It works just fine if I compile and link it as a console app. However, that makes the console window flash briefly on the screen every time it is run, which is a little bit annoying. I tried to make it a Windows app, but the problem then is that Windows releases control to the calling application (or the OS) immediately after start. Thus, any exit status my application generates is returned too late and is never seen by the calling application.
Is there a way to force my app to stay in the foreground, so to speak, and not release control before it actually exits? I tried to force the entry point to be the "main" function instead of "WinMain", but that didn't help.
It isn't a question of whether the child "releases control" or not - Windows is a preemptive multitasking operating system, so all processes run at once. If the parent process waits for the child to exit, it is because the programmer told it to wait for the child to exit.
It isn't easy to make a program wait for console programs but not non-console programs. The command shell (cmd.exe) works this way when run interactively, but there isn't any API that does this as far as I know. Assuming that it isn't deliberate - which would be very strange in this context - the only explanation I can think of is that the program is running an interactive command shell and feeding in your command via standard input. That's the wrong thing to do, but I have seen people trying to do it that way before.
Presumably you can choose the command line that the parent executes. Try this:
start /wait myapp.exe
(That's how you would do it in an interactive command shell.)
If that doesn't work, you may have to consult the author of the parent process for advice.

Using the console in a GUI app in windows, only if its run from a console

My application is a GUI app that has helpful (though optional) information through the terminal (via cout).
In Windows I either have a console appear (by compiling as a console app, or allocating it dynamically) or I don't.
My intention is to make use of the console IF it is being run from the console, but ignore the console completely if it was not. (Essentially what happens in Linux and OS X).
I do not wish to redirect to a file (and in the case of using cin, this is not a viable solution anyway).
Is there a way to attach a GUI app in Windows to the console it is run from, if and only if it is run from a console?
and in the case of using cin, this is not a viable solution anyway
This is the killer detail in your question. It is simple on paper, just first call AttachConsole(ATTACH_PARENT_PROCESS) to try to attach to an existing console. That will fail when your program got started from a GUI program like Explorer or a desktop shortcut. So if it returns FALSE then call AllocConsole() to create your own console.
Using cin is a problem however. The command processor pays attention to your EXE and checks if it is console mode app or a GUI app. It will detect a GUI app in your case and then doesn't wait for the process to complete. It displays the prompt again and waits for input. You will then also wait for input but you'll lose, the command processor got there first. Your output is also intermingled with the command prompt, the easy problem to solve.
There's a simple workaround for that, your user should start your program with start /wait yourapp to tell the command processor to wait for the process to complete. Problem is: nobody ever uses that. And the user will not realize what happens when they type input, intending it to go into your program but it is actually interpreted by the command processor. Producing a mystifying error message or formatting the hard drive.
Only two good ways to solve this unsolvable problem. Either build your program as a console mode app and call FreeConsole() when you find out you want to display a GUI. Or always call AllocConsole(). These are not great alternatives. The first approach is the one used by the Java JVM on Windows. One of the oldest bugs filed against the JVM and driving Java programmers completely batty from the flashing console window.
The third alternative is the only decent one, and the one you don't want, create another EXE that will always use the console. Like Java does, javaw.exe vs java.exe.
A trick is possible, you can rename that file from "yourapp2.exe" to "yourapp.com". It will be picked first when the user types "yourapp" at the command line prompt, a desktop shortcut can still point to "yourapp.exe". Visual Studio uses this trick, devenv.com vs devenv.exe.
You can check CONSOLE_SCREEN_BUFFER_INFO (via GetConsoleScreenBufferInfo) on startup to determine if you've been run from within an existing console. If the buffer's position is 0,0, you were run from outside of the console. For details, see this Microsoft Knowledgebase Article which describes the process.
In order for this to work, you need to compile your application as a console application (using /SUBSYSTEM:CONSOLE), and then detach yourself from the console if the application started a new console (buffer at 0,0). This will cause the program to properly "attach" to the calling console when launched from a command line.
As others have pointed out you have to create a console app and a window app. So, you'd end up with console.exe and app.exe. To make it less obvious at the command-line, you can take advantage of the PATHEXT trick like devenv does. cmd.exe treats a file as a command if its extension is in the PATHEXT environment variable. COM is there by default so you could rename console.exe as app.com, allowing the command app to start the console app attached to the current console.
Note: Of course, a console app can show a GUI if desired.
The difference in the build between app.com and app.exe depends on your build system but it could just be the one attribute that sets the output type. With msbuild (for .vcxproj files), it's just a matter of another build configuration.
you can create an application in console that get a line using argc and prints it;
////
int main(int argc, char *argv[])
{
//here print argv....using cout or printf
}
save the file as console.exe in the folder of your app.
now in your app if you want to see any line in console you can call the command
system("console.exe this is the line i want to print and see in console");

Auto-Restart a Console Application

I am looking for the console application equivalent of Application.Restart() but cannot seem to find a way to do this.
It has been suggested by others to simply call my Sub Main with Args when I need to restart. However the reason I need the functionality to physically restart the application is because the first thing I do is check for updates and install them if they any are availible.
The update technique itself works perfectly, the system installs new updates but changes do not take effect until next time the application runs obviously.
As the application is run from a batch file as a scheduled task only once a week any updates I release would not take effect for two weeks!
I had the same problem with a windows forms application however the ability to call Application.Restart allows changes to take place imediately. Can the same be achieved when creating a console application?
2 Possibilities i can think of.
First one start another instance of the application and close the current one using something like
System.Diagnostics.Process.Start(ProcessStartInfo startInfo)
and
Environment.Exit(int exitCode)
second if it's not possible to run 2 instances at the same time for some reasons u can create another application that gets started by the batch. Make it run your application and let it get an info if the updating process is done so it can first close the current application and then run another one

How to force a Qt Application to be the active/foreground window upon execution in OSX?

I'm going through Qt tutorials on OSX. One thing I noticed is that when I launch the executable (e.g. the push button hello world example), the app will launch as a background window and I have to switch tasks to bring it into the foreground. How can I force the Qt application window to be the foreground window upon execution?
I'd like to do this since it's how most apps behave, not to mention that manually switching tasks slows down my edit-compile-run-debug cycle).
The behavior you observe is due to interaction with the debugger when you start the application under the debugger using ⌘-Y. If you simply run it using ⌘-R, it behaves as you expect. Your application itself is fine.
Starting OS X applications by directly firing up the executable from within the app bundle from the terminal will act similarly to running them using ⌘-Y -- they all start in the background. Qt is probably mimicking whatever magic Finder does when it starts the process via ⌘-R -- said magic may reduce to simply bringing the child app to the foreground. gdb on OS X is not so "clever", and probably for a good reason.
OS X approach is to try harder not to steal focus -- a good thing IMHO.
If you merely want to run the application, not debug it, then modify your launch command to look like open -a '/Users/daj/foo/bar/baz.app', where baz.app is the app bundle folder. Do not append a trailing slash.
If you can coax your debugger to follow through to child processes, then you can of course launch open itself under gdb, and it will work as expected -- with your child application on top.

Windows Shell Extension Not Calling Initialize

I was hoping somebody here had some insight into what could be causing this problem. I've implemented several COM extensions for Explorer that provide ShellIconOverlays and a ContextMenu, and the overlays work perfectly. The Context Menu works fine when I click on the desktop but when I right click in any explorer instance, I can see the interface being queried in the debugger and an instance of IShellExtInit being generated but the initialize function doesn't get called in the explorer instances, but it is called fine from the desktop and a ContextMenu item is queried immediately after.
Has anybody here seen anything like this before?
If you're debugging a shell extension, chances are that you've had occasions to terminate the running explorer.exe process and start a new one. When you started a new one, was it running with the same integrity level as the original?
Do your Explorer settings say to browse files in a new process? If so, is that process running with the same integrity level as the original?
Also, since you're running a debugger, chances are that you built a debug build. Does explorer.exe sometimes try to load the debug build of your DLL and sometimes try to load the release build of your DLL?
OK, I run into the exact same problem here, and it turns out that the issue has to do with
ThreadingModel = Apartment
Basically, what I think you are experiencing, is that the second thread of explorer.exe (desktop runs in STA thread) uses the default (legacy) ThreadingModel - and expects your COM to implement IMarshal to do IPC. Apartment ThreadingModel allows multiple instances of your IShellExt class to co-exist.
Caveat - If you are using ActiveQt to develop Context Menu Shell Extensions, there are few more tricks to use.