BringWindowToTop не работает, даже если я получаю дескриптор окна класса - PullRequest
2 голосов
/ 17 ноября 2010

Я регистрирую свой класс следующим способом:

BOOL CNDSClientDlg::InitInstance()
{
    //Register Window Updated on 16th Nov 2010, @Subhen
    // Register our unique class name that we wish to use
    WNDCLASS wndcls;
    memset(&wndcls, 0, sizeof(WNDCLASS));

    wndcls.style = CS_DBLCLKS | CS_HREDRAW | CS_VREDRAW;
    wndcls.lpfnWndProc  =  ::DefWindowProc; 
    wndcls.hInstance = AfxGetInstanceHandle();
    wndcls.hbrBackground = (HBRUSH)(COLOR_WINDOW + 1);
    wndcls.lpszMenuName = NULL;

    //Class name for using FindWindow later
    wndcls.lpszClassName = _T("CNDSClientDlg");
    // Register new class and exit if it fails

    if(!AfxRegisterClass(&wndcls)) // [C]

    {
        return FALSE;
    }
}

, а затем вызов метода InitInstance и создание окна в конструкторе класса:

CNDSClientDlg::CNDSClientDlg(CWnd* pParent /*=NULL*/)
    : CDialog(CNDSClientDlg::IDD, pParent)

{
InitInstance();

    HWND hWnd;
    hInst = AfxGetInstanceHandle(); // Store instance handle in our global variable
    hWnd = CreateWindow(_T("CNDSClientDlg"), "NDS", WS_OVERLAPPEDWINDOW,
                        CW_USEDEFAULT, 0, CW_USEDEFAULT, 0, NULL, NULL, hInst, NULL);


}

Теперь в другом приложении я нахожу окно и пытаюсь вывести его наверх:

Редактировать Возможность принести недавно созданные Windows с кодом ниже

 CWnd *pWndPrev = NULL;
                    CWnd *FirstChildhWnd = NULL;
                    pWndPrev = CWnd::FindWindow(_T("CNDSClientDlg"),NULL);
                    if(pWndPrev != NULL)
                    {
                        //pWndPrev->BringWindowToTop();
                        WINDOWPLACEMENT wndplacement;
                        pWndPrev->GetWindowPlacement(&wndplacement);
                        wndplacement.showCmd = SW_RESTORE;
                        pWndPrev->SetWindowPlacement(&wndplacement);
                        pWndPrev->SetForegroundWindow();

                        FirstChildhWnd = pWndPrev->GetLastActivePopup();
                        if (pWndPrev != FirstChildhWnd)
                        {
                            // a pop-up window is active, bring it to the top too
                            FirstChildhWnd->GetWindowPlacement(&wndplacement);
                            wndplacement.showCmd = SW_RESTORE;
                            FirstChildhWnd->SetWindowPlacement(&wndplacement);
                            FirstChildhWnd->SetForegroundWindow();
                        }

Я могу найти окно, поскольку pWndPrev не NULL, но оно не выводит мое приложение на передний план Нужно ли регистрировать любой другой класс вместо CNDSClientDlg. Я хочу довести свое приложение MFC до вершины.

Ответы [ 4 ]

12 голосов
/ 17 ноября 2010

Несколько вещей, на которые стоит посмотреть ...

1) Попробуйте SetForegroundWindow () вместо BringWindowToTop (). Прошло некоторое время с тех пор, как я занялся программированием на Win32, но мне кажется, что BringWindowToTop () имеет некоторые ограничения (особенно при работе с окнами в разных процессах).

2) Существуют некоторые правила, которые Microsoft ввела в действие для SetForegroundWindow (), начиная с Windows 2000. Короткая версия заключается в том, что только переднее приложение может изменять переднее окно. Идея состоит в том, что приложение, которое не является передним, не может «перескочить» перед активным приложением. Если фоновое приложение вызывает SetForegroundWindow (), Windows высветит кнопку панели задач для приложения, но фактически не выведет приложение на передний план. Пользователь должен сделать это. Я упрощаю правила, но это может быть чем-то, на что стоит обратить внимание в зависимости от вашего конкретного сценария.

2 голосов
/ 17 ноября 2010

Вам может потребоваться вызвать AllowSetForegroundWindow в вашем "другом" приложении перед вызовом SetForegroundWindow.

Предполагается, что ваше другое приложение является приложением переднего плана и пытается передать свое состояние переднего плана приложению с окном.

Если ни одно из приложений не является приложением переднего плана, то вы не предполагали, что могли бы вывести окно на передний план, хотя есть способы сделать это (как случайно, так и специально). *

0 голосов
/ 18 сентября 2012
SetWindowPos(&wndTopMost, -1, -1, -1, -1,  SWP_NOMOVE | SWP_NOSIZE | SWP_SHOWWINDOW);
SetForegroundWindow();
...