Home | Info | Community | Development | myReactOS | Contact Us
ReactOS Development > Doxygenfiledlgbrowser.c
Go to the documentation of this file.
00001 /* 00002 * Implementation of IShellBrowser for the File Open common dialog 00003 * 00004 * Copyright 1999 Francois Boisvert 00005 * Copyright 1999, 2000 Juergen Schmied 00006 * 00007 * This library is free software; you can redistribute it and/or 00008 * modify it under the terms of the GNU Lesser General Public 00009 * License as published by the Free Software Foundation; either 00010 * version 2.1 of the License, or (at your option) any later version. 00011 * 00012 * This library is distributed in the hope that it will be useful, 00013 * but WITHOUT ANY WARRANTY; without even the implied warranty of 00014 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 00015 * Lesser General Public License for more details. 00016 * 00017 * You should have received a copy of the GNU Lesser General Public 00018 * License along with this library; if not, write to the Free Software 00019 * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA 00020 */ 00021 00022 #include <stdarg.h> 00023 #include <stdio.h> 00024 #include <string.h> 00025 00026 #define COBJMACROS 00027 #define NONAMELESSUNION 00028 #define NONAMELESSSTRUCT 00029 00030 #include "windef.h" 00031 #include "winbase.h" 00032 #include "winnls.h" 00033 #include "wingdi.h" 00034 #include "winuser.h" 00035 #include "winreg.h" 00036 00037 #define NO_SHLWAPI_STREAM 00038 #include "shlwapi.h" 00039 #include "filedlgbrowser.h" 00040 #include "cdlg.h" 00041 #include "shlguid.h" 00042 #include "servprov.h" 00043 #include "wine/debug.h" 00044 00045 WINE_DEFAULT_DEBUG_CHANNEL(commdlg); 00046 00047 typedef struct 00048 { 00049 00050 IShellBrowser IShellBrowser_iface; 00051 ICommDlgBrowser ICommDlgBrowser_iface; 00052 IServiceProvider IServiceProvider_iface; 00053 LONG ref; /* Reference counter */ 00054 HWND hwndOwner; /* Owner dialog of the interface */ 00055 00056 } IShellBrowserImpl; 00057 00058 static inline IShellBrowserImpl *impl_from_IShellBrowser(IShellBrowser *iface) 00059 { 00060 return CONTAINING_RECORD(iface, IShellBrowserImpl, IShellBrowser_iface); 00061 } 00062 00063 static inline IShellBrowserImpl *impl_from_ICommDlgBrowser( ICommDlgBrowser *iface ) 00064 { 00065 return CONTAINING_RECORD(iface, IShellBrowserImpl, ICommDlgBrowser_iface); 00066 } 00067 00068 static inline IShellBrowserImpl *impl_from_IServiceProvider( IServiceProvider *iface ) 00069 { 00070 return CONTAINING_RECORD(iface, IShellBrowserImpl, IServiceProvider_iface); 00071 } 00072 00073 /************************************************************************** 00074 * vtable 00075 */ 00076 static const IShellBrowserVtbl IShellBrowserImpl_Vtbl; 00077 static const ICommDlgBrowserVtbl IShellBrowserImpl_ICommDlgBrowser_Vtbl; 00078 static const IServiceProviderVtbl IShellBrowserImpl_IServiceProvider_Vtbl; 00079 00080 /* 00081 * Helper functions 00082 */ 00083 00084 #define add_flag(a) if (flags & a) {strcat(str, #a );strcat(str," ");} 00085 static void COMDLG32_DumpSBSPFlags(UINT uflags) 00086 { 00087 if (TRACE_ON(commdlg)) 00088 { 00089 unsigned int i; 00090 static const struct { 00091 DWORD mask; 00092 const char *name; 00093 } flags[] = { 00094 #define FE(x) { x, #x} 00095 /* SBSP_DEFBROWSER == 0 */ 00096 FE(SBSP_SAMEBROWSER), 00097 FE(SBSP_NEWBROWSER), 00098 00099 /* SBSP_DEFMODE == 0 */ 00100 FE(SBSP_OPENMODE), 00101 FE(SBSP_EXPLOREMODE), 00102 FE(SBSP_HELPMODE), 00103 FE(SBSP_NOTRANSFERHIST), 00104 00105 /* SBSP_ABSOLUTE == 0 */ 00106 FE(SBSP_RELATIVE), 00107 FE(SBSP_PARENT), 00108 FE(SBSP_NAVIGATEBACK), 00109 FE(SBSP_NAVIGATEFORWARD), 00110 FE(SBSP_ALLOW_AUTONAVIGATE), 00111 00112 FE(SBSP_NOAUTOSELECT), 00113 FE(SBSP_WRITENOHISTORY), 00114 00115 FE(SBSP_REDIRECT), 00116 FE(SBSP_INITIATEDBYHLINKFRAME), 00117 }; 00118 #undef FE 00119 TRACE("SBSP Flags: %08x =", uflags); 00120 for (i = 0; i < (sizeof(flags) / sizeof(flags[0])); i++) 00121 if (flags[i].mask & uflags) 00122 TRACE("%s ", flags[i].name); 00123 TRACE("\n"); 00124 } 00125 } 00126 00127 static void COMDLG32_UpdateCurrentDir(const FileOpenDlgInfos *fodInfos) 00128 { 00129 LPSHELLFOLDER psfDesktop; 00130 STRRET strret; 00131 HRESULT res; 00132 00133 res = SHGetDesktopFolder(&psfDesktop); 00134 if (FAILED(res)) 00135 return; 00136 00137 res = IShellFolder_GetDisplayNameOf(psfDesktop, fodInfos->ShellInfos.pidlAbsCurrent, 00138 SHGDN_FORPARSING, &strret); 00139 if (SUCCEEDED(res)) { 00140 WCHAR wszCurrentDir[MAX_PATH]; 00141 00142 res = StrRetToBufW(&strret, fodInfos->ShellInfos.pidlAbsCurrent, wszCurrentDir, MAX_PATH); 00143 if (SUCCEEDED(res)) 00144 SetCurrentDirectoryW(wszCurrentDir); 00145 } 00146 00147 IShellFolder_Release(psfDesktop); 00148 } 00149 00150 /* copied from shell32 to avoid linking to it */ 00151 static BOOL COMDLG32_StrRetToStrNW (LPVOID dest, DWORD len, LPSTRRET src, LPCITEMIDLIST pidl) 00152 { 00153 TRACE("dest=%p len=0x%x strret=%p pidl=%p stub\n",dest,len,src,pidl); 00154 00155 switch (src->uType) 00156 { 00157 case STRRET_WSTR: 00158 lstrcpynW(dest, src->u.pOleStr, len); 00159 COMDLG32_SHFree(src->u.pOleStr); 00160 break; 00161 00162 case STRRET_CSTR: 00163 if (len && !MultiByteToWideChar( CP_ACP, 0, src->u.cStr, -1, dest, len )) 00164 ((LPWSTR)dest)[len-1] = 0; 00165 break; 00166 00167 case STRRET_OFFSET: 00168 if (pidl) 00169 { 00170 if (len && !MultiByteToWideChar( CP_ACP, 0, ((LPCSTR)&pidl->mkid)+src->u.uOffset, 00171 -1, dest, len )) 00172 ((LPWSTR)dest)[len-1] = 0; 00173 } 00174 break; 00175 00176 default: 00177 FIXME("unknown type!\n"); 00178 if (len) 00179 { *(LPWSTR)dest = '\0'; 00180 } 00181 return(FALSE); 00182 } 00183 return TRUE; 00184 } 00185 00186 /* 00187 * IShellBrowser 00188 */ 00189 00190 /************************************************************************** 00191 * IShellBrowserImpl_Construct 00192 */ 00193 IShellBrowser * IShellBrowserImpl_Construct(HWND hwndOwner) 00194 { 00195 IShellBrowserImpl *sb; 00196 FileOpenDlgInfos *fodInfos = GetPropA(hwndOwner,FileOpenDlgInfosStr); 00197 00198 sb = COMDLG32_SHAlloc(sizeof(IShellBrowserImpl)); 00199 00200 /* Initialisation of the member variables */ 00201 sb->ref=1; 00202 sb->hwndOwner = hwndOwner; 00203 00204 /* Initialisation of the vTables */ 00205 sb->IShellBrowser_iface.lpVtbl = &IShellBrowserImpl_Vtbl; 00206 sb->ICommDlgBrowser_iface.lpVtbl = &IShellBrowserImpl_ICommDlgBrowser_Vtbl; 00207 sb->IServiceProvider_iface.lpVtbl = &IShellBrowserImpl_IServiceProvider_Vtbl; 00208 SHGetSpecialFolderLocation(hwndOwner, CSIDL_DESKTOP, 00209 &fodInfos->ShellInfos.pidlAbsCurrent); 00210 00211 TRACE("%p\n", sb); 00212 00213 return &sb->IShellBrowser_iface; 00214 } 00215 00216 /*************************************************************************** 00217 * IShellBrowserImpl_QueryInterface 00218 */ 00219 static HRESULT WINAPI IShellBrowserImpl_QueryInterface(IShellBrowser *iface, 00220 REFIID riid, 00221 LPVOID *ppvObj) 00222 { 00223 IShellBrowserImpl *This = impl_from_IShellBrowser(iface); 00224 00225 TRACE("(%p)\n\t%s\n", This, debugstr_guid(riid)); 00226 00227 *ppvObj = NULL; 00228 00229 if(IsEqualIID(riid, &IID_IUnknown)) /*IUnknown*/ 00230 { *ppvObj = This; 00231 } 00232 else if(IsEqualIID(riid, &IID_IOleWindow)) /*IOleWindow*/ 00233 { *ppvObj = This; 00234 } 00235 00236 else if(IsEqualIID(riid, &IID_IShellBrowser)) /*IShellBrowser*/ 00237 { *ppvObj = This; 00238 } 00239 00240 else if(IsEqualIID(riid, &IID_ICommDlgBrowser)) /*ICommDlgBrowser*/ 00241 *ppvObj = &This->ICommDlgBrowser_iface; 00242 else if(IsEqualIID(riid, &IID_IServiceProvider)) /* IServiceProvider */ 00243 *ppvObj = &This->IServiceProvider_iface; 00244 00245 if(*ppvObj) 00246 { IUnknown_AddRef( (IShellBrowser*) *ppvObj); 00247 return S_OK; 00248 } 00249 FIXME("Unknown interface requested\n"); 00250 return E_NOINTERFACE; 00251 } 00252 00253 /************************************************************************** 00254 * IShellBrowser::AddRef 00255 */ 00256 static ULONG WINAPI IShellBrowserImpl_AddRef(IShellBrowser * iface) 00257 { 00258 IShellBrowserImpl *This = impl_from_IShellBrowser(iface); 00259 ULONG ref = InterlockedIncrement(&This->ref); 00260 00261 TRACE("(%p,%u)\n", This, ref - 1); 00262 00263 return ref; 00264 } 00265 00266 /************************************************************************** 00267 * IShellBrowserImpl_Release 00268 */ 00269 static ULONG WINAPI IShellBrowserImpl_Release(IShellBrowser * iface) 00270 { 00271 IShellBrowserImpl *This = impl_from_IShellBrowser(iface); 00272 ULONG ref = InterlockedDecrement(&This->ref); 00273 00274 TRACE("(%p,%u)\n", This, ref + 1); 00275 00276 if (!ref) 00277 { 00278 COMDLG32_SHFree(This); 00279 TRACE("-- destroyed\n"); 00280 return 0; 00281 } 00282 return ref; 00283 } 00284 00285 /* 00286 * IOleWindow 00287 */ 00288 00289 /************************************************************************** 00290 * IShellBrowserImpl_GetWindow (IOleWindow) 00291 * 00292 * Inherited from IOleWindow::GetWindow 00293 * 00294 * See Windows documentation for more details 00295 * 00296 * Note : We will never be window less in the File Open dialog 00297 * 00298 */ 00299 static HRESULT WINAPI IShellBrowserImpl_GetWindow(IShellBrowser * iface, 00300 HWND * phwnd) 00301 { 00302 IShellBrowserImpl *This = impl_from_IShellBrowser(iface); 00303 00304 TRACE("(%p)\n", This); 00305 00306 if(!This->hwndOwner) 00307 return E_FAIL; 00308 00309 *phwnd = This->hwndOwner; 00310 00311 return (*phwnd) ? S_OK : E_UNEXPECTED; 00312 00313 } 00314 00315 /************************************************************************** 00316 * IShellBrowserImpl_ContextSensitiveHelp 00317 */ 00318 static HRESULT WINAPI IShellBrowserImpl_ContextSensitiveHelp(IShellBrowser * iface, 00319 BOOL fEnterMode) 00320 { 00321 IShellBrowserImpl *This = impl_from_IShellBrowser(iface); 00322 00323 TRACE("(%p)\n", This); 00324 00325 /* Feature not implemented */ 00326 return E_NOTIMPL; 00327 } 00328 00329 /* 00330 * IShellBrowser 00331 */ 00332 00333 /************************************************************************** 00334 * IShellBrowserImpl_BrowseObject 00335 * 00336 * See Windows documentation on IShellBrowser::BrowseObject for more details 00337 * 00338 * This function will override user specified flags and will always 00339 * use SBSP_DEFBROWSER and SBSP_DEFMODE. 00340 */ 00341 static HRESULT WINAPI IShellBrowserImpl_BrowseObject(IShellBrowser *iface, 00342 LPCITEMIDLIST pidl, 00343 UINT wFlags) 00344 { 00345 HRESULT hRes; 00346 IShellFolder *psfTmp; 00347 IShellView *psvTmp; 00348 FileOpenDlgInfos *fodInfos; 00349 LPITEMIDLIST pidlTmp; 00350 HWND hwndView; 00351 HWND hDlgWnd; 00352 BOOL bViewHasFocus; 00353 RECT rectView; 00354 00355 IShellBrowserImpl *This = impl_from_IShellBrowser(iface); 00356 00357 TRACE("(%p)(pidl=%p,flags=0x%08x)\n", This, pidl, wFlags); 00358 COMDLG32_DumpSBSPFlags(wFlags); 00359 00360 fodInfos = GetPropA(This->hwndOwner,FileOpenDlgInfosStr); 00361 00362 /* Format the pidl according to its parameter's category */ 00363 if(wFlags & SBSP_RELATIVE) 00364 { 00365 00366 /* SBSP_RELATIVE A relative pidl (relative from the current folder) */ 00367 if(FAILED(hRes = IShellFolder_BindToObject(fodInfos->Shell.FOIShellFolder, 00368 pidl, NULL, &IID_IShellFolder, (LPVOID *)&psfTmp))) 00369 { 00370 ERR("bind to object failed\n"); 00371 return hRes; 00372 } 00373 /* create an absolute pidl */ 00374 pidlTmp = COMDLG32_PIDL_ILCombine(fodInfos->ShellInfos.pidlAbsCurrent, pidl); 00375 } 00376 else if(wFlags & SBSP_PARENT) 00377 { 00378 /* Browse the parent folder (ignores the pidl) */ 00379 pidlTmp = GetParentPidl(fodInfos->ShellInfos.pidlAbsCurrent); 00380 psfTmp = GetShellFolderFromPidl(pidlTmp); 00381 00382 } 00383 else /* SBSP_ABSOLUTE is 0x0000 */ 00384 { 00385 /* An absolute pidl (relative from the desktop) */ 00386 pidlTmp = COMDLG32_PIDL_ILClone(pidl); 00387 psfTmp = GetShellFolderFromPidl(pidlTmp); 00388 } 00389 00390 if(!psfTmp) 00391 { 00392 ERR("could not browse to folder\n"); 00393 return E_FAIL; 00394 } 00395 00396 /* If the pidl to browse to is equal to the actual pidl ... 00397 do nothing and pretend you did it*/ 00398 if(COMDLG32_PIDL_ILIsEqual(pidlTmp,fodInfos->ShellInfos.pidlAbsCurrent)) 00399 { 00400 IShellFolder_Release(psfTmp); 00401 COMDLG32_SHFree(pidlTmp); 00402 TRACE("keep current folder\n"); 00403 return NOERROR; 00404 } 00405 00406 /* Release the current DataObject */ 00407 if (fodInfos->Shell.FOIDataObject) 00408 { 00409 IDataObject_Release(fodInfos->Shell.FOIDataObject); 00410 fodInfos->Shell.FOIDataObject = NULL; 00411 } 00412 00413 /* Create the associated view */ 00414 TRACE("create view object\n"); 00415 if(FAILED(hRes = IShellFolder_CreateViewObject(psfTmp, fodInfos->ShellInfos.hwndOwner, 00416 &IID_IShellView, (LPVOID *)&psvTmp))) goto error; 00417 00418 /* Check if listview has focus */ 00419 bViewHasFocus = IsChild(fodInfos->ShellInfos.hwndView,GetFocus()); 00420 00421 /* Get the foldersettings from the old view */ 00422 if(fodInfos->Shell.FOIShellView) 00423 IShellView_GetCurrentInfo(fodInfos->Shell.FOIShellView, &fodInfos->ShellInfos.folderSettings); 00424 00425 /* Release the old fodInfos->Shell.FOIShellView and update its value. 00426 We have to update this early since ShellView_CreateViewWindow of native 00427 shell32 calls OnStateChange and needs the correct view here.*/ 00428 if(fodInfos->Shell.FOIShellView) 00429 { 00430 IShellView_DestroyViewWindow(fodInfos->Shell.FOIShellView); 00431 IShellView_Release(fodInfos->Shell.FOIShellView); 00432 } 00433 fodInfos->Shell.FOIShellView = psvTmp; 00434 00435 /* Release old FOIShellFolder and update its value */ 00436 if (fodInfos->Shell.FOIShellFolder) 00437 IShellFolder_Release(fodInfos->Shell.FOIShellFolder); 00438 fodInfos->Shell.FOIShellFolder = psfTmp; 00439 00440 /* Release old pidlAbsCurrent and update its value */ 00441 COMDLG32_SHFree(fodInfos->ShellInfos.pidlAbsCurrent); 00442 fodInfos->ShellInfos.pidlAbsCurrent = pidlTmp; 00443 00444 COMDLG32_UpdateCurrentDir(fodInfos); 00445 00446 GetWindowRect(GetDlgItem(This->hwndOwner, IDC_SHELLSTATIC), &rectView); 00447 MapWindowPoints(0, This->hwndOwner, (LPPOINT)&rectView, 2); 00448 00449 /* Create the window */ 00450 TRACE("create view window\n"); 00451 if(FAILED(hRes = IShellView_CreateViewWindow(psvTmp, NULL, 00452 &fodInfos->ShellInfos.folderSettings, fodInfos->Shell.FOIShellBrowser, 00453 &rectView, &hwndView))) goto error; 00454 00455 fodInfos->ShellInfos.hwndView = hwndView; 00456 00457 /* Set view window control id to 5002 */ 00458 SetWindowLongPtrW(hwndView, GWLP_ID, lst2); 00459 00460 /* Select the new folder in the Look In combo box of the Open file dialog */ 00461 FILEDLG95_LOOKIN_SelectItem(fodInfos->DlgInfos.hwndLookInCB,fodInfos->ShellInfos.pidlAbsCurrent); 00462 00463 /* changes the tab order of the ListView to reflect the window's File Dialog */ 00464 hDlgWnd = GetDlgItem(GetParent(hwndView), IDC_LOOKIN); 00465 SetWindowPos(hwndView, hDlgWnd, 0,0,0,0, SWP_NOMOVE | SWP_NOSIZE); 00466 00467 /* Since we destroyed the old view if it had focus set focus to the newly created view */ 00468 if (bViewHasFocus) 00469 SetFocus(fodInfos->ShellInfos.hwndView); 00470 00471 return hRes; 00472 error: 00473 ERR("Failed with error 0x%08x\n", hRes); 00474 return hRes; 00475 } 00476 00477 /************************************************************************** 00478 * IShellBrowserImpl_EnableModelessSB 00479 */ 00480 static HRESULT WINAPI IShellBrowserImpl_EnableModelessSB(IShellBrowser *iface, 00481 BOOL fEnable) 00482 00483 { 00484 IShellBrowserImpl *This = impl_from_IShellBrowser(iface); 00485 00486 TRACE("(%p)\n", This); 00487 00488 /* Feature not implemented */ 00489 return E_NOTIMPL; 00490 } 00491 00492 /************************************************************************** 00493 * IShellBrowserImpl_GetControlWindow 00494 */ 00495 static HRESULT WINAPI IShellBrowserImpl_GetControlWindow(IShellBrowser *iface, 00496 UINT id, 00497 HWND *lphwnd) 00498 00499 { 00500 IShellBrowserImpl *This = impl_from_IShellBrowser(iface); 00501 00502 TRACE("(%p)\n", This); 00503 00504 /* Feature not implemented */ 00505 return E_NOTIMPL; 00506 } 00507 00508 /************************************************************************** 00509 * IShellBrowserImpl_GetViewStateStream 00510 */ 00511 static HRESULT WINAPI IShellBrowserImpl_GetViewStateStream(IShellBrowser *iface, 00512 DWORD grfMode, 00513 LPSTREAM *ppStrm) 00514 00515 { 00516 IShellBrowserImpl *This = impl_from_IShellBrowser(iface); 00517 00518 FIXME("(%p 0x%08x %p)\n", This, grfMode, ppStrm); 00519 00520 /* Feature not implemented */ 00521 return E_NOTIMPL; 00522 } 00523 00524 /************************************************************************** 00525 * IShellBrowserImpl_InsertMenusSB 00526 */ 00527 static HRESULT WINAPI IShellBrowserImpl_InsertMenusSB(IShellBrowser *iface, 00528 HMENU hmenuShared, 00529 LPOLEMENUGROUPWIDTHS lpMenuWidths) 00530 00531 { 00532 IShellBrowserImpl *This = impl_from_IShellBrowser(iface); 00533 00534 TRACE("(%p)\n", This); 00535 00536 /* Feature not implemented */ 00537 return E_NOTIMPL; 00538 } 00539 00540 /************************************************************************** 00541 * IShellBrowserImpl_OnViewWindowActive 00542 */ 00543 static HRESULT WINAPI IShellBrowserImpl_OnViewWindowActive(IShellBrowser *iface, 00544 IShellView *ppshv) 00545 00546 { 00547 IShellBrowserImpl *This = impl_from_IShellBrowser(iface); 00548 00549 TRACE("(%p)\n", This); 00550 00551 /* Feature not implemented */ 00552 return E_NOTIMPL; 00553 } 00554 00555 /************************************************************************** 00556 * IShellBrowserImpl_QueryActiveShellView 00557 */ 00558 static HRESULT WINAPI IShellBrowserImpl_QueryActiveShellView(IShellBrowser *iface, 00559 IShellView **ppshv) 00560 00561 { 00562 IShellBrowserImpl *This = impl_from_IShellBrowser(iface); 00563 00564 FileOpenDlgInfos *fodInfos; 00565 00566 TRACE("(%p)\n", This); 00567 00568 fodInfos = GetPropA(This->hwndOwner,FileOpenDlgInfosStr); 00569 00570 if(!(*ppshv = fodInfos->Shell.FOIShellView)) 00571 { 00572 return E_FAIL; 00573 } 00574 IShellView_AddRef(fodInfos->Shell.FOIShellView); 00575 return NOERROR; 00576 } 00577 00578 /************************************************************************** 00579 * IShellBrowserImpl_RemoveMenusSB 00580 */ 00581 static HRESULT WINAPI IShellBrowserImpl_RemoveMenusSB(IShellBrowser *iface, 00582 HMENU hmenuShared) 00583 00584 { 00585 IShellBrowserImpl *This = impl_from_IShellBrowser(iface); 00586 00587 TRACE("(%p)\n", This); 00588 00589 /* Feature not implemented */ 00590 return E_NOTIMPL; 00591 } 00592 00593 /************************************************************************** 00594 * IShellBrowserImpl_SendControlMsg 00595 */ 00596 static HRESULT WINAPI IShellBrowserImpl_SendControlMsg(IShellBrowser *iface, 00597 UINT id, 00598 UINT uMsg, 00599 WPARAM wParam, 00600 LPARAM lParam, 00601 LRESULT *pret) 00602 00603 { 00604 IShellBrowserImpl *This = impl_from_IShellBrowser(iface); 00605 LRESULT lres; 00606 00607 TRACE("(%p)->(0x%08x 0x%08x 0x%08lx 0x%08lx %p)\n", This, id, uMsg, wParam, lParam, pret); 00608 00609 switch (id) 00610 { 00611 case FCW_TOOLBAR: 00612 lres = SendDlgItemMessageA( This->hwndOwner, IDC_TOOLBAR, uMsg, wParam, lParam); 00613 break; 00614 default: 00615 FIXME("ctrl id: %x\n", id); 00616 return E_NOTIMPL; 00617 } 00618 if (pret) *pret = lres; 00619 return S_OK; 00620 } 00621 00622 /************************************************************************** 00623 * IShellBrowserImpl_SetMenuSB 00624 */ 00625 static HRESULT WINAPI IShellBrowserImpl_SetMenuSB(IShellBrowser *iface, 00626 HMENU hmenuShared, 00627 HOLEMENU holemenuReserved, 00628 HWND hwndActiveObject) 00629 00630 { 00631 IShellBrowserImpl *This = impl_from_IShellBrowser(iface); 00632 00633 TRACE("(%p)\n", This); 00634 00635 /* Feature not implemented */ 00636 return E_NOTIMPL; 00637 } 00638 00639 /************************************************************************** 00640 * IShellBrowserImpl_SetStatusTextSB 00641 */ 00642 static HRESULT WINAPI IShellBrowserImpl_SetStatusTextSB(IShellBrowser *iface, 00643 LPCOLESTR lpszStatusText) 00644 00645 { 00646 IShellBrowserImpl *This = impl_from_IShellBrowser(iface); 00647 00648 TRACE("(%p)\n", This); 00649 00650 /* Feature not implemented */ 00651 return E_NOTIMPL; 00652 } 00653 00654 /************************************************************************** 00655 * IShellBrowserImpl_SetToolbarItems 00656 */ 00657 static HRESULT WINAPI IShellBrowserImpl_SetToolbarItems(IShellBrowser *iface, 00658 LPTBBUTTON lpButtons, 00659 UINT nButtons, 00660 UINT uFlags) 00661 00662 { 00663 IShellBrowserImpl *This = impl_from_IShellBrowser(iface); 00664 00665 TRACE("(%p)\n", This); 00666 00667 /* Feature not implemented */ 00668 return E_NOTIMPL; 00669 } 00670 00671 /************************************************************************** 00672 * IShellBrowserImpl_TranslateAcceleratorSB 00673 */ 00674 static HRESULT WINAPI IShellBrowserImpl_TranslateAcceleratorSB(IShellBrowser *iface, 00675 LPMSG lpmsg, 00676 WORD wID) 00677 00678 { 00679 IShellBrowserImpl *This = impl_from_IShellBrowser(iface); 00680 00681 TRACE("(%p)\n", This); 00682 00683 /* Feature not implemented */ 00684 return E_NOTIMPL; 00685 } 00686 00687 static const IShellBrowserVtbl IShellBrowserImpl_Vtbl = 00688 { 00689 /* IUnknown */ 00690 IShellBrowserImpl_QueryInterface, 00691 IShellBrowserImpl_AddRef, 00692 IShellBrowserImpl_Release, 00693 /* IOleWindow */ 00694 IShellBrowserImpl_GetWindow, 00695 IShellBrowserImpl_ContextSensitiveHelp, 00696 /* IShellBrowser */ 00697 IShellBrowserImpl_InsertMenusSB, 00698 IShellBrowserImpl_SetMenuSB, 00699 IShellBrowserImpl_RemoveMenusSB, 00700 IShellBrowserImpl_SetStatusTextSB, 00701 IShellBrowserImpl_EnableModelessSB, 00702 IShellBrowserImpl_TranslateAcceleratorSB, 00703 IShellBrowserImpl_BrowseObject, 00704 IShellBrowserImpl_GetViewStateStream, 00705 IShellBrowserImpl_GetControlWindow, 00706 IShellBrowserImpl_SendControlMsg, 00707 IShellBrowserImpl_QueryActiveShellView, 00708 IShellBrowserImpl_OnViewWindowActive, 00709 IShellBrowserImpl_SetToolbarItems 00710 }; 00711 00712 00713 00714 /* 00715 * ICommDlgBrowser 00716 */ 00717 00718 /*************************************************************************** 00719 * IShellBrowserImpl_ICommDlgBrowser_QueryInterface 00720 */ 00721 static HRESULT WINAPI IShellBrowserImpl_ICommDlgBrowser_QueryInterface( 00722 ICommDlgBrowser *iface, 00723 REFIID riid, 00724 LPVOID *ppvObj) 00725 { 00726 IShellBrowserImpl *This = impl_from_ICommDlgBrowser(iface); 00727 00728 TRACE("(%p)\n", This); 00729 00730 return IShellBrowserImpl_QueryInterface(&This->IShellBrowser_iface,riid,ppvObj); 00731 } 00732 00733 /************************************************************************** 00734 * IShellBrowserImpl_ICommDlgBrowser_AddRef 00735 */ 00736 static ULONG WINAPI IShellBrowserImpl_ICommDlgBrowser_AddRef(ICommDlgBrowser * iface) 00737 { 00738 IShellBrowserImpl *This = impl_from_ICommDlgBrowser(iface); 00739 00740 TRACE("(%p)\n", This); 00741 00742 return IShellBrowserImpl_AddRef(&This->IShellBrowser_iface); 00743 } 00744 00745 /************************************************************************** 00746 * IShellBrowserImpl_ICommDlgBrowser_Release 00747 */ 00748 static ULONG WINAPI IShellBrowserImpl_ICommDlgBrowser_Release(ICommDlgBrowser * iface) 00749 { 00750 IShellBrowserImpl *This = impl_from_ICommDlgBrowser(iface); 00751 00752 TRACE("(%p)\n", This); 00753 00754 return IShellBrowserImpl_Release(&This->IShellBrowser_iface); 00755 } 00756 00757 /************************************************************************** 00758 * IShellBrowserImpl_ICommDlgBrowser_OnDefaultCommand 00759 * 00760 * Called when a user double-clicks in the view or presses the ENTER key 00761 */ 00762 static HRESULT WINAPI IShellBrowserImpl_ICommDlgBrowser_OnDefaultCommand(ICommDlgBrowser *iface, 00763 IShellView *ppshv) 00764 { 00765 LPITEMIDLIST pidl; 00766 FileOpenDlgInfos *fodInfos; 00767 00768 IShellBrowserImpl *This = impl_from_ICommDlgBrowser(iface); 00769 00770 TRACE("(%p)\n", This); 00771 00772 fodInfos = GetPropA(This->hwndOwner,FileOpenDlgInfosStr); 00773 00774 /* If the selected object is not a folder, send an IDOK command to parent window */ 00775 if((pidl = GetPidlFromDataObject(fodInfos->Shell.FOIDataObject, 1))) 00776 { 00777 HRESULT hRes; 00778 00779 ULONG ulAttr = SFGAO_FOLDER | SFGAO_HASSUBFOLDER; 00780 IShellFolder_GetAttributesOf(fodInfos->Shell.FOIShellFolder, 1, (LPCITEMIDLIST *)&pidl, &ulAttr); 00781 if (ulAttr & (SFGAO_FOLDER | SFGAO_HASSUBFOLDER) ) 00782 { 00783 hRes = IShellBrowser_BrowseObject(&This->IShellBrowser_iface,pidl,SBSP_RELATIVE); 00784 if(fodInfos->ofnInfos->Flags & OFN_EXPLORER) 00785 SendCustomDlgNotificationMessage(This->hwndOwner, CDN_FOLDERCHANGE); 00786 } 00787 else 00788 { 00789 /* Tell the dialog that the user selected a file */ 00790 PostMessageA(This->hwndOwner, WM_COMMAND, IDOK, 0L); 00791 hRes = S_OK; 00792 } 00793 00794 /* Free memory used by pidl */ 00795 COMDLG32_SHFree(pidl); 00796 00797 return hRes; 00798 } 00799 00800 return E_FAIL; 00801 } 00802 00803 /************************************************************************** 00804 * IShellBrowserImpl_OnSelChange 00805 */ 00806 static HRESULT IShellBrowserImpl_OnSelChange(IShellBrowserImpl *This, const IShellView *ppshv) 00807 { 00808 FileOpenDlgInfos *fodInfos; 00809 00810 fodInfos = GetPropA(This->hwndOwner,FileOpenDlgInfosStr); 00811 TRACE("(%p do=%p view=%p)\n", This, fodInfos->Shell.FOIDataObject, fodInfos->Shell.FOIShellView); 00812 00813 /* release old selections */ 00814 if (fodInfos->Shell.FOIDataObject) 00815 IDataObject_Release(fodInfos->Shell.FOIDataObject); 00816 00817 /* get a new DataObject from the ShellView */ 00818 if(FAILED(IShellView_GetItemObject(fodInfos->Shell.FOIShellView, SVGIO_SELECTION, 00819 &IID_IDataObject, (void**)&fodInfos->Shell.FOIDataObject))) 00820 return E_FAIL; 00821 00822 FILEDLG95_FILENAME_FillFromSelection(This->hwndOwner); 00823 00824 if(fodInfos->ofnInfos->Flags & OFN_EXPLORER) 00825 SendCustomDlgNotificationMessage(This->hwndOwner, CDN_SELCHANGE); 00826 return S_OK; 00827 } 00828 00829 /************************************************************************** 00830 * IShellBrowserImpl_ICommDlgBrowser_OnStateChange 00831 */ 00832 static HRESULT WINAPI IShellBrowserImpl_ICommDlgBrowser_OnStateChange(ICommDlgBrowser *iface, 00833 IShellView *ppshv, 00834 ULONG uChange) 00835 { 00836 00837 IShellBrowserImpl *This = impl_from_ICommDlgBrowser(iface); 00838 00839 TRACE("(%p shv=%p)\n", This, ppshv); 00840 00841 switch (uChange) 00842 { 00843 case CDBOSC_SETFOCUS: 00844 /* FIXME: Reset the default button. 00845 This should be taken care of by defdlg. If control 00846 other than button receives focus the default button 00847 should be restored. */ 00848 SendMessageA(This->hwndOwner, DM_SETDEFID, IDOK, 0); 00849 00850 break; 00851 case CDBOSC_KILLFOCUS: 00852 { 00853 FileOpenDlgInfos *fodInfos = GetPropA(This->hwndOwner,FileOpenDlgInfosStr); 00854 if(fodInfos->DlgInfos.dwDlgProp & FODPROP_SAVEDLG) 00855 { 00856 WCHAR szSave[16]; 00857 LoadStringW(COMDLG32_hInstance, IDS_SAVE_BUTTON, szSave, sizeof(szSave)/sizeof(WCHAR)); 00858 SetDlgItemTextW(fodInfos->ShellInfos.hwndOwner, IDOK, szSave); 00859 } 00860 } 00861 break; 00862 case CDBOSC_SELCHANGE: 00863 return IShellBrowserImpl_OnSelChange(This, ppshv); 00864 case CDBOSC_RENAME: 00865 /* nothing to do */ 00866 break; 00867 } 00868 00869 return NOERROR; 00870 } 00871 00872 /* send_includeitem_notification 00873 * 00874 * Sends a CDN_INCLUDEITEM notification for "pidl" to hwndParentDlg 00875 */ 00876 static LRESULT send_includeitem_notification(HWND hwndParentDlg, LPCITEMIDLIST pidl) 00877 { 00878 LRESULT hook_result = 0; 00879 FileOpenDlgInfos *fodInfos = GetPropA(hwndParentDlg, FileOpenDlgInfosStr); 00880 00881 if(!fodInfos) return 0; 00882 00883 if(fodInfos->DlgInfos.hwndCustomDlg) 00884 { 00885 TRACE("call notify CDN_INCLUDEITEM for pidl=%p\n", pidl); 00886 if(fodInfos->unicode) 00887 { 00888 OFNOTIFYEXW ofnNotify; 00889 ofnNotify.psf = fodInfos->Shell.FOIShellFolder; 00890 ofnNotify.pidl = (LPITEMIDLIST)pidl; 00891 ofnNotify.hdr.hwndFrom = hwndParentDlg; 00892 ofnNotify.hdr.idFrom = 0; 00893 ofnNotify.hdr.code = CDN_INCLUDEITEM; 00894 ofnNotify.lpOFN = fodInfos->ofnInfos; 00895 hook_result = SendMessageW(fodInfos->DlgInfos.hwndCustomDlg, WM_NOTIFY, 0, (LPARAM)&ofnNotify); 00896 } 00897 else 00898 { 00899 OFNOTIFYEXA ofnNotify; 00900 ofnNotify.psf = fodInfos->Shell.FOIShellFolder; 00901 ofnNotify.pidl = (LPITEMIDLIST)pidl; 00902 ofnNotify.hdr.hwndFrom = hwndParentDlg; 00903 ofnNotify.hdr.idFrom = 0; 00904 ofnNotify.hdr.code = CDN_INCLUDEITEM; 00905 ofnNotify.lpOFN = (LPOPENFILENAMEA)fodInfos->ofnInfos; 00906 hook_result = SendMessageA(fodInfos->DlgInfos.hwndCustomDlg, WM_NOTIFY, 0, (LPARAM)&ofnNotify); 00907 } 00908 } 00909 TRACE("Retval: 0x%08lx\n", hook_result); 00910 return hook_result; 00911 } 00912 00913 /************************************************************************** 00914 * IShellBrowserImpl_ICommDlgBrowser_IncludeObject 00915 */ 00916 static HRESULT WINAPI IShellBrowserImpl_ICommDlgBrowser_IncludeObject(ICommDlgBrowser *iface, 00917 IShellView * ppshv, 00918 LPCITEMIDLIST pidl) 00919 { 00920 FileOpenDlgInfos *fodInfos; 00921 ULONG ulAttr; 00922 STRRET str; 00923 WCHAR szPathW[MAX_PATH]; 00924 00925 IShellBrowserImpl *This = impl_from_ICommDlgBrowser(iface); 00926 00927 TRACE("(%p)\n", This); 00928 00929 fodInfos = GetPropA(This->hwndOwner,FileOpenDlgInfosStr); 00930 00931 ulAttr = SFGAO_HIDDEN | SFGAO_FOLDER | SFGAO_FILESYSTEM | SFGAO_FILESYSANCESTOR | SFGAO_LINK; 00932 IShellFolder_GetAttributesOf(fodInfos->Shell.FOIShellFolder, 1, &pidl, &ulAttr); 00933 00934 if( (ulAttr & SFGAO_HIDDEN) || /* hidden */ 00935 !(ulAttr & (SFGAO_FILESYSTEM | SFGAO_FILESYSANCESTOR))) /* special folder */ 00936 return S_FALSE; 00937 00938 /* always include directories and links */ 00939 if(ulAttr & (SFGAO_FOLDER | SFGAO_LINK)) 00940 return S_OK; 00941 00942 /* if the application takes care of including the item we are done */ 00943 if(fodInfos->ofnInfos->Flags & OFN_ENABLEINCLUDENOTIFY && 00944 send_includeitem_notification(This->hwndOwner, pidl)) 00945 return S_OK; 00946 00947 /* Check if there is a mask to apply if not */ 00948 if(!fodInfos->ShellInfos.lpstrCurrentFilter || !lstrlenW(fodInfos->ShellInfos.lpstrCurrentFilter)) 00949 return S_OK; 00950 00951 if (SUCCEEDED(IShellFolder_GetDisplayNameOf(fodInfos->Shell.FOIShellFolder, pidl, SHGDN_INFOLDER | SHGDN_FORPARSING, &str))) 00952 { 00953 if (COMDLG32_StrRetToStrNW(szPathW, MAX_PATH, &str, pidl)) 00954 { 00955 if (PathMatchSpecW(szPathW, fodInfos->ShellInfos.lpstrCurrentFilter)) 00956 return S_OK; 00957 } 00958 } 00959 return S_FALSE; 00960 00961 } 00962 00963 static const ICommDlgBrowserVtbl IShellBrowserImpl_ICommDlgBrowser_Vtbl = 00964 { 00965 /* IUnknown */ 00966 IShellBrowserImpl_ICommDlgBrowser_QueryInterface, 00967 IShellBrowserImpl_ICommDlgBrowser_AddRef, 00968 IShellBrowserImpl_ICommDlgBrowser_Release, 00969 /* ICommDlgBrowser */ 00970 IShellBrowserImpl_ICommDlgBrowser_OnDefaultCommand, 00971 IShellBrowserImpl_ICommDlgBrowser_OnStateChange, 00972 IShellBrowserImpl_ICommDlgBrowser_IncludeObject 00973 }; 00974 00975 00976 00977 00978 /* 00979 * IServiceProvider 00980 */ 00981 00982 /*************************************************************************** 00983 * IShellBrowserImpl_IServiceProvider_QueryInterface 00984 */ 00985 static HRESULT WINAPI IShellBrowserImpl_IServiceProvider_QueryInterface( 00986 IServiceProvider *iface, 00987 REFIID riid, 00988 LPVOID *ppvObj) 00989 { 00990 IShellBrowserImpl *This = impl_from_IServiceProvider(iface); 00991 00992 FIXME("(%p)\n", This); 00993 00994 return IShellBrowserImpl_QueryInterface(&This->IShellBrowser_iface,riid,ppvObj); 00995 } 00996 00997 /************************************************************************** 00998 * IShellBrowserImpl_IServiceProvider_AddRef 00999 */ 01000 static ULONG WINAPI IShellBrowserImpl_IServiceProvider_AddRef(IServiceProvider * iface) 01001 { 01002 IShellBrowserImpl *This = impl_from_IServiceProvider(iface); 01003 01004 FIXME("(%p)\n", This); 01005 01006 return IShellBrowserImpl_AddRef(&This->IShellBrowser_iface); 01007 } 01008 01009 /************************************************************************** 01010 * IShellBrowserImpl_IServiceProvider_Release 01011 */ 01012 static ULONG WINAPI IShellBrowserImpl_IServiceProvider_Release(IServiceProvider * iface) 01013 { 01014 IShellBrowserImpl *This = impl_from_IServiceProvider(iface); 01015 01016 FIXME("(%p)\n", This); 01017 01018 return IShellBrowserImpl_Release(&This->IShellBrowser_iface); 01019 } 01020 01021 /************************************************************************** 01022 * IShellBrowserImpl_IServiceProvider_Release 01023 * 01024 * NOTES 01025 * the w2k shellview asks for (guidService = SID_STopLevelBrowser, 01026 * riid = IShellBrowser) to call SendControlMsg (). 01027 * 01028 * FIXME 01029 * this is a hack! 01030 */ 01031 01032 static HRESULT WINAPI IShellBrowserImpl_IServiceProvider_QueryService( 01033 IServiceProvider * iface, 01034 REFGUID guidService, 01035 REFIID riid, 01036 void** ppv) 01037 { 01038 IShellBrowserImpl *This = impl_from_IServiceProvider(iface); 01039 01040 FIXME("(%p)\n\t%s\n\t%s\n", This,debugstr_guid(guidService), debugstr_guid(riid) ); 01041 01042 *ppv = NULL; 01043 if(guidService && IsEqualIID(guidService, &SID_STopLevelBrowser)) 01044 return IShellBrowserImpl_QueryInterface(&This->IShellBrowser_iface,riid,ppv); 01045 01046 FIXME("(%p) unknown interface requested\n", This); 01047 return E_NOINTERFACE; 01048 01049 } 01050 01051 static const IServiceProviderVtbl IShellBrowserImpl_IServiceProvider_Vtbl = 01052 { 01053 /* IUnknown */ 01054 IShellBrowserImpl_IServiceProvider_QueryInterface, 01055 IShellBrowserImpl_IServiceProvider_AddRef, 01056 IShellBrowserImpl_IServiceProvider_Release, 01057 /* IServiceProvider */ 01058 IShellBrowserImpl_IServiceProvider_QueryService 01059 }; Generated on Sun May 27 2012 04:23:07 for ReactOS by
1.7.6.1
|