如何验证使用ShellExecute打开的程序是否已准备好接收键盘输入?

时间:2013-05-17 20:04:15

标签: c++ visual-c++ shellexecute

我目前正致力于编写一个简单的程序,使用Firefox的内置更新服务自动更新Firefox(从菜单访问 - > help - > about)。我使用ShellExecute打开Firefox并使用sendInput将键击'Alt + h'和'a'发送到打开的Firefox窗口。我的代码目前正在打开更新菜单,但我正在使用系统睡眠方法调用,以便在调用sendInput之前为Firefox打开足够的时间。有没有办法让我查看Firefox是否已经打开并准备接收键盘输入(比如机器速度较慢的机器在我的机器上需要10秒对1秒)?我不确定sendInput是否有任何相关的方法可以提供此功能,我还无法在MSDN上找到有关此主题的任何信息。谢谢,请参阅随附的代码。

#include <Windows.h>
#include <exception>

const int ERROR_VALUE_RANGE = 32;

using namespace std;

//Method Declarations
void openProgram(char filePath[]);
void openUpdateMenu();


/**
 * exception class for throwing ShellExecute Exceptions
 * throws char* "Error opening program" if any issues arise
 */
class runException: public exception {

    virtual const char* what() const throw() {
        return "Error opening program";
    }

} runEx;

int main (void) {



    // Path to Mozilla Firefox
    char filePath[] = "C:\\Program Files (x86)\\Mozilla Firefox\\firefox.exe"; 

    // Start Firefox using openProgram Method
    try {
        openProgram(filePath);
    }
    catch (exception& e) {
        //Insert code to open dialog box displaying error message;
    }

    Sleep(5000); //sleep for one second while we wait for Windows Update to open

    openUpdateMenu();

    return 0;
}


/**
 * method openProgram opens a file using the ShellExecute method
 * @param filePath - a char array of the complete filepath
 */
void openProgram(char filePath[])  { // throws (runEx)

    HINSTANCE exReturn = ShellExecute(
        HWND_DESKTOP, // Parent is desktop
        "open",       // Opens file (explorer double click behavior)
        filePath,     // Path to Windows Update program
        NULL,         // Parameters
        NULL,         // Default Directory
        SW_SHOW);     // Show the program once it opens

    //if there are any issues opening the file the return value will be less than 32
    if ((int)exReturn <=  ERROR_VALUE_RANGE) { 
        throw runEx; //throws runException
    }

    return;
}

/**
 * method openUpdateMenu sends key commands to Firefox to open the about menu with the         update service
 */
void openUpdateMenu() {

    //set up keyboard emulation
    INPUT Input; //declare input object
    Input.type = INPUT_KEYBOARD;
    Input.ki.time = 0; //let system provide timestamp
    Input.ki.dwExtraInfo = 0;

    //simulate pressing alt down
    Input.ki.wVk = VK_LMENU;
    Input.ki.dwFlags = KEYEVENTF_EXTENDEDKEY;
    SendInput(1, &Input, sizeof(INPUT));

    //simulate pressing 'h' down
    Input.ki.wVk = 0x48;
    Input.ki.dwFlags = KEYEVENTF_EXTENDEDKEY;
    SendInput(1, &Input, sizeof(INPUT));

    //release alt key
    Input.ki.wVk = VK_LMENU;
    Input.ki.dwFlags = KEYEVENTF_KEYUP;
    SendInput(1, &Input, sizeof(INPUT));

    //release 'h' key
    Input.ki.wVk = 0x48;
    Input.ki.dwFlags = KEYEVENTF_KEYUP;
    SendInput(1, &Input, sizeof(INPUT));

    Sleep(500); // wait for menu to open

    //simulate pressing 'a' down
    Input.ki.wVk = 0x41 ;
    Input.ki.dwFlags = KEYEVENTF_EXTENDEDKEY;
    SendInput(1, &Input, sizeof(INPUT));

    //release 'a' key
    Input.ki.wVk = 0x41 ;
    Input.ki.dwFlags = KEYEVENTF_KEYUP;
    SendInput(1, &Input, sizeof(INPUT));

    //wait a second so user can see the program work
    Sleep(1000);
}

0 个答案:

没有答案