Программный предварительный выбор с использованием IFileDialog в C ++ - PullRequest
0 голосов
/ 08 мая 2018

Я озадачен тем, имеет ли IFileDialog возможность программного выбора элемента в диалоговом окне даже без выбора пользователя.

Ex. IFileDialog shows with nothing selected by default

Я надеялся открыть IFileDialog, а затем выбрать элемент / папку по умолчанию в диалоговом окне. Ex. Default selects an item/folder inside the dialog

Кстати, на картинке выше. Я сделал вручную щелкнуть / выбрать папку. Но я надеялся реализовать выбранный по умолчанию элемент внутри IFileDialog.

1 Ответ

0 голосов
/ 10 мая 2018

Процедура, предложенная zett42, работает. Вам необходимо реализовать собственную версию IFileDialogEvents. После подключения к IFileDialog::Advise вы можете запросить путь к IShellView, и это позволит вам изменить выбор.

Этот пример немного глуп, потому что я также заставляю каталог, чтобы убедиться, что у меня есть файл, который я могу выбрать.

struct MyIFileDialogEvents : public IFileDialogEvents {
    bool forcedDir, forcedSel;
    MyIFileDialogEvents() : forcedDir(false), forcedSel(false) {}
    ...
};

STDMETHODIMP MyIFileDialogEvents::OnFolderChanging( IFileDialog *pfd, IShellItem*psiFolder)
{
    if (forcedDir) return S_OK; else forcedDir = true;
    IShellItem*psiwindir;
    HRESULT hr = SHGetKnownFolderItem(FOLDERID_Windows, KF_FLAG_DEFAULT, NULL, IID_IShellItem, (void**) &psiwindir);
    if (!hr)
    {
        hr = pfd->SetFolder(psiwindir); // MSDN says it is OK to change the folder in OnFolderChanging with SetFolder
        psiwindir->Release();
    }
    if (FAILED(hr)) forcedSel = true;
    return S_OK;
}

STDMETHODIMP MyIFileDialogEvents::OnFolderChange(IFileDialog *pfd)
{
    if (forcedSel || !forcedDir) return S_OK; else forcedSel = true;
    IShellItem*psiwindir, *psiexp;
    HRESULT hr = SHGetKnownFolderItem(FOLDERID_Windows, KF_FLAG_DEFAULT, NULL, IID_IShellItem, (void**) &psiwindir);
    if (!hr)
    {
        hr = SHCreateItemFromRelativeName(psiwindir, L"Explorer.exe", NULL, IID_IShellItem, (void**) &psiexp);
        psiwindir->Release();
        if (!hr)
        {
            IServiceProvider*pSP;
            IShellBrowser*pSB;
            IShellView*pSV;
            if (!pfd->QueryInterface(IID_IServiceProvider, (void**) &pSP))
            {
                if (!pSP->QueryService(SID_STopLevelBrowser, IID_IShellBrowser, (void**)&pSB))
                {
                    if (!pSB->QueryActiveShellView(&pSV))
                    {
                        PIDLIST_ABSOLUTE pidl;
                        if (!SHGetIDListFromObject(psiexp, &pidl))
                        {
                            pSV->SelectItem(ILFindLastID(pidl), SVSI_SELECT|SVSI_ENSUREVISIBLE|SVSI_FOCUSED|SVSI_DESELECTOTHERS);
                            CoTaskMemFree(pidl);
                        }
                        pSV->Release();
                    }
                    pSB->Release();
                }
                pSP->Release();
            }
            psiexp->Release();
        }
    }
    return S_OK;
}
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...