微信公众号搜"智元新知"关注
微信扫一扫可直接关注哦!

如何读取/写入Windows 7库位置?

介绍

在Windows 7中,您有一些文件图片和音乐等特殊文件夹,称为库。

如果你不知道他们,基本上每个库文件夹可以包含位置(path),这基本上是每个库的快捷方式。

一些例子:

如何检查是否有认打印机(Windows)?

Windows视觉主题:部件和国家图库?

CreateProcess钩子添加CommandLine

RegisterDragDrop返回S_OK,但不调用dragenter方法

德尔菲计时器比毫秒更精确

Documents (Library)

E:个人文件(Location)

F: Backups Documents (Location)

Music (Library)

E: Media Music Albums (Location)

E: Media Music Singles (Location)

Pictures (Library)

E:媒体照片(Location)

当您从Windows资源pipe理器或“开始”菜单中单击任何这些库文件夹时,Windows资源pipe理器将显示该库中定义的位置。

任务

我需要做的是读取每个库types的位置,并能够用我自己的位置写回(更新)库。 我发现这些库存储在用户的AppData文件夹中,如下所示:

C:UseRSSOMEUSERAppDaTaroamingMicrosoftwindowsLibraries

这些库是这种文件types: 库(.library-ms) – 如果你右键点击一个,select属性,库选项卡,你可以看到与该库相关联的库位置。

我没有看到解压缩这些方法,并把它们放在一个TStringList中,以便在Delphi中进行编辑。 我想知道,如果这些库位置实际存储在Windowsregistry,所以从谷歌的一些研究,我发现这些path:

HKEY_CURRENT_USER Software Microsoft Windows CurrentVersion Explorer Shell文件

HKEY_CURRENT_USER Software Microsoft Windows CurrentVersion Explorer User Shell Folders

但是,我再次看不到实际的库位置列表。

那么,如何在Delphi中读取库文件中的位置列表,将它们添加到ListBox或TStringList,编辑条目,然后写回更改? 刚刚能够提取库位置path将是一个开始。

我只是有一种感觉,这将是一个简单的答案,我似乎无法find的问题之一!

在Windows 8中,具有pipe理员权限的Delphi外部exe被最小化

我可以打开/closures个别键盘上的Capslock指示灯吗?

RTTI元数据存储在可执行文件中的位置在哪里?

如何为仅用于远程COM对象的TLB创build清单文件

我怎样才能让任务pipe理器杀死我的程序?

使用SHLoadLibraryFrom...()函数SHLoadLibraryFromKNownFolder()如SHLoadLibraryFromKNownFolder()来获取IShellLibrary接口,然后可以使用其方法来枚举和操作库,例如IShellLibrary::GetFolders() , IShellLibrary::AddFolder() , IShellLibrary::RemoveFolder()等

更新:例如:

uses ...,ActiveX,KNownFolders,ShlObj; // The SHLoadLibraryFrom...() functions are implemented inline in the Win32 SDK // shobjidl.h header file,so you have to implement them manually in your // code if you you are not using a version of Delphi that already implements // them in the RTL's ShlObj.pas unit for you... // SHLoadLibraryFromKNownFolder() is defined wrong in ShlObj.pas!!! See QC #109306 function My_SHLoadLibraryFromKNownFolder(const kfidLibrary: TGUID; grfMode: DWORD; riid: TIID; out ppv): HRESULT; var plib: IShellLibrary; begin Result := CoCreateInstance(CLSID_ShellLibrary,nil,CLSCTX_INPROC_SERVER,IShellLibrary,plib); if SUCCEEDED(Result) then begin Result := plib.LoadLibraryFromKNownFolder(kfidLibrary,grfMode); if SUCCEEDED(Result) then Result := plib.QueryInterface(riid,ppv); end; end; function GetLibraryFileSystemFolders(FolderID: TGUID; Folders: TStrings): Boolean; var SL: IShellLibrary; Arr: IShellItemArray; Enum: IEnumShellItems; Item: IShellItem; Path: LPWSTR; begin Result := False; if Failed(My_SHLoadLibraryFromKNownFolder(FolderID,STGM_READ,SL)) then Exit; if Failed(SL.GetFolders(LFF_FORCEFILESYstem,IShellItemArray,Arr)) then Exit; if Failed(Arr.EnumItems(Enum)) then Exit; while Enum.Next(1,Item,nil) = S_OK then begin if Failed(Item.GetdisplayName(SIGDN_FILESYSPATH,Path)) then Exit; try Folders.Add(Path); finally CoTaskMemFree(Path); end; Item := nil; end; Result := True; end;

