在开发ActiveX时,有一个功能时让用户选择要保存的目标目录,在执行的过程发现文件并没有真正被保存到用户设置的目标目录,检查了下发现文件被存到了C:\Users\当前用户名\AppData\Local\Microsoft\Windows\Temporary Internet Files\Virtualized\用户实际设置的目标目录(盘符后面的’:‘被替换成’\‘),而我们在windows资源管理器中视图其实无法在Temporary Internet Files中找到Virtualized文件夹,但可以在地址栏中用路径访问到目标目录和文件;这实际上是windows的重定向机制,IE对本地文件系统写入限制在某些文件夹中,并且这些如IE缓存目录等windows设定的目录,普通用户往往不知道。
IE对读取没有做限制,这里我的思路是先将文件写入操作在IE保护模式下允许的那几个文件夹中进行如Temporary Iternet Files,IE用来缓存临时文件的目录,以下为API和实现获取临时目录
Requirements(注意系统要求)
Minimum supported client | Windows Vista [desktop apps only] |
---|---|
Minimum supported server | Windows Server 2008 [desktop apps only] |
Header |
|
DLL |
|
HRESULT SHGetKnownFolderPath(
_In_ REFKNOWNFOLDERID rfid,
_In_ DWORD dwFlags,
_In_opt_ HANDLE hToken,
_Out_ PWSTR *ppszPath
);
<pre name="code" class="cpp"> //获取Temporary Internet Files目录
hr = SHGetKnownFolderPath(FOLDERID_InternetCache, 0, NULL, &pwszTempDir);
if (!SUCCEEDED(hr))
{
return FALSE;
}
m_csTempDir = CW2CT(pwszTempDir); //UNICODE转项目所需字符集
m_csTempDir += _T("\\");
CoTaskMemFree(pwszTempDir); //不需要后需释放
接下来所有的文件的写入操作都在此目录中操作,完成文件操作后,只要考虑将文件移动到用户设定的目标目录即可,完成这个目的需要用到IE保护模式提供的API
BOOL IEMoveFileEx( _In_ LPCWSTR lpExistingFileName, _In_ LPCWSTR lpNewFileName, DWORD dwFlags );IE保护模式将一系列API提供给开发者,用于访问高完整性用户上下文( higher-integrity user context),而上述API用于移动文件,从上述临时目录将文件移到目标目录
<span style="font-size:18px;">bRet = <span style="font-family: Consolas, Courier, monospace; line-height: 18.18181800842285px;">IEMoveFileEx</span>(lpExistingFileName, lpNewFileName, dwFlags);</span>
之所以用移动的方式,主要是前面的文件操作都可以用熟悉的API或MFC类库来实现。