diff options
author | Darkvater <darkvater@openttd.org> | 2006-12-09 23:55:56 +0000 |
---|---|---|
committer | Darkvater <darkvater@openttd.org> | 2006-12-09 23:55:56 +0000 |
commit | 74106ce6e90c2871ac78f21390ce01da6ec4f209 (patch) | |
tree | db4b5a398448256d50bf2166c258937fe8f07aa7 | |
parent | 5f8f0e4e47bda12d75239977a7519ceae9518a75 (diff) | |
download | openttd-74106ce6e90c2871ac78f21390ce01da6ec4f209.tar.xz |
(svn r7460) -Fix (r7337): [win32] If the underlying OS didn't have support for SHGetFolderPath the
application failed to run. Now test if the function exists and if not try a different
approach using our own OTTDSHGetFolderPath wrapper.
-rw-r--r-- | win32.c | 50 | ||||
-rw-r--r-- | win32.h | 9 |
2 files changed, 59 insertions, 0 deletions
@@ -14,6 +14,7 @@ #include <wininet.h> #include <io.h> #include <fcntl.h> +#include <shlobj.h> // SHGetFolderPath #include "variables.h" #include "win32.h" #include "fios.h" // opendir/readdir/closedir @@ -1092,3 +1093,52 @@ const char *FS2OTTD(const wchar_t *name) static char utf8_buf[512]; return convert_from_fs(name, utf8_buf, lengthof(utf8_buf)); } + +/** Our very own SHGetFolderPath function for support of windows operating + * systems that don't have this function (eg Win9x, etc.). We try using the + * native function, and if that doesn't exist we will try a more crude approach + * of environment variables and hope for the best */ +HRESULT OTTDSHGetFolderPath(HWND hwnd, int csidl, HANDLE hToken, DWORD dwFlags, LPTSTR pszPath) +{ + static HRESULT (WINAPI *SHGetFolderPath)(HWND, int, HANDLE, DWORD, LPTSTR) = NULL; + static bool first_time = true; + + /* We only try to load the library one time; if it fails, it fails */ + if (first_time) { +#if defined(UNICODE) +# define W(x) x "W" +#else +# define W(x) x "A" +#endif + if (!LoadLibraryList((Function*)&SHGetFolderPath, "SHFolder.dll\0" W("SHGetFolderPath") "\0\0")) { + DEBUG(misc, 0) ("Unable to load " W("SHGetFolderPath") "from SHFolder.dll"); + } +#undef W + first_time = false; + } + + if (SHGetFolderPath != NULL) return SHGetFolderPath(hwnd, csidl, hToken, dwFlags, pszPath); + + /* SHGetFolderPath doesn't exist, try a more conservative approach, + * eg environment variables. This is only included for legacy modes + * MSDN says: that 'pszPath' is a "Pointer to a null-terminated string of + * length MAX_PATH which will receive the path" so let's assume that + * Windows 95 with Internet Explorer 5.0, Windows 98 with Internet Explorer 5.0, + * Windows 98 Second Edition (SE), Windows NT 4.0 with Internet Explorer 5.0, + * Windows NT 4.0 with Service Pack 4 (SP4) */ + { + DWORD ret; + switch (csidl) { + case CSIDL_FONTS: /* Get the system font path, eg %WINDIR%\Fonts */ + ret = GetEnvironmentVariable(_T("WINDIR"), pszPath, MAX_PATH * sizeof(TCHAR)); + if (ret == 0) break; + _tcsncat(pszPath, _T("\\Fonts"), MAX_PATH * sizeof(TCHAR)); + + return (HRESULT)0; + break; + /* XXX - other types to go here when needed... */ + } + } + + return E_INVALIDARG; +} @@ -3,6 +3,7 @@ #ifndef WIN32_H #define WIN32_H +#include <windows.h> bool MyShowCursor(bool show); typedef void (*Function)(int); @@ -23,6 +24,14 @@ wchar_t *convert_to_fs(const char *name, wchar_t *utf16_buf, size_t buflen); # define WIDE_TO_MB_BUFFER(str, buffer, buflen) (str) #endif +/* Override SHGetFolderPath with our custom implementation */ +#if defined(SHGetFolderPath) +#undef SHGetFolderPath +#endif +#define SHGetFolderPath OTTDSHGetFolderPath + +HRESULT OTTDSHGetFolderPath(HWND, int, HANDLE, DWORD, LPTSTR); + #if defined(__MINGW32__) #define SHGFP_TYPE_CURRENT 0 #endif /* __MINGW32__ */ |