How to find targets in shortcuts

Source: Internet
Author: User

I recently wrote a development auxiliary tool. In this process, I want to create a function similar to the file shortcut to find the target. Check msdn98 first. Don't laugh. I have been using it all the time and there is no corresponding API, later. the msdn in net 2003 finds the API that can implement this function. The shopenfolderandselectitems () function is prototype as follows:
(For specific usage, refer to msdn) "opens a Microsoft Windows Explorer window with specified items in a participant folder selected ."

 
Hresult shopenfolderandselectitems (lpcitemidlistPidlfolder, UintCIDL, Lpcitemidlist *Apidl, DWORDDwflags);

However, it requires Windows XP and Windows XP. How can it be implemented in Win2000 or Win98? So I searched the internet and finally found one after several twists and turns.ArticleBut it is only obtained by means of tool disassembly of Windows API functions.CodeIt may be possible to implement a dialog box with the same shortcut (I have not tried it), but its code is very poorly readable. I can only refer to the general process. He mentioned a very important point, it is to use an undisclosed API function shgetidispatchforfolder, which can help me open folders. The following is a key part:
The search Target function is divided into two steps: first open or find the folder where the target file is located, and then select the corresponding project (that is, the file) in the opened folder ). Before proceeding to this step, let's take a look at the following two structures:

Typedef struct _ shitemid {ushort CB; byte Abid [1];} shitemid, * lpshitemid; typedef const shitemid * lpcshitemid; typedef struct _ itemidlist {shitemid mkid;} itemidlist, * region; typedef const itemidlist * lpcitemidlist;

The data of these two structures is saved in the project definition list (only literal translation). The folders and files represented by this structure are not normal, it also contains some special folders and files (such as directories and my computer). The shgetidispatchforfolder function uses it as a parameter to open some special folders. The shgetidispatchforfolder function is prototype:

 
Hresult (winapi * gpfshgetidispatchforfolder) (itemidlist * pidl, iwebbrowserapp ** ppiwebbrowserapp );

The itemidlist provided by the shortcut usually contains the file name. If you call the above function directly, it will open the target file instead of the folder. The following Code distinguishes files and folders:

 
Pidlfile = pidl; // find the offset of the object name in the target file while (cb = pidlfile-> mkid. CB) {pidl2 = pidlfile; pidlfile = (itemidlist *) (byte *) pidlfile + CB);} cb = pidl2-> mkid. CB; pidl2-> mkid. CB = 0;

The following is the code for opening folders and selecting files.

/// Open the target file folder if (succeeded (getshellfolderviewdual (pidl, & pishellfolderviewdual) {pidl2-> mkid. CB = CB; // 0 deselect the item. // 1 select the item. // 3 put the item in edit mode. // 4 deselect all but the specified item. // 8 ensure the item is displayed in the view. // 0x10 give the item the focus. colevariant bszfile (pidl2); If (pishellfolderviewdual! = NULL) {// select the appropriate option pishellfolderviewdual-> selectitem (bszfile, 0x1d); pishellfolderviewdual-> release ();} return true ;}

Source codeContains a demo. The following is a complete function. You can directly call the findtarget (cstring Str) parameter as the file name. If it is a shortcut, it will automatically point to its target. If you have initialized COM in the code, delete the coinitialize (null); and couninitialize (); statement.