var Folders: TStringList; begin Folders := TStringList.Create; try if GetLibraryFileSystemFolders(FOLDERID_DocumentsLibrary,Folders) then begin //... end; finally Folders.Free; end; end;

更新 : SHLoadLibraryFromKNownFolder()仅适用于定义了KNowNFOLDERID值的Microsoft定义的库。 如果要访问自定义库,则必须使用稍微修改方法获取IShellLibrary接口,例如:

// SHLoadLibraryFromItem() is defined wrong in ShlObj.pas!!! See QC #109306 function My_SHLoadLibraryFromItem(const psiLibrary: IShellItem; grfMode: DWORD; const riid: TIID; out ppv): HResult; var plib: IShellLibrary; begin Result := CoCreateInstance(CLSID_ShellLibrary,IID_IShellLibrary,plib); if Succeeded(Result) then begin Result := plib.LoadLibraryFromItem(psiLibrary,grfMode); if Succeeded(Result) then Result := plib.QueryInterface(riid,ppv); end; end; function GetShellLibraryforLibrary(const LibraryName: String; grfMode: DWORD; var ppv: IShellLibrary): Boolean; var SL: IShellLibrary; Enum: IEnumShellItems; Item: IShellItem; displayName: LPWSTR; hr: HRESULT; begin Result := False; ppv := nil; if Failed(SHGetKNownFolderItem(FOLDERID_Libraries,IShellItem,PPointer(@Item)^) then Exit; hr := Item.BindToHandler(nil,BHID_EnumItems,IEnumShellItems,Enum); if Failed(hr) then Exit; Item := nil; while Enum.Next(1,nil) = S_OK do begin if Failed(Item.GetdisplayName(SIGDN_norMALdisPLAY,displayName)) then Exit; try if AnsiSameText(displayName,LibraryName) then begin Result := SUCCEEDED(My_SHLoadLibraryFromItem(Item,grfMode,ppv)); Break; end; finally CoTaskMemFree(displayName); end; Item := nil; end; end; function GetLibraryFileSystemFolders(const LibraryName: String; Folders: TStrings): Boolean; var SL: IShellLibrary; Arr: IShellItemArray; Enum: IEnumShellItems; Item: IShellItem; Path: LPWSTR; begin Result := False; if not GetShellLibraryforLibrary(LibraryName,SL) then Exit; if Failed(SL.GetFolders(LFF_FORCEFILESYstem,Path)) then Exit; try Folders.Add(Path); finally CoTaskMemFree(Path); end; Item := nil; end; Result := True; end;

var Folders: TStringList; begin Folders := TStringList.Create; try if GetLibraryFileSystemFolders('MyLibrary',Folders) then begin //... end; finally Folders.Free; end; end;

我刚刚在marco Cantu的Mastering Delphi书籍的源代码库中找到了一个Delphi 2010的例子,它显示一个在库中获取位置的方法

到版本库的链接在这里: http : //code.marcocantu.com/p/marcodelphibooks/source/tree/HEAD/

在chapter 05 (Win7Libraries) , chapter 05 (Win7Libraries)就是示例源码。

该演示中使用的方法基本上是已经提到的Windows API的使用,演示确认库文件确实是XML格式。

此外,我发现以下信息非常有用:

SHAddFolderPathToLibrary – 将文件添加到库。

SHCreateLibrary IShellLibrary – 创建一个对象。

SHLoadLibraryFromItem – 创建并加载IShellLibrary以从指定的库定义文件中对象。

SHLoadLibraryFromKNownFolder – 为指定的KNowNFOLDERID创建并加载IShellLibrary对象。

SHLoadLibraryFromParsingName – 创建并加载指定路径的IShellLibrary对象。

SHRemoveFolderPathFromLibrary – 从库中删除文件夹。

SHResolveFolderPathInLibrary – 尝试解析已移动或重命名的库文件夹的目标位置。

SHResolveLibrary – 尝试查找库的位置。

SHSaveLibraryInFolderPath – 将IShellLibrary对象保存到磁盘。

SHShowManageLibraryUI显示图书馆管理对话框,使用户能够管理图书馆文件夹和认保存位置。

版权声明:本文内容由互联网用户自发贡献,该文观点与技术仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌侵权/违法违规的内容, 请发送邮件至 [email protected] 举报,一经查实,本站将立刻删除。

相关推荐