Mercurial > foo_out_sdl
comparison foosdk/sdk/foobar2000/shared/utf8api.cpp @ 1:20d02a178406 default tip
*: check in everything else
yay
| author | Paper <paper@tflc.us> |
|---|---|
| date | Mon, 05 Jan 2026 02:15:46 -0500 |
| parents | |
| children |
comparison
equal
deleted
inserted
replaced
| 0:e9bb126753e7 | 1:20d02a178406 |
|---|---|
| 1 #include "shared.h" | |
| 2 | |
| 3 | |
| 4 #include <lmcons.h> | |
| 5 | |
| 6 #ifndef BIF_NEWDIALOGSTYLE | |
| 7 #define BIF_NEWDIALOGSTYLE 0x0040 | |
| 8 #endif | |
| 9 | |
| 10 using namespace pfc; | |
| 11 | |
| 12 class param_os_from_utf8 | |
| 13 { | |
| 14 bool m_is_null; | |
| 15 WORD m_low_word; | |
| 16 stringcvt::string_os_from_utf8 m_cvt; | |
| 17 public: | |
| 18 param_os_from_utf8(const char * p) : | |
| 19 m_is_null(p==NULL), | |
| 20 m_low_word( ((t_size)p & ~0xFFFF) == 0 ? (WORD)((t_size)p & 0xFFFF) : 0), | |
| 21 m_cvt( p != NULL && ((t_size)p & ~0xFFFF) != 0 ? p : "") | |
| 22 {} | |
| 23 operator const TCHAR *() | |
| 24 { | |
| 25 return get_ptr(); | |
| 26 } | |
| 27 const TCHAR * get_ptr() | |
| 28 { | |
| 29 return m_low_word ? (const TCHAR*)(t_size)m_low_word : m_is_null ? 0 : m_cvt.get_ptr(); | |
| 30 } | |
| 31 | |
| 32 }; | |
| 33 | |
| 34 | |
| 35 | |
| 36 extern "C" { | |
| 37 | |
| 38 LRESULT SHARED_EXPORT uSendMessageText(HWND wnd,UINT msg,WPARAM wp,const char * p_text) | |
| 39 { | |
| 40 if (p_text == NULL) | |
| 41 return SendMessage(wnd,msg,wp,0); | |
| 42 else { | |
| 43 stringcvt::string_os_from_utf8 temp; | |
| 44 temp.convert(p_text); | |
| 45 return SendMessage(wnd,msg,wp,(LPARAM)temp.get_ptr()); | |
| 46 } | |
| 47 } | |
| 48 | |
| 49 LRESULT SHARED_EXPORT uSendDlgItemMessageText(HWND wnd,UINT id,UINT msg,WPARAM wp,const char * text) | |
| 50 { | |
| 51 return uSendMessageText(uGetDlgItem(wnd,id),msg,wp,text);//SendDlgItemMessage(wnd,id,msg,wp,(long)(const TCHAR*)string_os_from_utf8(text)); | |
| 52 } | |
| 53 | |
| 54 BOOL SHARED_EXPORT uGetWindowText(HWND wnd,string_base & out) | |
| 55 { | |
| 56 PFC_ASSERT( wnd != NULL ); | |
| 57 int len = GetWindowTextLength(wnd); | |
| 58 if (len>0) | |
| 59 { | |
| 60 len++; | |
| 61 pfc::array_t<TCHAR> temp; | |
| 62 temp.set_size(len); | |
| 63 temp[0]=0; | |
| 64 if (GetWindowText(wnd,temp.get_ptr(),len)>0) | |
| 65 { | |
| 66 out = stringcvt::string_utf8_from_os(temp.get_ptr(),len); | |
| 67 return TRUE; | |
| 68 } | |
| 69 else return FALSE; | |
| 70 } | |
| 71 else | |
| 72 { | |
| 73 out.reset(); | |
| 74 return TRUE; | |
| 75 } | |
| 76 } | |
| 77 | |
| 78 BOOL SHARED_EXPORT uSetWindowTextEx(HWND wnd,const char * p_text,size_t p_text_length) | |
| 79 { | |
| 80 return SetWindowText(wnd,stringcvt::string_os_from_utf8(p_text, p_text_length)); | |
| 81 } | |
| 82 | |
| 83 | |
| 84 BOOL SHARED_EXPORT uGetDlgItemText(HWND wnd,UINT id,string_base & out) | |
| 85 { | |
| 86 return uGetWindowText(GetDlgItem(wnd,id),out); | |
| 87 } | |
| 88 | |
| 89 BOOL SHARED_EXPORT uSetDlgItemTextEx(HWND wnd,UINT id,const char * p_text,size_t p_text_length) | |
| 90 { | |
| 91 return SetDlgItemText(wnd,id,stringcvt::string_os_from_utf8(p_text,p_text_length)); | |
| 92 } | |
| 93 | |
| 94 int SHARED_EXPORT uMessageBox(HWND wnd,const char * text,const char * caption,UINT type) | |
| 95 { | |
| 96 modal_dialog_scope scope(wnd); | |
| 97 return MessageBox(wnd,param_os_from_utf8(text),param_os_from_utf8(caption),type); | |
| 98 } | |
| 99 | |
| 100 void SHARED_EXPORT uOutputDebugString(const char * msg) {OutputDebugString(stringcvt::string_os_from_utf8(msg));} | |
| 101 | |
| 102 BOOL SHARED_EXPORT uAppendMenu(HMENU menu,UINT flags,UINT_PTR id,const char * content) | |
| 103 { | |
| 104 return AppendMenu(menu,flags,id,param_os_from_utf8(content)); | |
| 105 } | |
| 106 | |
| 107 BOOL SHARED_EXPORT uInsertMenu(HMENU menu,UINT position,UINT flags,UINT_PTR id,const char * content) | |
| 108 { | |
| 109 return InsertMenu(menu,position,flags,id,param_os_from_utf8(content)); | |
| 110 } | |
| 111 | |
| 112 int SHARED_EXPORT uCharCompare(t_uint32 p_char1,t_uint32 p_char2) { | |
| 113 #ifdef UNICODE | |
| 114 wchar_t temp1[4],temp2[4]; | |
| 115 temp1[utf16_encode_char(p_char1,temp1)]=0; | |
| 116 temp2[utf16_encode_char(p_char2,temp2)]=0; | |
| 117 return lstrcmpiW(temp1,temp2); | |
| 118 #else | |
| 119 wchar_t temp1[4],temp2[4]; | |
| 120 char ctemp1[20],ctemp2[20]; | |
| 121 temp1[utf16_encode_char(p_char1,temp1)]=0; | |
| 122 temp2[utf16_encode_char(p_char2,temp2)]=0; | |
| 123 WideCharToMultiByte(CP_ACP,0,temp1,-1,ctemp1,_countof(ctemp1),0,0); | |
| 124 WideCharToMultiByte(CP_ACP,0,temp2,-1,ctemp2,_countof(ctemp2),0,0); | |
| 125 return lstrcmpiA(ctemp1,ctemp2); | |
| 126 #endif | |
| 127 } | |
| 128 | |
| 129 int SHARED_EXPORT uStringCompare(const char * elem1, const char * elem2) { | |
| 130 for(;;) { | |
| 131 unsigned c1,c2; t_size l1,l2; | |
| 132 l1 = utf8_decode_char(elem1,c1); | |
| 133 l2 = utf8_decode_char(elem2,c2); | |
| 134 if (l1==0 && l2==0) return 0; | |
| 135 if (c1!=c2) { | |
| 136 int test = uCharCompare(c1,c2); | |
| 137 if (test) return test; | |
| 138 } | |
| 139 elem1 += l1; | |
| 140 elem2 += l2; | |
| 141 } | |
| 142 } | |
| 143 | |
| 144 int SHARED_EXPORT uStringCompare_ConvertNumbers(const char * elem1,const char * elem2) { | |
| 145 for(;;) { | |
| 146 if (pfc::char_is_numeric(*elem1) && pfc::char_is_numeric(*elem2)) { | |
| 147 t_size delta1 = 1, delta2 = 1; | |
| 148 while(pfc::char_is_numeric(elem1[delta1])) delta1++; | |
| 149 while(pfc::char_is_numeric(elem2[delta2])) delta2++; | |
| 150 int test = pfc::compare_t(pfc::atoui64_ex(elem1,delta1),pfc::atoui64_ex(elem2,delta2)); | |
| 151 if (test != 0) return test; | |
| 152 elem1 += delta1; | |
| 153 elem2 += delta2; | |
| 154 } else { | |
| 155 unsigned c1,c2; t_size l1,l2; | |
| 156 l1 = utf8_decode_char(elem1,c1); | |
| 157 l2 = utf8_decode_char(elem2,c2); | |
| 158 if (l1==0 && l2==0) return 0; | |
| 159 if (c1!=c2) { | |
| 160 int test = uCharCompare(c1,c2); | |
| 161 if (test) return test; | |
| 162 } | |
| 163 elem1 += l1; | |
| 164 elem2 += l2; | |
| 165 } | |
| 166 } | |
| 167 } | |
| 168 | |
| 169 HINSTANCE SHARED_EXPORT uLoadLibrary(const char * name) | |
| 170 { | |
| 171 return LoadLibrary(param_os_from_utf8(name)); | |
| 172 } | |
| 173 | |
| 174 HANDLE SHARED_EXPORT uCreateEvent(LPSECURITY_ATTRIBUTES lpEventAttributes,BOOL bManualReset,BOOL bInitialState, const char * lpName) | |
| 175 { | |
| 176 return CreateEvent(lpEventAttributes,bManualReset,bInitialState, param_os_from_utf8(lpName)); | |
| 177 } | |
| 178 | |
| 179 DWORD SHARED_EXPORT uGetModuleFileName(HMODULE hMod,string_base & out) | |
| 180 { | |
| 181 try { | |
| 182 pfc::array_t<TCHAR> buffer; buffer.set_size(256); | |
| 183 for(;;) { | |
| 184 DWORD ret = GetModuleFileName(hMod,buffer.get_ptr(), (DWORD)buffer.get_size()); | |
| 185 if (ret == 0) return 0; | |
| 186 if (ret < buffer.get_size()) break; | |
| 187 buffer.set_size(buffer.get_size() * 2); | |
| 188 } | |
| 189 out = stringcvt::string_utf8_from_os(buffer.get_ptr(),buffer.get_size()); | |
| 190 return (DWORD) out.length(); | |
| 191 } catch(...) { | |
| 192 return 0; | |
| 193 } | |
| 194 } | |
| 195 | |
| 196 BOOL SHARED_EXPORT uSetClipboardRawData(UINT format,const void * ptr,t_size size) { | |
| 197 try { | |
| 198 HANDLE buffer = GlobalAlloc(GMEM_DDESHARE,size); | |
| 199 if (buffer == NULL) throw std::bad_alloc(); | |
| 200 try { | |
| 201 CGlobalLockScope lock(buffer); | |
| 202 PFC_ASSERT(lock.GetSize() == size); | |
| 203 memcpy(lock.GetPtr(),ptr,size); | |
| 204 } catch(...) { | |
| 205 GlobalFree(buffer); throw; | |
| 206 } | |
| 207 | |
| 208 if (SetClipboardData(format,buffer) == NULL) throw pfc::exception_bug_check(); | |
| 209 return TRUE; | |
| 210 } catch(...) { | |
| 211 return FALSE; | |
| 212 } | |
| 213 } | |
| 214 BOOL SHARED_EXPORT uSetClipboardString(const char * ptr) | |
| 215 { | |
| 216 try { | |
| 217 CClipboardOpenScope scope; | |
| 218 if (!scope.Open(NULL)) return FALSE; | |
| 219 EmptyClipboard(); | |
| 220 stringcvt::string_os_from_utf8 temp(ptr); | |
| 221 return uSetClipboardRawData( | |
| 222 #ifdef UNICODE | |
| 223 CF_UNICODETEXT | |
| 224 #else | |
| 225 CF_TEXT | |
| 226 #endif | |
| 227 ,temp.get_ptr(), (temp.length() + 1) * sizeof(TCHAR)); | |
| 228 } catch(...) { | |
| 229 return FALSE; | |
| 230 } | |
| 231 } | |
| 232 | |
| 233 BOOL SHARED_EXPORT uGetClipboardString(pfc::string_base & p_out) { | |
| 234 try { | |
| 235 CClipboardOpenScope scope; | |
| 236 if (!scope.Open(NULL)) return FALSE; | |
| 237 HANDLE data = GetClipboardData( | |
| 238 #ifdef UNICODE | |
| 239 CF_UNICODETEXT | |
| 240 #else | |
| 241 CF_TEXT | |
| 242 #endif | |
| 243 ); | |
| 244 if (data == NULL) return FALSE; | |
| 245 | |
| 246 CGlobalLockScope lock(data); | |
| 247 p_out = pfc::stringcvt::string_utf8_from_os( (const TCHAR*) lock.GetPtr(), lock.GetSize() / sizeof(TCHAR) ); | |
| 248 return TRUE; | |
| 249 } catch(...) { | |
| 250 return FALSE; | |
| 251 } | |
| 252 } | |
| 253 | |
| 254 | |
| 255 BOOL SHARED_EXPORT uGetClassName(HWND wnd,string_base & out) | |
| 256 { | |
| 257 TCHAR temp[512]; | |
| 258 temp[0]=0; | |
| 259 if (GetClassName(wnd,temp,_countof(temp))>0) | |
| 260 { | |
| 261 out = stringcvt::string_utf8_from_os(temp,_countof(temp)); | |
| 262 return TRUE; | |
| 263 } | |
| 264 else return FALSE; | |
| 265 } | |
| 266 | |
| 267 t_size SHARED_EXPORT uCharLength(const char * src) {return utf8_char_len(src);} | |
| 268 | |
| 269 BOOL SHARED_EXPORT uDragQueryFile(HDROP hDrop,UINT idx,string_base & out) | |
| 270 { | |
| 271 UINT len = DragQueryFile(hDrop,idx,0,0); | |
| 272 if (len>0 && len!=(UINT)(~0)) | |
| 273 { | |
| 274 len++; | |
| 275 array_t<TCHAR> temp; | |
| 276 temp.set_size(len); | |
| 277 temp[0] =0 ; | |
| 278 if (DragQueryFile(hDrop,idx,temp.get_ptr(),len)>0) | |
| 279 { | |
| 280 out = stringcvt::string_utf8_from_os(temp.get_ptr(),len); | |
| 281 return TRUE; | |
| 282 } | |
| 283 } | |
| 284 return FALSE; | |
| 285 } | |
| 286 | |
| 287 UINT SHARED_EXPORT uDragQueryFileCount(HDROP hDrop) | |
| 288 { | |
| 289 return DragQueryFile(hDrop,-1,0,0); | |
| 290 } | |
| 291 | |
| 292 | |
| 293 | |
| 294 BOOL SHARED_EXPORT uGetTextExtentPoint32(HDC dc,const char * text,UINT cb,LPSIZE size) | |
| 295 { | |
| 296 stringcvt::string_os_from_utf8 temp(text,cb); | |
| 297 return GetTextExtentPoint32(dc,temp,pfc::downcast_guarded<int>(temp.length()),size); | |
| 298 } | |
| 299 | |
| 300 BOOL SHARED_EXPORT uExtTextOut(HDC dc,int x,int y,UINT flags,const RECT * rect,const char * text,UINT cb,const int * lpdx) | |
| 301 { | |
| 302 stringcvt::string_os_from_utf8 temp(text,cb); | |
| 303 return ExtTextOut(dc,x,y,flags,rect,temp,pfc::downcast_guarded<int>(_tcslen(temp)),lpdx); | |
| 304 } | |
| 305 | |
| 306 static UINT_PTR CALLBACK choose_color_hook(HWND wnd,UINT msg,WPARAM wp,LPARAM lp) | |
| 307 { | |
| 308 switch(msg) | |
| 309 { | |
| 310 case WM_INITDIALOG: | |
| 311 { | |
| 312 CHOOSECOLOR * cc = reinterpret_cast<CHOOSECOLOR*>(lp); | |
| 313 reinterpret_cast<modal_dialog_scope*>(cc->lCustData)->initialize(FindOwningPopup(wnd)); | |
| 314 } | |
| 315 return 0; | |
| 316 default: | |
| 317 return 0; | |
| 318 } | |
| 319 } | |
| 320 | |
| 321 BOOL SHARED_EXPORT uChooseColor(DWORD * p_color,HWND parent,DWORD * p_custom_colors) | |
| 322 { | |
| 323 modal_dialog_scope scope; | |
| 324 | |
| 325 CHOOSECOLOR cc = {}; | |
| 326 cc.lStructSize = sizeof(cc); | |
| 327 cc.hwndOwner = parent; | |
| 328 cc.rgbResult = *p_color; | |
| 329 cc.lpCustColors = p_custom_colors; | |
| 330 cc.Flags = CC_ANYCOLOR|CC_FULLOPEN|CC_RGBINIT|CC_ENABLEHOOK; | |
| 331 cc.lpfnHook = choose_color_hook; | |
| 332 cc.lCustData = reinterpret_cast<LPARAM>(&scope); | |
| 333 BOOL rv = ChooseColor(&cc); | |
| 334 if (rv) | |
| 335 { | |
| 336 *p_color = cc.rgbResult; | |
| 337 return TRUE; | |
| 338 } | |
| 339 else return FALSE; | |
| 340 } | |
| 341 | |
| 342 HCURSOR SHARED_EXPORT uLoadCursor(HINSTANCE hIns,const char * name) | |
| 343 { | |
| 344 return LoadCursor(hIns,param_os_from_utf8(name)); | |
| 345 } | |
| 346 | |
| 347 HICON SHARED_EXPORT uLoadIcon(HINSTANCE hIns,const char * name) | |
| 348 { | |
| 349 return LoadIcon(hIns,param_os_from_utf8(name)); | |
| 350 } | |
| 351 | |
| 352 HMENU SHARED_EXPORT uLoadMenu(HINSTANCE hIns,const char * name) | |
| 353 { | |
| 354 return LoadMenu(hIns,param_os_from_utf8(name)); | |
| 355 } | |
| 356 | |
| 357 | |
| 358 | |
| 359 BOOL SHARED_EXPORT uGetEnvironmentVariable(const char * name,string_base & out) | |
| 360 { | |
| 361 stringcvt::string_os_from_utf8 name_t(name); | |
| 362 DWORD size = GetEnvironmentVariable(name_t,0,0); | |
| 363 if (size>0) | |
| 364 { | |
| 365 size++; | |
| 366 array_t<TCHAR> temp; | |
| 367 temp.set_size(size); | |
| 368 temp[0]=0; | |
| 369 if (GetEnvironmentVariable(name_t,temp.get_ptr(),size)>0) | |
| 370 { | |
| 371 out = stringcvt::string_utf8_from_os(temp.get_ptr(),size); | |
| 372 return TRUE; | |
| 373 } | |
| 374 } | |
| 375 return FALSE; | |
| 376 } | |
| 377 | |
| 378 HMODULE SHARED_EXPORT uGetModuleHandle(const char * name) | |
| 379 { | |
| 380 return GetModuleHandle(param_os_from_utf8(name)); | |
| 381 } | |
| 382 | |
| 383 UINT SHARED_EXPORT uRegisterWindowMessage(const char * name) | |
| 384 { | |
| 385 return RegisterWindowMessage(stringcvt::string_os_from_utf8(name)); | |
| 386 } | |
| 387 | |
| 388 BOOL SHARED_EXPORT uMoveFile(const char * src,const char * dst) | |
| 389 { | |
| 390 return MoveFile(stringcvt::string_os_from_utf8(src),stringcvt::string_os_from_utf8(dst)); | |
| 391 } | |
| 392 | |
| 393 BOOL SHARED_EXPORT uDeleteFile(const char * fn) | |
| 394 { | |
| 395 return DeleteFile(stringcvt::string_os_from_utf8(fn)); | |
| 396 } | |
| 397 | |
| 398 DWORD SHARED_EXPORT uGetFileAttributes(const char * fn) | |
| 399 { | |
| 400 PFC_ASSERT( ! pfc::string_has_prefix_i( fn, "file://" ) ); | |
| 401 return GetFileAttributes(stringcvt::string_os_from_utf8(fn)); | |
| 402 } | |
| 403 | |
| 404 BOOL SHARED_EXPORT uRemoveDirectory(const char * fn) | |
| 405 { | |
| 406 return RemoveDirectory(stringcvt::string_os_from_utf8(fn)); | |
| 407 } | |
| 408 | |
| 409 HANDLE SHARED_EXPORT uCreateFile(const char * fn,DWORD access,DWORD share,LPSECURITY_ATTRIBUTES blah,DWORD creat,DWORD flags,HANDLE tmpl) | |
| 410 { | |
| 411 return CreateFile(stringcvt::string_os_from_utf8(fn),access,share,blah,creat,flags,tmpl); | |
| 412 } | |
| 413 | |
| 414 BOOL SHARED_EXPORT uCreateDirectory(const char * fn,LPSECURITY_ATTRIBUTES blah) | |
| 415 { | |
| 416 return CreateDirectory(stringcvt::string_os_from_utf8(fn),blah); | |
| 417 } | |
| 418 | |
| 419 HANDLE SHARED_EXPORT uCreateMutex(LPSECURITY_ATTRIBUTES blah,BOOL bInitialOwner,const char * name) | |
| 420 { | |
| 421 return name ? CreateMutex(blah,bInitialOwner,stringcvt::string_os_from_utf8(name)) : CreateMutex(blah,bInitialOwner,0); | |
| 422 } | |
| 423 | |
| 424 BOOL SHARED_EXPORT uGetFullPathName(const char * name,string_base & out) | |
| 425 { | |
| 426 stringcvt::string_os_from_utf8 name_os(name); | |
| 427 unsigned len = GetFullPathName(name_os,0,0,0); | |
| 428 if (len==0) return FALSE; | |
| 429 array_t<TCHAR> temp; | |
| 430 temp.set_size(len+1); | |
| 431 TCHAR * blah; | |
| 432 if (GetFullPathName(name_os,len+1,temp.get_ptr(),&blah)==0) return FALSE; | |
| 433 out = stringcvt::string_utf8_from_os(temp.get_ptr(),len); | |
| 434 return TRUE; | |
| 435 } | |
| 436 | |
| 437 BOOL SHARED_EXPORT uGetLongPathName(const char * name,string_base & out) | |
| 438 { | |
| 439 TCHAR temp[4096]; | |
| 440 temp[0]=0; | |
| 441 BOOL state = GetLongPathName(stringcvt::string_os_from_utf8(name),temp,_countof(temp)); | |
| 442 if (state) out = stringcvt::string_utf8_from_os(temp,_countof(temp)); | |
| 443 return state; | |
| 444 } | |
| 445 | |
| 446 void SHARED_EXPORT uGetCommandLine(string_base & out) | |
| 447 { | |
| 448 out = stringcvt::string_utf8_from_os(GetCommandLine()); | |
| 449 } | |
| 450 | |
| 451 BOOL SHARED_EXPORT uGetTempPath(string_base & out) | |
| 452 { | |
| 453 TCHAR temp[MAX_PATH+1]; | |
| 454 temp[0]=0; | |
| 455 if (GetTempPath(_countof(temp),temp)) | |
| 456 { | |
| 457 out = stringcvt::string_utf8_from_os(temp,_countof(temp)); | |
| 458 return TRUE; | |
| 459 } | |
| 460 return FALSE; | |
| 461 | |
| 462 } | |
| 463 BOOL SHARED_EXPORT uGetTempFileName(const char * path_name,const char * prefix,UINT unique,string_base & out) | |
| 464 { | |
| 465 if (path_name==0 || prefix==0) return FALSE; | |
| 466 TCHAR temp[MAX_PATH+1]; | |
| 467 temp[0]=0; | |
| 468 if (GetTempFileName(stringcvt::string_os_from_utf8(path_name),stringcvt::string_os_from_utf8(prefix),unique,temp)) | |
| 469 { | |
| 470 out = stringcvt::string_utf8_from_os(temp,_countof(temp)); | |
| 471 return TRUE; | |
| 472 } | |
| 473 return FALSE; | |
| 474 } | |
| 475 | |
| 476 class uFindFile_i : public uFindFile | |
| 477 { | |
| 478 string8 fn; | |
| 479 WIN32_FIND_DATA fd; | |
| 480 HANDLE hFF; | |
| 481 public: | |
| 482 uFindFile_i() {hFF = INVALID_HANDLE_VALUE;} | |
| 483 bool FindFirst(const char * path) | |
| 484 { | |
| 485 hFF = FindFirstFile(stringcvt::string_os_from_utf8(path),&fd); | |
| 486 if (hFF==INVALID_HANDLE_VALUE) return false; | |
| 487 fn = stringcvt::string_utf8_from_os(fd.cFileName,_countof(fd.cFileName)); | |
| 488 return true; | |
| 489 } | |
| 490 virtual BOOL FindNext() | |
| 491 { | |
| 492 if (hFF==INVALID_HANDLE_VALUE) return FALSE; | |
| 493 BOOL rv = FindNextFile(hFF,&fd); | |
| 494 if (rv) fn = stringcvt::string_utf8_from_os(fd.cFileName,_countof(fd.cFileName)); | |
| 495 return rv; | |
| 496 } | |
| 497 | |
| 498 virtual const char * GetFileName() | |
| 499 { | |
| 500 return fn; | |
| 501 } | |
| 502 | |
| 503 virtual t_uint64 GetFileSize() | |
| 504 { | |
| 505 union | |
| 506 { | |
| 507 t_uint64 val64; | |
| 508 struct | |
| 509 { | |
| 510 DWORD lo,hi; | |
| 511 }; | |
| 512 } ret; | |
| 513 | |
| 514 ret.hi = fd.nFileSizeHigh; | |
| 515 ret.lo = fd.nFileSizeLow; | |
| 516 return ret.val64; | |
| 517 | |
| 518 } | |
| 519 virtual DWORD GetAttributes() | |
| 520 { | |
| 521 return fd.dwFileAttributes; | |
| 522 } | |
| 523 | |
| 524 virtual FILETIME GetCreationTime() | |
| 525 { | |
| 526 return fd.ftCreationTime; | |
| 527 } | |
| 528 virtual FILETIME GetLastAccessTime() | |
| 529 { | |
| 530 return fd.ftLastAccessTime; | |
| 531 } | |
| 532 virtual FILETIME GetLastWriteTime() | |
| 533 { | |
| 534 return fd.ftLastWriteTime; | |
| 535 } | |
| 536 virtual ~uFindFile_i() | |
| 537 { | |
| 538 if (hFF!=INVALID_HANDLE_VALUE) FindClose(hFF); | |
| 539 } | |
| 540 }; | |
| 541 | |
| 542 puFindFile SHARED_EXPORT uFindFirstFile(const char * path) | |
| 543 { | |
| 544 pfc::ptrholder_t<uFindFile_i> ptr = new uFindFile_i; | |
| 545 if (!ptr->FindFirst(path)) { | |
| 546 ptr.release(); | |
| 547 return NULL; | |
| 548 } else { | |
| 549 return ptr.detach(); | |
| 550 } | |
| 551 } | |
| 552 | |
| 553 HINSTANCE SHARED_EXPORT uShellExecute(HWND wnd,const char * oper,const char * file,const char * params,const char * dir,int cmd) | |
| 554 { | |
| 555 modal_dialog_scope modal; // IDIOCY - ShellExecute may spawn a modal dialog | |
| 556 if (wnd) modal.initialize(wnd); | |
| 557 return ShellExecute(wnd,param_os_from_utf8(oper),param_os_from_utf8(file),param_os_from_utf8(params),param_os_from_utf8(dir),cmd); | |
| 558 } | |
| 559 | |
| 560 HWND SHARED_EXPORT uCreateStatusWindow(LONG style,const char * text,HWND parent,UINT id) | |
| 561 { | |
| 562 return CreateStatusWindow(style,param_os_from_utf8(text),parent,id); | |
| 563 } | |
| 564 | |
| 565 HWND SHARED_EXPORT uCreateWindowEx(DWORD dwExStyle,const char * lpClassName,const char * lpWindowName,DWORD dwStyle,int x,int y,int nWidth,int nHeight,HWND hWndParent,HMENU hMenu,HINSTANCE hInstance,LPVOID lpParam) | |
| 566 { | |
| 567 return CreateWindowEx(dwExStyle,param_os_from_utf8(lpClassName),param_os_from_utf8(lpWindowName),dwStyle,x,y,nWidth,nHeight,hWndParent,hMenu,hInstance,lpParam); | |
| 568 } | |
| 569 | |
| 570 HANDLE SHARED_EXPORT uLoadImage(HINSTANCE hIns,const char * name,UINT type,int x,int y,UINT flags) | |
| 571 { | |
| 572 return LoadImage(hIns,param_os_from_utf8(name),type,x,y,flags); | |
| 573 } | |
| 574 | |
| 575 BOOL SHARED_EXPORT uGetSystemDirectory(string_base & out) | |
| 576 { | |
| 577 UINT len = GetSystemDirectory(0,0); | |
| 578 if (len==0) len = MAX_PATH; | |
| 579 len++; | |
| 580 array_t<TCHAR> temp; | |
| 581 temp.set_size(len); | |
| 582 if (GetSystemDirectory(temp.get_ptr(),len)==0) return FALSE; | |
| 583 out = stringcvt::string_utf8_from_os(temp.get_ptr(),len); | |
| 584 return TRUE; | |
| 585 } | |
| 586 | |
| 587 BOOL SHARED_EXPORT uGetWindowsDirectory(string_base & out) | |
| 588 { | |
| 589 UINT len = GetWindowsDirectory(0,0); | |
| 590 if (len==0) len = MAX_PATH; | |
| 591 len++; | |
| 592 array_t<TCHAR> temp; | |
| 593 temp.set_size(len); | |
| 594 if (GetWindowsDirectory(temp.get_ptr(),len)==0) return FALSE; | |
| 595 out = stringcvt::string_utf8_from_os(temp.get_ptr(),len); | |
| 596 return TRUE; | |
| 597 } | |
| 598 | |
| 599 BOOL SHARED_EXPORT uSetCurrentDirectory(const char * path) | |
| 600 { | |
| 601 return SetCurrentDirectory(stringcvt::string_os_from_utf8(path)); | |
| 602 } | |
| 603 | |
| 604 BOOL SHARED_EXPORT uGetCurrentDirectory(string_base & out) | |
| 605 { | |
| 606 UINT len = GetCurrentDirectory(0,0); | |
| 607 if (len==0) len = MAX_PATH; | |
| 608 len++; | |
| 609 array_t<TCHAR> temp; | |
| 610 temp.set_size(len); | |
| 611 if (GetCurrentDirectory(len,temp.get_ptr())==0) return FALSE; | |
| 612 out = stringcvt::string_utf8_from_os(temp.get_ptr(),len); | |
| 613 return TRUE; | |
| 614 } | |
| 615 | |
| 616 BOOL SHARED_EXPORT uExpandEnvironmentStrings(const char * src,string_base & out) | |
| 617 { | |
| 618 stringcvt::string_os_from_utf8 src_os(src); | |
| 619 UINT len = ExpandEnvironmentStrings(src_os,0,0); | |
| 620 if (len==0) len = 256; | |
| 621 len++; | |
| 622 array_t<TCHAR> temp; | |
| 623 temp.set_size(len); | |
| 624 if (ExpandEnvironmentStrings(src_os,temp.get_ptr(),len)==0) return FALSE; | |
| 625 out = stringcvt::string_utf8_from_os(temp.get_ptr(),len); | |
| 626 return TRUE; | |
| 627 } | |
| 628 | |
| 629 BOOL SHARED_EXPORT uGetUserName(string_base & out) | |
| 630 { | |
| 631 TCHAR temp[UNLEN+1]; | |
| 632 DWORD len = _countof(temp); | |
| 633 if (GetUserName(temp,&len)) | |
| 634 { | |
| 635 out = stringcvt::string_utf8_from_os(temp,_countof(temp)); | |
| 636 return TRUE; | |
| 637 } | |
| 638 else return FALSE; | |
| 639 } | |
| 640 | |
| 641 BOOL SHARED_EXPORT uGetShortPathName(const char * src,string_base & out) | |
| 642 { | |
| 643 stringcvt::string_os_from_utf8 src_os(src); | |
| 644 UINT len = GetShortPathName(src_os,0,0); | |
| 645 if (len==0) len = MAX_PATH; | |
| 646 len++; | |
| 647 array_t<TCHAR> temp; temp.set_size(len); | |
| 648 if (GetShortPathName(src_os,temp.get_ptr(),len)) | |
| 649 { | |
| 650 out = stringcvt::string_utf8_from_os(temp.get_ptr(),len); | |
| 651 return TRUE; | |
| 652 } | |
| 653 else return FALSE; | |
| 654 } | |
| 655 | |
| 656 | |
| 657 #ifdef UNICODE | |
| 658 #define DDE_CODEPAGE CP_WINUNICODE | |
| 659 #else | |
| 660 #define DDE_CODEPAGE CP_WINANSI | |
| 661 #endif | |
| 662 | |
| 663 | |
| 664 HSZ SHARED_EXPORT uDdeCreateStringHandle(DWORD ins,const char * src) | |
| 665 { | |
| 666 return DdeCreateStringHandle(ins,stringcvt::string_os_from_utf8(src),DDE_CODEPAGE); | |
| 667 } | |
| 668 | |
| 669 BOOL SHARED_EXPORT uDdeQueryString(DWORD ins,HSZ hsz,string_base & out) | |
| 670 { | |
| 671 array_t<TCHAR> temp; | |
| 672 UINT len = DdeQueryString(ins,hsz,0,0,DDE_CODEPAGE); | |
| 673 if (len==0) len = MAX_PATH; | |
| 674 len++; | |
| 675 temp.set_size(len); | |
| 676 if (DdeQueryString(ins,hsz,temp.get_ptr(),len,DDE_CODEPAGE)) | |
| 677 { | |
| 678 out = stringcvt::string_utf8_from_os(temp.get_ptr(),len); | |
| 679 return TRUE; | |
| 680 } | |
| 681 else return FALSE; | |
| 682 } | |
| 683 | |
| 684 UINT SHARED_EXPORT uDdeInitialize(LPDWORD pidInst,PFNCALLBACK pfnCallback,DWORD afCmd,DWORD ulRes) | |
| 685 { | |
| 686 return DdeInitialize(pidInst,pfnCallback,afCmd,ulRes); | |
| 687 } | |
| 688 | |
| 689 BOOL SHARED_EXPORT uDdeAccessData_Text(HDDEDATA data,string_base & out) | |
| 690 { | |
| 691 const TCHAR * ptr = (const TCHAR*) DdeAccessData(data,0); | |
| 692 if (ptr) | |
| 693 { | |
| 694 out = stringcvt::string_utf8_from_os(ptr); | |
| 695 return TRUE; | |
| 696 } | |
| 697 else return FALSE; | |
| 698 } | |
| 699 | |
| 700 uSortString_t SHARED_EXPORT uSortStringCreate(const char * src) { | |
| 701 t_size lenEst = pfc::stringcvt::estimate_utf8_to_wide(src,SIZE_MAX); | |
| 702 TCHAR * ret = pfc::__raw_malloc_t<TCHAR>(lenEst); | |
| 703 pfc::stringcvt::convert_utf8_to_wide(ret,lenEst,src,SIZE_MAX); | |
| 704 return reinterpret_cast<uSortString_t>( ret ); | |
| 705 } | |
| 706 | |
| 707 int SHARED_EXPORT uSortStringCompareEx(uSortString_t string1, uSortString_t string2,uint32_t flags) { | |
| 708 return CompareString(LOCALE_USER_DEFAULT,flags,reinterpret_cast<const TCHAR*>(string1),-1,reinterpret_cast<const TCHAR*>(string2),-1); | |
| 709 } | |
| 710 | |
| 711 int SHARED_EXPORT uSortStringCompare(uSortString_t string1, uSortString_t string2) { | |
| 712 return lstrcmpi(reinterpret_cast<const TCHAR*>(string1),reinterpret_cast<const TCHAR*>(string2)); | |
| 713 } | |
| 714 | |
| 715 void SHARED_EXPORT uSortStringFree(uSortString_t string) { | |
| 716 pfc::__raw_free_t(reinterpret_cast<TCHAR*>(string)); | |
| 717 } | |
| 718 | |
| 719 HTREEITEM SHARED_EXPORT uTreeView_InsertItem(HWND wnd,const uTVINSERTSTRUCT * param) | |
| 720 { | |
| 721 stringcvt::string_os_from_utf8 temp; | |
| 722 temp.convert(param->item.pszText); | |
| 723 | |
| 724 | |
| 725 TVINSERTSTRUCT l_param = {}; | |
| 726 l_param.hParent = param->hParent; | |
| 727 l_param.hInsertAfter = param->hInsertAfter; | |
| 728 l_param.item.mask = param->item.mask; | |
| 729 l_param.item.hItem = param->item.hItem; | |
| 730 l_param.item.state = param->item.state; | |
| 731 l_param.item.stateMask = param->item.stateMask; | |
| 732 l_param.item.pszText = const_cast<TCHAR*>(temp.get_ptr()); | |
| 733 l_param.item.cchTextMax = 0; | |
| 734 l_param.item.iImage = param->item.iImage; | |
| 735 l_param.item.iSelectedImage = param->item.iImage; | |
| 736 l_param.item.cChildren = param->item.cChildren; | |
| 737 l_param.item.lParam = param->item.lParam; | |
| 738 if (param->item.mask & TVIF_INTEGRAL) | |
| 739 { | |
| 740 l_param.itemex.iIntegral = param->itemex.iIntegral; | |
| 741 } | |
| 742 | |
| 743 return (HTREEITEM) uSendMessage(wnd,TVM_INSERTITEM,0,(LPARAM)&l_param); | |
| 744 } | |
| 745 | |
| 746 UINT SHARED_EXPORT uGetFontHeight(HFONT font) | |
| 747 { | |
| 748 UINT ret; | |
| 749 HDC dc = CreateCompatibleDC(0); | |
| 750 SelectObject(dc,font); | |
| 751 ret = uGetTextHeight(dc); | |
| 752 DeleteDC(dc); | |
| 753 return ret; | |
| 754 } | |
| 755 | |
| 756 | |
| 757 HIMAGELIST SHARED_EXPORT uImageList_LoadImage(HINSTANCE hi, const char * lpbmp, int cx, int cGrow, COLORREF crMask, UINT uType, UINT uFlags) | |
| 758 { | |
| 759 return ImageList_LoadImage(hi,param_os_from_utf8(lpbmp),cx,cGrow,crMask,uType,uFlags); | |
| 760 } | |
| 761 | |
| 762 int SHARED_EXPORT uTabCtrl_InsertItem(HWND wnd,t_size idx,const uTCITEM * item) | |
| 763 { | |
| 764 param_os_from_utf8 text((item->mask & TCIF_TEXT) ? item->pszText : 0); | |
| 765 TCITEM l_item; | |
| 766 assert(sizeof(l_item)==sizeof(*item));//meh lazy | |
| 767 memcpy(&l_item,item,sizeof(l_item)); | |
| 768 l_item.pszText = const_cast<TCHAR*>(text.get_ptr()); | |
| 769 l_item.cchTextMax = 0; | |
| 770 return TabCtrl_InsertItem(wnd,idx,&l_item); | |
| 771 } | |
| 772 | |
| 773 int SHARED_EXPORT uTabCtrl_SetItem(HWND wnd,t_size idx,const uTCITEM * item) | |
| 774 { | |
| 775 param_os_from_utf8 text((item->mask & TCIF_TEXT) ? item->pszText : 0); | |
| 776 TCITEM l_item; | |
| 777 PFC_STATIC_ASSERT(sizeof(l_item)==sizeof(*item));//meh lazy | |
| 778 memcpy(&l_item,item,sizeof(l_item)); | |
| 779 l_item.pszText = const_cast<TCHAR*>(text.get_ptr()); | |
| 780 l_item.cchTextMax = 0; | |
| 781 return TabCtrl_SetItem(wnd,idx,&l_item); | |
| 782 } | |
| 783 | |
| 784 int SHARED_EXPORT uGetKeyNameText(LONG lparam,string_base & out) | |
| 785 { | |
| 786 TCHAR temp[256]; | |
| 787 temp[0]=0; | |
| 788 if (!GetKeyNameText(lparam,temp,_countof(temp))) return 0; | |
| 789 out = stringcvt::string_utf8_from_os(temp,_countof(temp)); | |
| 790 return 1; | |
| 791 } | |
| 792 | |
| 793 HANDLE SHARED_EXPORT uCreateFileMapping(HANDLE hFile,LPSECURITY_ATTRIBUTES lpFileMappingAttributes,DWORD flProtect,DWORD dwMaximumSizeHigh,DWORD dwMaximumSizeLow,const char * lpName) | |
| 794 { | |
| 795 return CreateFileMapping(hFile,lpFileMappingAttributes,flProtect,dwMaximumSizeHigh,dwMaximumSizeLow,param_os_from_utf8(lpName)); | |
| 796 } | |
| 797 | |
| 798 BOOL SHARED_EXPORT uListBox_GetText(HWND listbox,UINT index,string_base & out) | |
| 799 { | |
| 800 t_size len = uSendMessage(listbox,LB_GETTEXTLEN,index,0); | |
| 801 if (len==LB_ERR || len>16*1024*1024) return FALSE; | |
| 802 if (len==0) {out.reset();return TRUE;} | |
| 803 | |
| 804 array_t<TCHAR> temp; temp.set_size(len+1); | |
| 805 pfc::memset_t(temp,(TCHAR)0); | |
| 806 len = uSendMessage(listbox,LB_GETTEXT,index,(LPARAM)temp.get_ptr()); | |
| 807 if (len==LB_ERR) return false; | |
| 808 out = stringcvt::string_utf8_from_os(temp.get_ptr()); | |
| 809 return TRUE; | |
| 810 } | |
| 811 /* | |
| 812 void SHARED_EXPORT uPrintf(string_base & out,const char * fmt,...) | |
| 813 { | |
| 814 va_list list; | |
| 815 va_start(list,fmt); | |
| 816 uPrintfV(out,fmt,list); | |
| 817 va_end(list); | |
| 818 } | |
| 819 */ | |
| 820 void SHARED_EXPORT uPrintfV(string_base & out,const char * fmt,va_list arglist) | |
| 821 { | |
| 822 pfc::string_printf_here_va(out, fmt, arglist); | |
| 823 } | |
| 824 | |
| 825 int SHARED_EXPORT uCompareString(DWORD flags,const char * str1,size_t len1,const char * str2,size_t len2) | |
| 826 { | |
| 827 return CompareString(LOCALE_USER_DEFAULT,flags,stringcvt::string_os_from_utf8(str1,len1),-1,stringcvt::string_os_from_utf8(str2,len2),-1); | |
| 828 } | |
| 829 | |
| 830 class uResource_i : public uResource | |
| 831 { | |
| 832 unsigned size; | |
| 833 const void * ptr; | |
| 834 public: | |
| 835 inline uResource_i(const void * p_ptr,unsigned p_size) : ptr(p_ptr), size(p_size) | |
| 836 { | |
| 837 } | |
| 838 virtual const void * GetPointer() | |
| 839 { | |
| 840 return ptr; | |
| 841 } | |
| 842 virtual unsigned GetSize() | |
| 843 { | |
| 844 return size; | |
| 845 } | |
| 846 virtual ~uResource_i() | |
| 847 { | |
| 848 } | |
| 849 }; | |
| 850 | |
| 851 puResource SHARED_EXPORT uLoadResource(HMODULE hMod,const char * name,const char * type,WORD wLang) | |
| 852 { | |
| 853 HRSRC res = uFindResource(hMod,name,type,wLang); | |
| 854 if (res==0) return 0; | |
| 855 HGLOBAL hglob = LoadResource(hMod,res); | |
| 856 if (hglob) | |
| 857 { | |
| 858 void * ptr = LockResource(hglob); | |
| 859 if (ptr) | |
| 860 { | |
| 861 return new uResource_i(ptr,SizeofResource(hMod,res)); | |
| 862 } | |
| 863 else return 0; | |
| 864 } | |
| 865 else return 0; | |
| 866 } | |
| 867 | |
| 868 puResource SHARED_EXPORT LoadResourceEx(HMODULE hMod,const TCHAR * name,const TCHAR * type,WORD wLang) | |
| 869 { | |
| 870 HRSRC res = wLang ? FindResourceEx(hMod,type,name,wLang) : FindResource(hMod,name,type); | |
| 871 if (res==0) return 0; | |
| 872 HGLOBAL hglob = LoadResource(hMod,res); | |
| 873 if (hglob) | |
| 874 { | |
| 875 void * ptr = LockResource(hglob); | |
| 876 if (ptr) | |
| 877 { | |
| 878 return new uResource_i(ptr,SizeofResource(hMod,res)); | |
| 879 } | |
| 880 else return 0; | |
| 881 } | |
| 882 else return 0; | |
| 883 } | |
| 884 | |
| 885 HRSRC SHARED_EXPORT uFindResource(HMODULE hMod,const char * name,const char * type,WORD wLang) | |
| 886 { | |
| 887 return wLang ? FindResourceEx(hMod,param_os_from_utf8(type),param_os_from_utf8(name),wLang) : FindResource(hMod,param_os_from_utf8(name),param_os_from_utf8(type)); | |
| 888 } | |
| 889 | |
| 890 BOOL SHARED_EXPORT uLoadString(HINSTANCE ins,UINT id,string_base & out) | |
| 891 { | |
| 892 BOOL rv = FALSE; | |
| 893 uResource * res = uLoadResource(ins,uMAKEINTRESOURCE(id),(const char*)(RT_STRING)); | |
| 894 if (res) | |
| 895 { | |
| 896 unsigned size = res->GetSize(); | |
| 897 const WCHAR * ptr = (const WCHAR*)res->GetPointer(); | |
| 898 if (size>=4) | |
| 899 { | |
| 900 unsigned len = *(const WORD*)(ptr+1); | |
| 901 if (len * 2 + 4 <= size) | |
| 902 { | |
| 903 out = stringcvt::string_utf8_from_wide(ptr+2,len); | |
| 904 } | |
| 905 } | |
| 906 | |
| 907 delete res; | |
| 908 rv = TRUE; | |
| 909 } | |
| 910 return rv; | |
| 911 } | |
| 912 | |
| 913 BOOL SHARED_EXPORT uGetMenuString(HMENU menu,UINT id,string_base & out,UINT flag) | |
| 914 { | |
| 915 unsigned len = GetMenuString(menu,id,0,0,flag); | |
| 916 if (len==0) | |
| 917 { | |
| 918 out.reset(); | |
| 919 return FALSE; | |
| 920 } | |
| 921 array_t<TCHAR> temp; | |
| 922 temp.set_size(len+1); | |
| 923 if (GetMenuString(menu,id,temp.get_ptr(),len+1,flag)==0) { | |
| 924 out.reset(); | |
| 925 return FALSE; | |
| 926 } | |
| 927 out = stringcvt::string_utf8_from_os(temp.get_ptr()); | |
| 928 return TRUE; | |
| 929 } | |
| 930 | |
| 931 BOOL SHARED_EXPORT uModifyMenu(HMENU menu,UINT id,UINT flags,UINT newitem,const char * data) | |
| 932 { | |
| 933 return ModifyMenu(menu,id,flags,newitem,param_os_from_utf8(data)); | |
| 934 } | |
| 935 | |
| 936 UINT SHARED_EXPORT uGetMenuItemType(HMENU menu,UINT position) | |
| 937 { | |
| 938 MENUITEMINFO info = {}; | |
| 939 info.cbSize = sizeof(info); | |
| 940 info.fMask = MIIM_TYPE; | |
| 941 if (!GetMenuItemInfo(menu,position,TRUE,&info)) | |
| 942 return 0; | |
| 943 return info.fType; | |
| 944 } | |
| 945 | |
| 946 static inline bool i_is_path_separator(unsigned c) | |
| 947 { | |
| 948 return c=='\\' || c=='/' || c=='|' || c==':'; | |
| 949 } | |
| 950 | |
| 951 int SHARED_EXPORT uSortPathCompare(HANDLE string1,HANDLE string2) | |
| 952 { | |
| 953 const TCHAR * s1 = reinterpret_cast<const TCHAR*>(string1); | |
| 954 const TCHAR * s2 = reinterpret_cast<const TCHAR*>(string2); | |
| 955 const TCHAR * p1, * p2; | |
| 956 | |
| 957 while (*s1 || *s2) | |
| 958 { | |
| 959 if (*s1 == *s2) | |
| 960 { | |
| 961 s1++; | |
| 962 s2++; | |
| 963 continue; | |
| 964 } | |
| 965 | |
| 966 p1 = s1; while (*p1 && !i_is_path_separator(*p1)) p1++; | |
| 967 p2 = s2; while (*p2 && !i_is_path_separator(*p2)) p2++; | |
| 968 | |
| 969 if ((!*p1 && !*p2) || (*p1 && *p2)) | |
| 970 { | |
| 971 int test = CompareString(LOCALE_USER_DEFAULT, NORM_IGNORECASE | NORM_IGNOREKANATYPE | NORM_IGNOREWIDTH, s1, pfc::downcast_guarded<int>(p1 - s1), s2, pfc::downcast_guarded<int>(p2 - s2)); | |
| 972 if (test && test != 2) return test - 2; | |
| 973 if (!*p1) return 0; | |
| 974 } | |
| 975 else | |
| 976 { | |
| 977 if (*p1) return -1; | |
| 978 else return 1; | |
| 979 } | |
| 980 | |
| 981 s1 = p1 + 1; | |
| 982 s2 = p2 + 1; | |
| 983 } | |
| 984 | |
| 985 return 0; | |
| 986 } | |
| 987 | |
| 988 UINT SHARED_EXPORT uRegisterClipboardFormat(const char * name) | |
| 989 { | |
| 990 return RegisterClipboardFormat(stringcvt::string_os_from_utf8(name)); | |
| 991 } | |
| 992 | |
| 993 BOOL SHARED_EXPORT uGetClipboardFormatName(UINT format,string_base & out) | |
| 994 { | |
| 995 TCHAR temp[1024]; | |
| 996 if (!GetClipboardFormatName(format,temp,_countof(temp))) return FALSE; | |
| 997 out = stringcvt::string_utf8_from_os(temp,_countof(temp)); | |
| 998 return TRUE; | |
| 999 } | |
| 1000 | |
| 1001 }//extern "C" | |
| 1002 | |
| 1003 BOOL SHARED_EXPORT uSearchPath(const char * path, const char * filename, const char * extension, string_base & p_out) | |
| 1004 { | |
| 1005 enum {temp_size = 1024}; | |
| 1006 param_os_from_utf8 path_os(path), filename_os(filename), extension_os(extension); | |
| 1007 array_t<TCHAR> temp; temp.set_size(temp_size); | |
| 1008 LPTSTR dummy; | |
| 1009 unsigned len; | |
| 1010 | |
| 1011 len = SearchPath(path_os,filename_os,extension_os,temp_size,temp.get_ptr(),&dummy); | |
| 1012 if (len == 0) return FALSE; | |
| 1013 if (len >= temp_size) | |
| 1014 { | |
| 1015 unsigned len2; | |
| 1016 temp.set_size(len + 1); | |
| 1017 len2 = SearchPath(path_os,filename_os,extension_os,len+1,temp.get_ptr(),&dummy); | |
| 1018 if (len2 == 0 || len2 > len) return FALSE; | |
| 1019 len = len2; | |
| 1020 } | |
| 1021 | |
| 1022 p_out = stringcvt::string_utf8_from_os(temp.get_ptr(),len); | |
| 1023 | |
| 1024 return TRUE; | |
| 1025 | |
| 1026 } | |
| 1027 | |
| 1028 static bool is_ascii_alpha(char c) | |
| 1029 { | |
| 1030 return (c >= 'a' && c <= 'z') || (c >= 'A' && c <= 'Z'); | |
| 1031 } | |
| 1032 | |
| 1033 static char ascii_upper(char c) | |
| 1034 { | |
| 1035 if (c >= 'a' && c <= 'z') c += 'A' - 'a'; | |
| 1036 return c; | |
| 1037 } | |
| 1038 | |
| 1039 static BOOL uFixPathCaps_Internal(const char * path,string_base & p_out, bool bQuick) { | |
| 1040 pfc::string8_fastalloc temp, prependbuffer; | |
| 1041 if (path[0] == '\\' && path[1] == '\\') | |
| 1042 { | |
| 1043 unsigned index = 2; | |
| 1044 while(path[index] != '\\') | |
| 1045 { | |
| 1046 if (path[index] == 0) return FALSE; | |
| 1047 index++; | |
| 1048 } | |
| 1049 index++; | |
| 1050 if (path[index] == '\\' || path[index] == 0) return FALSE; | |
| 1051 while(path[index] != '\\') | |
| 1052 { | |
| 1053 if (path[index] == 0) { | |
| 1054 // \\host\share | |
| 1055 uStringLower(p_out,path); | |
| 1056 return TRUE; | |
| 1057 } | |
| 1058 index++; | |
| 1059 } | |
| 1060 index++; | |
| 1061 if (path[index] == '\\') return FALSE; | |
| 1062 uAddStringLower(temp,path,index); | |
| 1063 path += index; | |
| 1064 } | |
| 1065 else if (is_ascii_alpha(path[0]) && path[1] == ':' && path[2] == '\\') | |
| 1066 { | |
| 1067 temp.add_char(ascii_upper(path[0])); | |
| 1068 temp.add_string(":\\"); | |
| 1069 path += 3; | |
| 1070 } | |
| 1071 else return FALSE; | |
| 1072 | |
| 1073 for(;;) | |
| 1074 { | |
| 1075 t_size truncat = temp.length(); | |
| 1076 t_size delta = 0; | |
| 1077 while(path[delta]!=0 && path[delta]!='\\') delta++; | |
| 1078 if (delta == 0) break; | |
| 1079 temp.add_string_nc(path,delta); | |
| 1080 | |
| 1081 bool found = false; | |
| 1082 if (!bQuick) { | |
| 1083 #ifdef UNICODE | |
| 1084 pfc::winPrefixPath( prependbuffer, temp ); | |
| 1085 pfc::ptrholder_t<uFindFile> ff = uFindFirstFile(prependbuffer); | |
| 1086 #else | |
| 1087 pfc::ptrholder_t<uFindFile> ff = uFindFirstFile(temp); | |
| 1088 #endif | |
| 1089 if (ff.is_valid()) { | |
| 1090 do { | |
| 1091 const char * fn = ff->GetFileName(); | |
| 1092 if (!stricmp_utf8_ex(path,delta,fn,strlen(fn))) | |
| 1093 { | |
| 1094 found = true; | |
| 1095 temp.truncate(truncat); | |
| 1096 temp.add_string(fn); | |
| 1097 break; | |
| 1098 } | |
| 1099 } while(ff->FindNext()); | |
| 1100 } | |
| 1101 } | |
| 1102 if (!found) | |
| 1103 { | |
| 1104 temp.add_string(path + delta); | |
| 1105 break; | |
| 1106 } | |
| 1107 path += delta; | |
| 1108 if (*path == 0) break; | |
| 1109 path ++; | |
| 1110 temp.add_char('\\'); | |
| 1111 } | |
| 1112 | |
| 1113 | |
| 1114 p_out = temp; | |
| 1115 | |
| 1116 return TRUE; | |
| 1117 } | |
| 1118 /*BOOL SHARED_EXPORT uFixPathCapsQuick(const char * path,string_base & p_out) { | |
| 1119 return uFixPathCaps_Internal(path, p_out, true); | |
| 1120 }*/ | |
| 1121 BOOL SHARED_EXPORT uFixPathCaps(const char * path,string_base & p_out) { | |
| 1122 return uFixPathCaps_Internal(path, p_out, false); | |
| 1123 } | |
| 1124 | |
| 1125 LPARAM SHARED_EXPORT uTreeView_GetUserData(HWND p_tree,HTREEITEM p_item) | |
| 1126 { | |
| 1127 TVITEM item = {}; | |
| 1128 item.mask = TVIF_PARAM; | |
| 1129 item.hItem = p_item; | |
| 1130 if (uSendMessage(p_tree,TVM_GETITEM,0,(LPARAM)&item)) | |
| 1131 return item.lParam; | |
| 1132 return 0; | |
| 1133 } | |
| 1134 | |
| 1135 bool SHARED_EXPORT uTreeView_GetText(HWND p_tree,HTREEITEM p_item,string_base & p_out) | |
| 1136 { | |
| 1137 TCHAR temp[1024];//changeme ? | |
| 1138 TVITEM item = {}; | |
| 1139 item.mask = TVIF_TEXT; | |
| 1140 item.hItem = p_item; | |
| 1141 item.pszText = temp; | |
| 1142 item.cchTextMax = _countof(temp); | |
| 1143 if (uSendMessage(p_tree,TVM_GETITEM,0,(LPARAM)&item)) | |
| 1144 { | |
| 1145 p_out = stringcvt::string_utf8_from_os(temp,_countof(temp)); | |
| 1146 return true; | |
| 1147 } | |
| 1148 else return false; | |
| 1149 } | |
| 1150 | |
| 1151 BOOL SHARED_EXPORT uSetWindowText(HWND wnd,const char * p_text) | |
| 1152 { | |
| 1153 PFC_ASSERT( wnd != NULL ); | |
| 1154 return SetWindowText(wnd,stringcvt::string_os_from_utf8(p_text)); | |
| 1155 } | |
| 1156 | |
| 1157 BOOL SHARED_EXPORT uSetDlgItemText(HWND wnd,UINT id,const char * p_text) | |
| 1158 { | |
| 1159 PFC_ASSERT( wnd != NULL ); | |
| 1160 return SetDlgItemText(wnd, id, stringcvt::string_os_from_utf8(p_text)); | |
| 1161 } | |
| 1162 | |
| 1163 BOOL SHARED_EXPORT uFileExists(const char * fn) | |
| 1164 { | |
| 1165 DWORD attrib = uGetFileAttributes(fn); | |
| 1166 if (attrib == 0xFFFFFFFF || (attrib & FILE_ATTRIBUTE_DIRECTORY)) return FALSE; | |
| 1167 return TRUE; | |
| 1168 } | |
| 1169 | |
| 1170 BOOL SHARED_EXPORT uFormatSystemErrorMessage(string_base & p_out,DWORD p_code) { | |
| 1171 return pfc::winFormatSystemErrorMessage(p_out, p_code); | |
| 1172 } | |
| 1173 | |
| 1174 HMODULE SHARED_EXPORT LoadSystemLibrary(const TCHAR * name) { | |
| 1175 pfc::array_t<TCHAR> buffer; buffer.set_size( MAX_PATH + _tcslen(name) + 2 ); | |
| 1176 TCHAR * bufptr = buffer.get_ptr(); | |
| 1177 if (GetSystemDirectory(bufptr, MAX_PATH) == 0) return NULL; | |
| 1178 bufptr[MAX_PATH] = 0; | |
| 1179 | |
| 1180 size_t idx = _tcslen(bufptr); | |
| 1181 if (idx > 0 && bufptr[idx-1] != '\\') bufptr[idx++] = '\\'; | |
| 1182 | |
| 1183 pfc::strcpy_t(bufptr+idx, name); | |
| 1184 | |
| 1185 return LoadLibrary(bufptr); | |
| 1186 } |