Hresult upload (itemidlist * pidl, ishellfolderviewdual ** handle) {iwebbrowserapp * piwebbrowserapp; idispatch * pdoc; hwnd; hresult hr; hinstance ghshdocvw; hresult (winapi * handle) (itemidlist * pidl, iwebbrowserapp ** ppiwebbrowserapp); * ppishellfolderviewdual = NULL; ghshdocvw = loadlibrary (_ T ("shdocvw. DLL "); If (ghshdocvw = NULL) return false; piwebbrows Erapp = NULL; Result = (hresult (winapi *) (itemidlist *, iwebbrowserapp **) getprocaddress (ghshdocvw, "shgetidispatchforfolder"); If (condition = NULL) return false; /// call the undisclosed API function shgetidispatchforfolderif (succeeded (partition (pidl, & piwebbrowserapp) {If (succeeded (piwebbrowserapp-> get_hwnd (long *) & hwnd) {setforegroundwindow (hwnd); showwindow (hwn D, sw_shownormal);} If (succeeded (hR = piwebbrowserapp-> get_document (& pdoc) {pdoc-> QueryInterface (response, (void **) ppishellfolderviewdual ); pdoc-> release ();} piwebbrowserapp-> release ();} freelibrary (ghshdocvw); Return true;} bool handler (itemidlist * pidlfolder) {itemidlist * pidl, * pidl2; itemidlist * pidlfile; ushort CB; ishellfolderviewdual * pishellfolderviewdual; hres Ult (winapi * handle) (lpcitemidlist * pidlfolder, uint CIDL, lpcitemidlist * apidl, DWORD dwflags); hinstance ghshell32; // shopenfolderandselectitems () is supported only for WINXP and later systems () API // How do other systems implement this function? You can only use other methods to process it. // first, use XP to track the shopenfolderandselectitems () API and see how it works, use the same method to implement this function of // other systems using the tool vc6. NET 2003 msdn ollydbg v1.10 Chinese Version ghshell32 = loadlibrary (_ T ("shell32.dll"); If (ghshell32 = NULL) return false; gpfshopenfolderandselectitems = (hresult (winapi *) (lpcitemidlist *, uint, lpcitemidlist *, DWORD) getprocaddress (ghshell32, "shopenfolderandselectitems"); If (gpfshopenfolderandselectitems! = NULL) {// obtain the API address of the shopenfolderandselectitems () function if (succeeded (round (lpcitemidlist *) pidlfolder, 0, (lpcitemidlist *) null, 0 ))) {// call the system function freelibrary (ghshell32); Return true;} freelibrary (ghshell32); Return false;} freelibrary (ghshell32 ); /// processing when the operating system does not support the shopenfolderandselectitems () function API. // You can manually write the code pidl = pidlfolder; pidlfile = pidl; /// find the offset of the object name in the target file while (cb = pidlf Ile-> mkid. CB) {pidl2 = pidlfile; pidlfile = (itemidlist *) (byte *) pidlfile + CB);} cb = pidl2-> mkid. CB; pidl2-> mkid. CB = 0; // open the target file folder if (succeeded (getshellfolderviewdual (pidl, & pishellfolderviewdual) {pidl2-> mkid. CB = CB; // 0 deselect the item. // 1 select the item. // 3 put the item in edit mode. // 4 deselect all but the specified item. // 8 ensure the item is displayed in the view. // 0x10 Give the item the focus. colevariant bszfile (pidl2); If (pishellfolderviewdual! = NULL) {// select the appropriate option pishellfolderviewdual-> selectitem (bszfile, 0x1d); pishellfolderviewdual-> release ();} return true;} return false ;} void findtarget (cstring Str) {hresult hres; ishelllink * PSL; itemidlist * pidl; ipersistfile * PPF; coinitialize (null); // get a pointer to the ishelllink interface. hres = cocreateinstance (clsid_shelllink, null, clsctx_inproc_server, iid_ishelllink, (lpvoid *) & PSL); If (succeeded (hres )) {// set the target file PSL-> setpath (STR); // obtain the itemidlistpsl-> getidlist (& pidl) of the target file; // get a pointer to the ipersistfile interface. hres = PSL-> QueryInterface (iid_ipersistfile, (void **) & PPF); If (succeeded (hres) {wchar wsz [max_path]; # ifdef _ unicodewcscpy (wsz, str); # else // ensure that the string is Unicode. multibytetowidechar (cp_acp, 0, STR,-1, wsz, max_path); # endif // load the shortcut. hres = PPF-> load (wsz, stgm_read); If (succeeded (hres) {// obtain the shortcut itemidlistpsl-> getidlist (& pidl );} m ppf-> release ();} // open the folder and select the project xzshopenfolderandselectitems (pidl); PSL-> release ();} couninitialize ();}

Contact Us

The content source of this page is from Internet, which doesn't represent Alibaba Cloud's opinion; products and services mentioned on that page don't have any relationship with Alibaba Cloud. If the content of the page makes you feel confusing, please write us an email, we will handle the problem within 5 days after receiving your email.

If you find any instances of plagiarism from the community, please send an email to: info-contact@alibabacloud.com and provide relevant evidence. A staff member will contact you within 5 working days.

A Free Trial That Lets You Build Big!

Start building with 50+ products and up to 12 months usage for Elastic Compute Service

  • Sales Support

    1 on 1 presale consultation

  • After-Sales Support

    24/7 Technical Support 6 Free Tickets per Quarter Faster Response

  • Alibaba Cloud offers highly flexible support services tailored to meet your exact needs.