xref: /reactos/sdk/lib/atl/atlpath.h (revision d955b932)
1 // PROJECT:        ReactOS ATL CPathT
2 // LICENSE:        Public Domain
3 // PURPOSE:        Provides compatibility to Microsoft ATL
4 // PROGRAMMERS:    Benedikt Freisen
5 
6 #ifndef __ATLPATH_H__
7 #define __ATLPATH_H__
8 
9 #pragma once
10 
11 #include <atlcore.h>
12 #include <atlstr.h>
13 #include <shlwapi.h>
14 
15 namespace ATL
16 {
17 
18 template<typename StringType>
19 class CPathT
20 {
21     // const
PathFileExistsX(LPCSTR pszPath)22     inline BOOL PathFileExistsX(LPCSTR pszPath) const { return PathFileExistsA(pszPath); }
PathFileExistsX(LPCWSTR pszPath)23     inline BOOL PathFileExistsX(LPCWSTR pszPath) const { return PathFileExistsW(pszPath); }
PathFindExtensionX(LPCSTR pszPath)24     inline LPCSTR PathFindExtensionX(LPCSTR pszPath) const { return PathFindExtensionA(pszPath); }
PathFindExtensionX(LPCWSTR pszPath)25     inline LPCWSTR PathFindExtensionX(LPCWSTR pszPath) const { return PathFindExtensionW(pszPath); }
PathFindFileNameX(LPCSTR pszPath)26     inline LPCSTR PathFindFileNameX(LPCSTR pszPath) const { return PathFindFileNameA(pszPath); }
PathFindFileNameX(LPCWSTR pszPath)27     inline LPCWSTR PathFindFileNameX(LPCWSTR pszPath) const { return PathFindFileNameW(pszPath); }
PathGetDriveNumberX(LPCSTR pszPath)28     inline int PathGetDriveNumberX(LPCSTR pszPath) const { return PathGetDriveNumberA(pszPath); }
PathGetDriveNumberX(LPCWSTR pszPath)29     inline int PathGetDriveNumberX(LPCWSTR pszPath) const { return PathGetDriveNumberW(pszPath); }
PathIsDirectoryX(LPCSTR pszPath)30     inline BOOL PathIsDirectoryX(LPCSTR pszPath) const { return PathIsDirectoryA(pszPath); }
PathIsDirectoryX(LPCWSTR pszPath)31     inline BOOL PathIsDirectoryX(LPCWSTR pszPath) const { return PathIsDirectoryW(pszPath); }
PathIsFileSpecX(LPCSTR pszPath)32     inline BOOL PathIsFileSpecX(LPCSTR pszPath) const { return PathIsFileSpecA(pszPath); }
PathIsFileSpecX(LPCWSTR pszPath)33     inline BOOL PathIsFileSpecX(LPCWSTR pszPath) const { return PathIsFileSpecW(pszPath); }
PathIsPrefixX(LPCSTR pszPath,LPCSTR pszPrefix)34     inline BOOL PathIsPrefixX(LPCSTR pszPath, LPCSTR pszPrefix) { return PathIsPrefixA(pszPath, pszPrefix); }
PathIsPrefixX(LPCWSTR pszPath,LPCWSTR pszPrefix)35     inline BOOL PathIsPrefixX(LPCWSTR pszPath, LPCWSTR pszPrefix) { return PathIsPrefixW(pszPath, pszPrefix); }
PathIsRelativeX(LPCSTR pszPath)36     inline BOOL PathIsRelativeX(LPCSTR pszPath) const { return PathIsRelativeA(pszPath); }
PathIsRelativeX(LPCWSTR pszPath)37     inline BOOL PathIsRelativeX(LPCWSTR pszPath) const { return PathIsRelativeW(pszPath); }
PathIsRootX(LPCSTR pszPath)38     inline BOOL PathIsRootX(LPCSTR pszPath) const { return PathIsRootA(pszPath); }
PathIsRootX(LPCWSTR pszPath)39     inline BOOL PathIsRootX(LPCWSTR pszPath) const { return PathIsRootW(pszPath); }
PathIsSameRootX(LPCSTR pszPath,LPCSTR pszOther)40     inline BOOL PathIsSameRootX(LPCSTR pszPath, LPCSTR pszOther) const { return PathIsSameRootA(pszPath, pszOther); }
PathIsSameRootX(LPCWSTR pszPath,LPCWSTR pszOther)41     inline BOOL PathIsSameRootX(LPCWSTR pszPath, LPCWSTR pszOther) const { return PathIsSameRootW(pszPath, pszOther); }
PathIsUNCX(LPCSTR pszPath)42     inline BOOL PathIsUNCX(LPCSTR pszPath) { return PathIsUNCA(pszPath); }
PathIsUNCX(LPCWSTR pszPath)43     inline BOOL PathIsUNCX(LPCWSTR pszPath) { return PathIsUNCW(pszPath); }
PathIsUNCServerX(LPCSTR pszPath)44     inline BOOL PathIsUNCServerX(LPCSTR pszPath) { return PathIsUNCServerA(pszPath); }
PathIsUNCServerX(LPCWSTR pszPath)45     inline BOOL PathIsUNCServerX(LPCWSTR pszPath) { return PathIsUNCServerW(pszPath); }
PathIsUNCServerShareX(LPCSTR pszPath)46     inline BOOL PathIsUNCServerShareX(LPCSTR pszPath) { return PathIsUNCServerShareA(pszPath); }
PathIsUNCServerShareX(LPCWSTR pszPath)47     inline BOOL PathIsUNCServerShareX(LPCWSTR pszPath) { return PathIsUNCServerShareW(pszPath); }
PathMatchSpecX(LPCSTR pszPath,LPCSTR pszSpec)48     inline BOOL PathMatchSpecX(LPCSTR pszPath, LPCSTR pszSpec) const { return PathMatchSpecA(pszPath, pszSpec); }
PathMatchSpecX(LPCWSTR pszPath,LPCWSTR pszSpec)49     inline BOOL PathMatchSpecX(LPCWSTR pszPath, LPCWSTR pszSpec) const { return PathMatchSpecW(pszPath, pszSpec); }
PathSkipRootX(LPCSTR pszPath)50     inline LPCSTR PathSkipRootX(LPCSTR pszPath) const { return PathSkipRootA(pszPath); }
PathSkipRootX(LPCWSTR pszPath)51     inline LPCWSTR PathSkipRootX(LPCWSTR pszPath) const { return PathSkipRootW(pszPath); }
52 
53     // non-const
PathAddBackslashX(LPSTR pszPath)54     inline void PathAddBackslashX(LPSTR pszPath) { PathAddBackslashA(pszPath); }
PathAddBackslashX(LPWSTR pszPath)55     inline void PathAddBackslashX(LPWSTR pszPath) { PathAddBackslashW(pszPath); }
PathAddExtensionX(LPSTR pszPath,LPCSTR pszExt)56     inline BOOL PathAddExtensionX(LPSTR pszPath, LPCSTR pszExt) { return PathAddExtensionA(pszPath, pszExt); }
PathAddExtensionX(LPWSTR pszPath,LPCWSTR pszExt)57     inline BOOL PathAddExtensionX(LPWSTR pszPath, LPCWSTR pszExt) { return PathAddExtensionW(pszPath, pszExt); }
PathAppendX(LPSTR pszPath,LPCSTR pszMore)58     inline BOOL PathAppendX(LPSTR pszPath, LPCSTR pszMore) { return PathAppendA(pszPath, pszMore); }
PathAppendX(LPWSTR pszPath,LPCWSTR pszMore)59     inline BOOL PathAppendX(LPWSTR pszPath, LPCWSTR pszMore) { return PathAppendW(pszPath, pszMore); }
PathBuildRootX(LPSTR pszRoot,int iDrive)60     inline void PathBuildRootX(LPSTR pszRoot, int iDrive) { PathBuildRootA(pszRoot, iDrive); }
PathBuildRootX(LPWSTR pszRoot,int iDrive)61     inline void PathBuildRootX(LPWSTR pszRoot, int iDrive) { PathBuildRootW(pszRoot, iDrive); }
PathCanonicalizeX(LPSTR pszDst,LPCSTR pszSrc)62     inline void PathCanonicalizeX(LPSTR pszDst, LPCSTR pszSrc) { PathCanonicalizeA(pszDst, pszSrc); }
PathCanonicalizeX(LPWSTR pszDst,LPCWSTR pszSrc)63     inline void PathCanonicalizeX(LPWSTR pszDst, LPCWSTR pszSrc) { PathCanonicalizeW(pszDst, pszSrc); }
PathCombineX(LPSTR pszPathOut,LPCSTR pszPathIn,LPCSTR pszMore)64     inline void PathCombineX(LPSTR pszPathOut, LPCSTR pszPathIn, LPCSTR pszMore) { PathCombineA(pszPathOut, pszPathIn, pszMore); }
PathCombineX(LPWSTR pszPathOut,LPCWSTR pszPathIn,LPCWSTR pszMore)65     inline void PathCombineX(LPWSTR pszPathOut, LPCWSTR pszPathIn, LPCWSTR pszMore) { PathCombineW(pszPathOut, pszPathIn, pszMore); }
PathCommonPrefixX(LPCSTR pszFile1,LPCSTR pszFile2,LPSTR pszPath)66     inline CPathT<StringType> PathCommonPrefixX(LPCSTR pszFile1, LPCSTR pszFile2, LPSTR pszPath) { return PathCommonPrefixA(pszFile1, pszFile2, pszPath); }
PathCommonPrefixX(LPCWSTR pszFile1,LPCWSTR pszFile2,LPWSTR pszPath)67     inline CPathT<StringType> PathCommonPrefixX(LPCWSTR pszFile1, LPCWSTR pszFile2, LPWSTR pszPath) { return PathCommonPrefixW(pszFile1, pszFile2, pszPath); }
PathCompactPathX(HDC hDC,LPSTR pszPath,UINT dx)68     inline BOOL PathCompactPathX(HDC hDC, LPSTR pszPath, UINT dx) { return PathCompactPathA(hDC, pszPath, dx); }
PathCompactPathX(HDC hDC,LPWSTR pszPath,UINT dx)69     inline BOOL PathCompactPathX(HDC hDC, LPWSTR pszPath, UINT dx) { return PathCompactPathW(hDC, pszPath, dx); }
PathCompactPathExX(LPSTR pszOut,LPCSTR pszSrc,UINT cchMax,DWORD dwFlags)70     inline BOOL PathCompactPathExX(LPSTR pszOut, LPCSTR pszSrc, UINT cchMax, DWORD dwFlags) { return PathCompactPathExA(pszOut, pszSrc, cchMax, dwFlags); }
PathCompactPathExX(LPWSTR pszOut,LPCWSTR pszSrc,UINT cchMax,DWORD dwFlags)71     inline BOOL PathCompactPathExX(LPWSTR pszOut, LPCWSTR pszSrc, UINT cchMax, DWORD dwFlags) { return PathCompactPathExW(pszOut, pszSrc, cchMax, dwFlags); }
PathMakePrettyX(LPSTR pszPath)72     inline BOOL PathMakePrettyX(LPSTR pszPath) { return PathMakePrettyA(pszPath); }
PathMakePrettyX(LPWSTR pszPath)73     inline BOOL PathMakePrettyX(LPWSTR pszPath) { return PathMakePrettyW(pszPath); }
PathQuoteSpacesX(LPSTR pszPath)74     inline void PathQuoteSpacesX(LPSTR pszPath) { PathQuoteSpacesA(pszPath); }
PathQuoteSpacesX(LPWSTR pszPath)75     inline void PathQuoteSpacesX(LPWSTR pszPath) { PathQuoteSpacesW(pszPath); }
PathRelativePathToX(LPSTR pszPath,LPCSTR pszFrom,DWORD dwAttrFrom,LPCSTR pszTo,DWORD dwAttrTo)76     inline BOOL PathRelativePathToX(LPSTR pszPath, LPCSTR pszFrom, DWORD dwAttrFrom, LPCSTR pszTo, DWORD dwAttrTo) { return PathRelativePathToA(pszPath, pszFrom, dwAttrFrom, pszTo, dwAttrTo); }
PathRelativePathToX(LPWSTR pszPath,LPCWSTR pszFrom,DWORD dwAttrFrom,LPCWSTR pszTo,DWORD dwAttrTo)77     inline BOOL PathRelativePathToX(LPWSTR pszPath, LPCWSTR pszFrom, DWORD dwAttrFrom, LPCWSTR pszTo, DWORD dwAttrTo) { return PathRelativePathToW(pszPath, pszFrom, dwAttrFrom, pszTo, dwAttrTo); }
PathRemoveArgsX(LPSTR pszPath)78     inline void PathRemoveArgsX(LPSTR pszPath) { PathRemoveArgsA(pszPath); }
PathRemoveArgsX(LPWSTR pszPath)79     inline void PathRemoveArgsX(LPWSTR pszPath) { PathRemoveArgsW(pszPath); }
PathRemoveBackslashX(LPSTR pszPath)80     inline void PathRemoveBackslashX(LPSTR pszPath) { PathRemoveBackslashA(pszPath); }
PathRemoveBackslashX(LPWSTR pszPath)81     inline void PathRemoveBackslashX(LPWSTR pszPath) { PathRemoveBackslashW(pszPath); }
PathRemoveBlanksX(LPSTR pszPath)82     inline void PathRemoveBlanksX(LPSTR pszPath) { PathRemoveBlanksA(pszPath); }
PathRemoveBlanksX(LPWSTR pszPath)83     inline void PathRemoveBlanksX(LPWSTR pszPath) { PathRemoveBlanksW(pszPath); }
PathRemoveExtensionX(LPSTR pszPath)84     inline void PathRemoveExtensionX(LPSTR pszPath) { PathRemoveExtensionA(pszPath); }
PathRemoveExtensionX(LPWSTR pszPath)85     inline void PathRemoveExtensionX(LPWSTR pszPath) { PathRemoveExtensionW(pszPath); }
PathRemoveFileSpecX(LPSTR pszPath)86     inline BOOL PathRemoveFileSpecX(LPSTR pszPath) { return PathRemoveFileSpecA(pszPath); }
PathRemoveFileSpecX(LPWSTR pszPath)87     inline BOOL PathRemoveFileSpecX(LPWSTR pszPath) { return PathRemoveFileSpecW(pszPath); }
PathRenameExtensionX(LPSTR pszPath,LPCSTR pszExt)88     inline BOOL PathRenameExtensionX(LPSTR pszPath, LPCSTR pszExt) { return PathRenameExtensionA(pszPath, pszExt); }
PathRenameExtensionX(LPWSTR pszPath,LPCWSTR pszExt)89     inline BOOL PathRenameExtensionX(LPWSTR pszPath, LPCWSTR pszExt) { return PathRenameExtensionW(pszPath, pszExt); }
PathStripPathX(LPSTR pszPath)90     inline void PathStripPathX(LPSTR pszPath) { PathStripPathA(pszPath); }
PathStripPathX(LPWSTR pszPath)91     inline void PathStripPathX(LPWSTR pszPath) { PathStripPathW(pszPath); }
PathStripToRootX(LPSTR pszPath)92     inline BOOL PathStripToRootX(LPSTR pszPath) { return PathStripToRootA(pszPath); }
PathStripToRootX(LPWSTR pszPath)93     inline BOOL PathStripToRootX(LPWSTR pszPath) { return PathStripToRootW(pszPath); }
PathUnquoteSpacesX(LPSTR pszPath)94     inline void PathUnquoteSpacesX(LPSTR pszPath) { PathUnquoteSpacesA(pszPath); }
PathUnquoteSpacesX(LPWSTR pszPath)95     inline void PathUnquoteSpacesX(LPWSTR pszPath) { PathUnquoteSpacesW(pszPath); }
96 
97 public:
98     typedef typename StringType::PCXSTR PCXSTR;
99     typedef typename StringType::PXSTR PXSTR;
100     typedef typename StringType::XCHAR XCHAR;
101 
102     StringType m_strPath;
103 
CPathT(PCXSTR pszPath)104     CPathT(PCXSTR pszPath)
105     {
106         m_strPath = StringType(pszPath);
107     }
108 
CPathT(const CPathT<StringType> & path)109     CPathT(const CPathT<StringType>& path)
110     {
111         m_strPath = path.m_strPath;
112     }
113 
CPathT()114     CPathT() noexcept
115     {
116         // do nothing, m_strPath initializes itself
117     }
118 
AddBackslash()119     void AddBackslash()
120     {
121         PXSTR str = m_strPath.GetBuffer(MAX_PATH);
122         PathAddBackslashX(str);
123         m_strPath.ReleaseBuffer();
124     }
125 
AddExtension(PCXSTR pszExtension)126     BOOL AddExtension(PCXSTR pszExtension)
127     {
128         PXSTR str = m_strPath.GetBuffer(MAX_PATH);
129         BOOL result = PathAddExtensionX(str, pszExtension);
130         m_strPath.ReleaseBuffer();
131         return result;
132     }
133 
Append(PCXSTR pszMore)134     BOOL Append(PCXSTR pszMore)
135     {
136         PXSTR str = m_strPath.GetBuffer(MAX_PATH);
137         BOOL result = PathAppendX(str, pszMore);
138         m_strPath.ReleaseBuffer();
139         return result;
140     }
141 
BuildRoot(int iDrive)142     void BuildRoot(int iDrive)
143     {
144         PXSTR str = m_strPath.GetBuffer(4);
145         PathBuildRootX(str, iDrive);
146         m_strPath.ReleaseBuffer();
147     }
148 
Canonicalize()149     void Canonicalize()
150     {
151         StringType strTemp;
152         PXSTR str = strTemp.GetBuffer(MAX_PATH);
153         PathCanonicalizeX(str, m_strPath);
154         strTemp.ReleaseBuffer();
155         m_strPath = strTemp;
156     }
157 
Combine(PCXSTR pszDir,PCXSTR pszFile)158     void Combine(PCXSTR pszDir, PCXSTR pszFile)
159     {
160         PXSTR str = m_strPath.GetBuffer(MAX_PATH);
161         PathCombineX(str, pszDir, pszFile);
162         m_strPath.ReleaseBuffer();
163     }
164 
CommonPrefix(PCXSTR pszOther)165     CPathT<StringType> CommonPrefix(PCXSTR pszOther)
166     {
167         StringType result;
168         result.SetString(m_strPath, PathCommonPrefixX(m_strPath, pszOther, NULL));
169         return result;
170     }
171 
CompactPath(HDC hDC,UINT nWidth)172     BOOL CompactPath(HDC hDC, UINT nWidth)
173     {
174         PXSTR str = m_strPath.GetBuffer(MAX_PATH);
175         BOOL result = PathCompactPathX(hDC, str, nWidth);
176         m_strPath.ReleaseBuffer();
177         return result;
178     }
179 
180     BOOL CompactPathEx(UINT nMaxChars, DWORD dwFlags = 0)
181     {
182         StringType strTemp;
183         PXSTR str = strTemp.GetBuffer(nMaxChars);
184         BOOL result = PathCompactPathExX(str, m_strPath, nMaxChars, dwFlags);
185         strTemp.ReleaseBuffer();
186         m_strPath = strTemp;
187         return result;
188     }
189 
FileExists()190     BOOL FileExists() const
191     {
192         return PathFileExistsX(m_strPath);
193     }
194 
FindExtension()195     int FindExtension() const
196     {
197         PCXSTR extension = PathFindExtensionX(m_strPath);
198         if (*extension == '\0')
199             return -1;
200 
201         PCXSTR str = m_strPath;
202         return (int)(extension - str);
203     }
204 
FindFileName()205     int FindFileName() const
206     {
207         PCXSTR filename = PathFindFileNameX(m_strPath);
208         if (*filename == '\0')
209             return -1;
210 
211         PCXSTR str = m_strPath;
212         return (int)(filename - str);
213     }
214 
GetDriveNumber()215     int GetDriveNumber() const
216     {
217         return PathGetDriveNumberX(m_strPath);
218     }
219 
GetExtension()220     StringType GetExtension() const
221     {
222         return StringType(PathFindExtensionX(m_strPath));
223     }
224 
IsDirectory()225     BOOL IsDirectory() const
226     {
227         return PathIsDirectoryX(m_strPath);
228     }
229 
IsFileSpec()230     BOOL IsFileSpec() const
231     {
232         return PathIsFileSpecX(m_strPath);
233     }
234 
IsPrefix(PCXSTR pszPrefix)235     BOOL IsPrefix(PCXSTR pszPrefix) const
236     {
237         return PathIsPrefixX(m_strPath);
238     }
239 
IsRelative()240     BOOL IsRelative() const
241     {
242         return PathIsRelativeX(m_strPath);
243     }
244 
IsRoot()245     BOOL IsRoot() const
246     {
247         return PathIsRootX(m_strPath);
248     }
249 
IsSameRoot(PCXSTR pszOther)250     BOOL IsSameRoot(PCXSTR pszOther) const
251     {
252         return PathIsSameRootX(m_strPath, pszOther);
253     }
254 
IsUNC()255     BOOL IsUNC() const
256     {
257         return PathIsUNCX(m_strPath);
258     }
259 
IsUNCServer()260     BOOL IsUNCServer() const
261     {
262         return PathIsUNCServerX(m_strPath);
263     }
264 
IsUNCServerShare()265     BOOL IsUNCServerShare() const
266     {
267         return PathIsUNCServerShareX(m_strPath);
268     }
269 
MakePretty()270     BOOL MakePretty()
271     {
272         PXSTR str = m_strPath.GetBuffer(MAX_PATH);
273         BOOL result = PathMakePrettyX(str);
274         m_strPath.ReleaseBuffer();
275         return result;
276     }
277 
MatchSpec(PCXSTR pszSpec)278     BOOL MatchSpec(PCXSTR pszSpec) const
279     {
280         return PathMatchSpecX(m_strPath, pszSpec);
281     }
282 
QuoteSpaces()283     void QuoteSpaces()
284     {
285         PXSTR str = m_strPath.GetBuffer(MAX_PATH);
286         PathQuoteSpacesX(str);
287         m_strPath.ReleaseBuffer();
288     }
289 
RelativePathTo(PCXSTR pszFrom,DWORD dwAttrFrom,PCXSTR pszTo,DWORD dwAttrTo)290     BOOL RelativePathTo(PCXSTR pszFrom, DWORD dwAttrFrom, PCXSTR pszTo, DWORD dwAttrTo)
291     {
292         PXSTR str = m_strPath.GetBuffer(MAX_PATH);
293         BOOL result = PathRelativePathToX(str, pszFrom, dwAttrFrom, pszTo, dwAttrTo);
294         m_strPath.ReleaseBuffer();
295         return result;
296     }
297 
RemoveArgs()298     void RemoveArgs()
299     {
300         PXSTR str = m_strPath.GetBuffer(MAX_PATH);
301         PathRemoveArgsX(str);
302         m_strPath.ReleaseBuffer();
303     }
304 
RemoveBackslash()305     void RemoveBackslash()
306     {
307         PXSTR str = m_strPath.GetBuffer(MAX_PATH);
308         PathRemoveBackslashX(str);
309         m_strPath.ReleaseBuffer();
310     }
311 
RemoveBlanks()312     void RemoveBlanks()
313     {
314         PXSTR str = m_strPath.GetBuffer(MAX_PATH);
315         PathRemoveBlanksX(str);
316         m_strPath.ReleaseBuffer();
317     }
318 
RemoveExtension()319     void RemoveExtension()
320     {
321         PXSTR str = m_strPath.GetBuffer(MAX_PATH);
322         PathRemoveExtensionX(str);
323         m_strPath.ReleaseBuffer();
324     }
325 
RemoveFileSpec()326     BOOL RemoveFileSpec()
327     {
328         PXSTR str = m_strPath.GetBuffer(MAX_PATH);
329         BOOL result = PathRemoveFileSpecX(str);
330         m_strPath.ReleaseBuffer();
331         return result;
332     }
333 
RenameExtension(PCXSTR pszExtension)334     BOOL RenameExtension(PCXSTR pszExtension)
335     {
336         PXSTR str = m_strPath.GetBuffer(MAX_PATH);
337         BOOL result = PathRenameExtensionX(str, pszExtension);
338         m_strPath.ReleaseBuffer();
339         return result;
340     }
341 
SkipRoot()342     int SkipRoot() const
343     {
344         PCXSTR str = m_strPath;
345         return (int)(PathSkipRootX(m_strPath) - str);
346     }
347 
StripPath()348     void StripPath()
349     {
350         PXSTR str = m_strPath.GetBuffer(MAX_PATH);
351         PathStripPathX(str);
352         m_strPath.ReleaseBuffer();
353     }
354 
StripToRoot()355     BOOL StripToRoot()
356     {
357         PXSTR str = m_strPath.GetBuffer(MAX_PATH);
358         BOOL result = PathStripToRootX(str);
359         m_strPath.ReleaseBuffer();
360         return result;
361     }
362 
UnquoteSpaces()363     void UnquoteSpaces()
364     {
365         PXSTR str = m_strPath.GetBuffer(MAX_PATH);
366         PathUnquoteSpacesX(str);
367         m_strPath.ReleaseBuffer();
368     }
369 
370     operator const StringType&() const noexcept
371     {
372         return m_strPath;
373     }
374 
PCXSTR()375     operator PCXSTR() const noexcept
376     {
377         return m_strPath;
378     }
379 
380     operator StringType&() noexcept
381     {
382         return m_strPath;
383     }
384 
385     CPathT<StringType>& operator+=(PCXSTR pszMore)
386     {
387         Append(pszMore);
388         return *this;
389     }
390 
391 };
392 
393 typedef CPathT<CString> CPath;
394 typedef CPathT<CStringA> CPathA;
395 typedef CPathT<CStringW> CPathW;
396 
397 }  // namespace ATL
398 
399 #endif
400