1
0
mirror of https://github.com/wolfpld/tracy synced 2025-04-29 04:23:51 +00:00

Update nfd to ceb75f7abf3.

This commit is contained in:
Bartosz Taudul 2019-06-23 00:35:19 +02:00
parent 815ad7df28
commit 6bdfedead2
3 changed files with 79 additions and 44 deletions

View File

@ -117,7 +117,7 @@ static nfdresult_t AllocPathSet( NSArray *urls, nfdpathset_t *pathset )
/* public */ /* public */
nfdresult_t NFD_OpenDialog( const char *filterList, nfdresult_t NFD_OpenDialog( const nfdchar_t *filterList,
const nfdchar_t *defaultPath, const nfdchar_t *defaultPath,
nfdchar_t **outPath ) nfdchar_t **outPath )
{ {
@ -146,6 +146,7 @@ nfdresult_t NFD_OpenDialog( const char *filterList,
if ( !*outPath ) if ( !*outPath )
{ {
[pool release]; [pool release];
[keyWindow makeKeyAndOrderFront:nil];
return NFD_ERROR; return NFD_ERROR;
} }
memcpy( *outPath, utf8Path, len+1 ); /* copy null term */ memcpy( *outPath, utf8Path, len+1 ); /* copy null term */
@ -163,6 +164,7 @@ nfdresult_t NFD_OpenDialogMultiple( const nfdchar_t *filterList,
nfdpathset_t *outPaths ) nfdpathset_t *outPaths )
{ {
NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init]; NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
NSWindow *keyWindow = [[NSApplication sharedApplication] keyWindow];
NSOpenPanel *dialog = [NSOpenPanel openPanel]; NSOpenPanel *dialog = [NSOpenPanel openPanel];
[dialog setAllowsMultipleSelection:YES]; [dialog setAllowsMultipleSelection:YES];
@ -181,12 +183,14 @@ nfdresult_t NFD_OpenDialogMultiple( const nfdchar_t *filterList,
if ( [urls count] == 0 ) if ( [urls count] == 0 )
{ {
[pool release]; [pool release];
[keyWindow makeKeyAndOrderFront:nil];
return NFD_CANCEL; return NFD_CANCEL;
} }
if ( AllocPathSet( urls, outPaths ) == NFD_ERROR ) if ( AllocPathSet( urls, outPaths ) == NFD_ERROR )
{ {
[pool release]; [pool release];
[keyWindow makeKeyAndOrderFront:nil];
return NFD_ERROR; return NFD_ERROR;
} }
@ -194,6 +198,7 @@ nfdresult_t NFD_OpenDialogMultiple( const nfdchar_t *filterList,
} }
[pool release]; [pool release];
[keyWindow makeKeyAndOrderFront:nil];
return nfdResult; return nfdResult;
} }
@ -203,7 +208,8 @@ nfdresult_t NFD_SaveDialog( const nfdchar_t *filterList,
nfdchar_t **outPath ) nfdchar_t **outPath )
{ {
NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init]; NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
NSWindow *keyWindow = [[NSApplication sharedApplication] keyWindow];
NSSavePanel *dialog = [NSSavePanel savePanel]; NSSavePanel *dialog = [NSSavePanel savePanel];
[dialog setExtensionHidden:NO]; [dialog setExtensionHidden:NO];
@ -225,6 +231,7 @@ nfdresult_t NFD_SaveDialog( const nfdchar_t *filterList,
if ( !*outPath ) if ( !*outPath )
{ {
[pool release]; [pool release];
[keyWindow makeKeyAndOrderFront:nil];
return NFD_ERROR; return NFD_ERROR;
} }
memcpy( *outPath, utf8Path, byteLen ); memcpy( *outPath, utf8Path, byteLen );
@ -232,7 +239,7 @@ nfdresult_t NFD_SaveDialog( const nfdchar_t *filterList,
} }
[pool release]; [pool release];
[keyWindow makeKeyAndOrderFront:nil];
return nfdResult; return nfdResult;
} }
@ -241,7 +248,7 @@ nfdresult_t NFD_PickFolder(const nfdchar_t *defaultPath,
{ {
NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init]; NSAutoreleasePool *pool = [[NSAutoreleasePool alloc] init];
NSWindow *keyWindow = [[NSApplication sharedApplication] keyWindow]; NSWindow *keyWindow = [[NSApplication sharedApplication] keyWindow];
NSOpenPanel *dialog = [NSOpenPanel openPanel]; NSOpenPanel *dialog = [NSOpenPanel openPanel];
[dialog setAllowsMultipleSelection:NO]; [dialog setAllowsMultipleSelection:NO];
[dialog setCanChooseDirectories:YES]; [dialog setCanChooseDirectories:YES];
@ -264,6 +271,7 @@ nfdresult_t NFD_PickFolder(const nfdchar_t *defaultPath,
if ( !*outPath ) if ( !*outPath )
{ {
[pool release]; [pool release];
[keyWindow makeKeyAndOrderFront:nil];
return NFD_ERROR; return NFD_ERROR;
} }
memcpy( *outPath, utf8Path, len+1 ); /* copy null term */ memcpy( *outPath, utf8Path, len+1 ); /* copy null term */

View File

@ -165,7 +165,7 @@ static void WaitForCleanup(void)
/* public */ /* public */
nfdresult_t NFD_OpenDialog( const char *filterList, nfdresult_t NFD_OpenDialog( const nfdchar_t *filterList,
const nfdchar_t *defaultPath, const nfdchar_t *defaultPath,
nfdchar_t **outPath ) nfdchar_t **outPath )
{ {

View File

@ -4,6 +4,10 @@
http://www.frogtoss.com/labs http://www.frogtoss.com/labs
*/ */
#define _CRTDBG_MAP_ALLOC
#include <stdlib.h>
#include <crtdbg.h>
/* only locally define UNICODE in this compilation unit */ /* only locally define UNICODE in this compilation unit */
#ifndef UNICODE #ifndef UNICODE
#define UNICODE #define UNICODE
@ -21,7 +25,7 @@
#include <windows.h> #include <windows.h>
struct IUnknown; // Workaround for "combaseapi.h(229): error C2187: syntax error: 'identifier' was unexpected here" when using /permissive- struct IUnknown; // Workaround for "combaseapi.h(229): error C2187: syntax error: 'identifier' was unexpected here" when using /permissive-
#include <ShObjIdl.h> #include <shobjidl.h>
#include "nfd_common.h" #include "nfd_common.h"
@ -50,9 +54,9 @@ static void CopyWCharToNFDChar( const wchar_t *inStr, nfdchar_t **outStr )
/* includes NULL terminator byte in return */ /* includes NULL terminator byte in return */
static size_t GetUTF8ByteCountForWChar( const wchar_t *str ) static size_t GetUTF8ByteCountForWChar( const wchar_t *str )
{ {
int bytesNeeded = WideCharToMultiByte( CP_UTF8, 0, size_t bytesNeeded = WideCharToMultiByte( CP_UTF8, 0,
str, -1, str, -1,
NULL, 0, NULL, NULL ); NULL, 0, NULL, NULL );
assert( bytesNeeded ); assert( bytesNeeded );
return bytesNeeded+1; return bytesNeeded+1;
} }
@ -151,12 +155,12 @@ static nfdresult_t AddFiltersToDialog( ::IFileDialog *fileOpenDialog, const char
} }
/* filterCount plus 1 because we hardcode the *.* wildcard after the while loop */ /* filterCount plus 1 because we hardcode the *.* wildcard after the while loop */
COMDLG_FILTERSPEC *specList = (COMDLG_FILTERSPEC*)NFDi_Malloc( sizeof(COMDLG_FILTERSPEC) * (filterCount + 1) ); COMDLG_FILTERSPEC *specList = (COMDLG_FILTERSPEC*)NFDi_Malloc( sizeof(COMDLG_FILTERSPEC) * ((size_t)filterCount + 1) );
if ( !specList ) if ( !specList )
{ {
return NFD_ERROR; return NFD_ERROR;
} }
for (size_t i = 0; i < filterCount+1; ++i ) for (UINT i = 0; i < filterCount+1; ++i )
{ {
specList[i].pszName = NULL; specList[i].pszName = NULL;
specList[i].pszSpec = NULL; specList[i].pszSpec = NULL;
@ -184,9 +188,8 @@ static nfdresult_t AddFiltersToDialog( ::IFileDialog *fileOpenDialog, const char
if ( *p_filterList == ';' || *p_filterList == '\0' ) if ( *p_filterList == ';' || *p_filterList == '\0' )
{ {
/* end of filter -- add it to specList */ /* end of filter -- add it to specList */
// Empty filter name -- Windows describes them by extension. CopyNFDCharToWChar( specbuf, (wchar_t**)&specList[specIdx].pszName );
specList[specIdx].pszName = EMPTY_WSTR;
CopyNFDCharToWChar( specbuf, (wchar_t**)&specList[specIdx].pszSpec ); CopyNFDCharToWChar( specbuf, (wchar_t**)&specList[specIdx].pszSpec );
memset( specbuf, 0, sizeof(char)*NFD_MAX_STRLEN ); memset( specbuf, 0, sizeof(char)*NFD_MAX_STRLEN );
@ -206,7 +209,7 @@ static nfdresult_t AddFiltersToDialog( ::IFileDialog *fileOpenDialog, const char
/* Add wildcard */ /* Add wildcard */
specList[specIdx].pszSpec = WILDCARD; specList[specIdx].pszSpec = WILDCARD;
specList[specIdx].pszName = EMPTY_WSTR; specList[specIdx].pszName = WILDCARD;
fileOpenDialog->SetFileTypes( filterCount+1, specList ); fileOpenDialog->SetFileTypes( filterCount+1, specList );
@ -273,6 +276,8 @@ static nfdresult_t AllocPathSet( IShellItemArray *shellItems, nfdpathset_t *path
// Calculate length of name with UTF-8 encoding // Calculate length of name with UTF-8 encoding
bufSize += GetUTF8ByteCountForWChar( name ); bufSize += GetUTF8ByteCountForWChar( name );
CoTaskMemFree(name);
} }
assert(bufSize); assert(bufSize);
@ -307,6 +312,7 @@ static nfdresult_t AllocPathSet( IShellItemArray *shellItems, nfdpathset_t *path
shellItem->GetDisplayName(SIGDN_FILESYSPATH, &name); shellItem->GetDisplayName(SIGDN_FILESYSPATH, &name);
int bytesWritten = CopyWCharToExistingNFDCharBuffer(name, p_buf); int bytesWritten = CopyWCharToExistingNFDCharBuffer(name, p_buf);
CoTaskMemFree(name);
ptrdiff_t index = p_buf - pathSet->buf; ptrdiff_t index = p_buf - pathSet->buf;
assert( index >= 0 ); assert( index >= 0 );
@ -356,29 +362,30 @@ static nfdresult_t SetDefaultPath( IFileDialog *dialog, const char *defaultPath
/* public */ /* public */
nfdresult_t NFD_OpenDialog( const char *filterList, nfdresult_t NFD_OpenDialog( const nfdchar_t *filterList,
const nfdchar_t *defaultPath, const nfdchar_t *defaultPath,
nfdchar_t **outPath ) nfdchar_t **outPath )
{ {
nfdresult_t nfdResult = NFD_ERROR; nfdresult_t nfdResult = NFD_ERROR;
// Init COM library. // Init COM library.
HRESULT result = ::CoInitializeEx(NULL, HRESULT coResult = ::CoInitializeEx(NULL,
::COINIT_APARTMENTTHREADED | ::COINIT_APARTMENTTHREADED |
::COINIT_DISABLE_OLE1DDE ); ::COINIT_DISABLE_OLE1DDE );
::IFileOpenDialog *fileOpenDialog(NULL); ::IFileOpenDialog *fileOpenDialog(NULL);
if ( !SUCCEEDED(result)) if ( !SUCCEEDED(coResult))
{ {
fileOpenDialog = NULL;
NFDi_SetError("Could not initialize COM."); NFDi_SetError("Could not initialize COM.");
goto end; goto end;
} }
// Create dialog // Create dialog
result = ::CoCreateInstance(::CLSID_FileOpenDialog, NULL, HRESULT result = ::CoCreateInstance(::CLSID_FileOpenDialog, NULL,
CLSCTX_ALL, ::IID_IFileOpenDialog, CLSCTX_ALL, ::IID_IFileOpenDialog,
reinterpret_cast<void**>(&fileOpenDialog) ); reinterpret_cast<void**>(&fileOpenDialog) );
if ( !SUCCEEDED(result) ) if ( !SUCCEEDED(result) )
{ {
@ -415,6 +422,7 @@ nfdresult_t NFD_OpenDialog( const char *filterList,
if ( !SUCCEEDED(result) ) if ( !SUCCEEDED(result) )
{ {
NFDi_SetError("Could not get file path for selected."); NFDi_SetError("Could not get file path for selected.");
shellItem->Release();
goto end; goto end;
} }
@ -423,6 +431,7 @@ nfdresult_t NFD_OpenDialog( const char *filterList,
if ( !*outPath ) if ( !*outPath )
{ {
/* error is malloc-based, error message would be redundant */ /* error is malloc-based, error message would be redundant */
shellItem->Release();
goto end; goto end;
} }
@ -439,8 +448,12 @@ nfdresult_t NFD_OpenDialog( const char *filterList,
nfdResult = NFD_ERROR; nfdResult = NFD_ERROR;
} }
end: end:
::CoUninitialize(); if (fileOpenDialog)
fileOpenDialog->Release();
if (SUCCEEDED(coResult))
::CoUninitialize();
return nfdResult; return nfdResult;
} }
@ -452,10 +465,10 @@ nfdresult_t NFD_OpenDialogMultiple( const nfdchar_t *filterList,
nfdresult_t nfdResult = NFD_ERROR; nfdresult_t nfdResult = NFD_ERROR;
// Init COM library. // Init COM library.
HRESULT result = ::CoInitializeEx(NULL, HRESULT coResult = ::CoInitializeEx(NULL,
::COINIT_APARTMENTTHREADED | ::COINIT_APARTMENTTHREADED |
::COINIT_DISABLE_OLE1DDE ); ::COINIT_DISABLE_OLE1DDE );
if ( !SUCCEEDED(result)) if ( !SUCCEEDED(coResult))
{ {
NFDi_SetError("Could not initialize COM."); NFDi_SetError("Could not initialize COM.");
return NFD_ERROR; return NFD_ERROR;
@ -464,12 +477,13 @@ nfdresult_t NFD_OpenDialogMultiple( const nfdchar_t *filterList,
::IFileOpenDialog *fileOpenDialog(NULL); ::IFileOpenDialog *fileOpenDialog(NULL);
// Create dialog // Create dialog
result = ::CoCreateInstance(::CLSID_FileOpenDialog, NULL, HRESULT result = ::CoCreateInstance(::CLSID_FileOpenDialog, NULL,
CLSCTX_ALL, ::IID_IFileOpenDialog, CLSCTX_ALL, ::IID_IFileOpenDialog,
reinterpret_cast<void**>(&fileOpenDialog) ); reinterpret_cast<void**>(&fileOpenDialog) );
if ( !SUCCEEDED(result) ) if ( !SUCCEEDED(result) )
{ {
fileOpenDialog = NULL;
NFDi_SetError("Could not create dialog."); NFDi_SetError("Could not create dialog.");
goto end; goto end;
} }
@ -515,6 +529,7 @@ nfdresult_t NFD_OpenDialogMultiple( const nfdchar_t *filterList,
if ( AllocPathSet( shellItems, outPaths ) == NFD_ERROR ) if ( AllocPathSet( shellItems, outPaths ) == NFD_ERROR )
{ {
shellItems->Release();
goto end; goto end;
} }
@ -531,8 +546,12 @@ nfdresult_t NFD_OpenDialogMultiple( const nfdchar_t *filterList,
nfdResult = NFD_ERROR; nfdResult = NFD_ERROR;
} }
end: end:
::CoUninitialize(); if ( fileOpenDialog )
fileOpenDialog->Release();
if (SUCCEEDED(coResult))
::CoUninitialize();
return nfdResult; return nfdResult;
} }
@ -544,10 +563,10 @@ nfdresult_t NFD_SaveDialog( const nfdchar_t *filterList,
nfdresult_t nfdResult = NFD_ERROR; nfdresult_t nfdResult = NFD_ERROR;
// Init COM library. // Init COM library.
HRESULT result = ::CoInitializeEx(NULL, HRESULT coResult = ::CoInitializeEx(NULL,
::COINIT_APARTMENTTHREADED | ::COINIT_APARTMENTTHREADED |
::COINIT_DISABLE_OLE1DDE ); ::COINIT_DISABLE_OLE1DDE );
if ( !SUCCEEDED(result)) if ( !SUCCEEDED(coResult))
{ {
NFDi_SetError("Could not initialize COM."); NFDi_SetError("Could not initialize COM.");
return NFD_ERROR; return NFD_ERROR;
@ -556,12 +575,13 @@ nfdresult_t NFD_SaveDialog( const nfdchar_t *filterList,
::IFileSaveDialog *fileSaveDialog(NULL); ::IFileSaveDialog *fileSaveDialog(NULL);
// Create dialog // Create dialog
result = ::CoCreateInstance(::CLSID_FileSaveDialog, NULL, HRESULT result = ::CoCreateInstance(::CLSID_FileSaveDialog, NULL,
CLSCTX_ALL, ::IID_IFileSaveDialog, CLSCTX_ALL, ::IID_IFileSaveDialog,
reinterpret_cast<void**>(&fileSaveDialog) ); reinterpret_cast<void**>(&fileSaveDialog) );
if ( !SUCCEEDED(result) ) if ( !SUCCEEDED(result) )
{ {
fileSaveDialog = NULL;
NFDi_SetError("Could not create dialog."); NFDi_SetError("Could not create dialog.");
goto end; goto end;
} }
@ -594,6 +614,7 @@ nfdresult_t NFD_SaveDialog( const nfdchar_t *filterList,
result = shellItem->GetDisplayName(::SIGDN_FILESYSPATH, &filePath); result = shellItem->GetDisplayName(::SIGDN_FILESYSPATH, &filePath);
if ( !SUCCEEDED(result) ) if ( !SUCCEEDED(result) )
{ {
shellItem->Release();
NFDi_SetError("Could not get file path for selected."); NFDi_SetError("Could not get file path for selected.");
goto end; goto end;
} }
@ -603,6 +624,7 @@ nfdresult_t NFD_SaveDialog( const nfdchar_t *filterList,
if ( !*outPath ) if ( !*outPath )
{ {
/* error is malloc-based, error message would be redundant */ /* error is malloc-based, error message would be redundant */
shellItem->Release();
goto end; goto end;
} }
@ -619,8 +641,12 @@ nfdresult_t NFD_SaveDialog( const nfdchar_t *filterList,
nfdResult = NFD_ERROR; nfdResult = NFD_ERROR;
} }
end: end:
::CoUninitialize(); if ( fileSaveDialog )
fileSaveDialog->Release();
if (SUCCEEDED(coResult))
::CoUninitialize();
return nfdResult; return nfdResult;
} }
@ -732,7 +758,8 @@ nfdresult_t NFD_PickFolder(const nfdchar_t *defaultPath,
ComPtr<IShellItem> pShellItem; ComPtr<IShellItem> pShellItem;
if (!SUCCEEDED(pFileDialog->GetResult(&pShellItem))) if (!SUCCEEDED(pFileDialog->GetResult(&pShellItem)))
{ {
return NFD_OKAY; NFDi_SetError("Could not get shell item from dialog.");
return NFD_ERROR;
} }
// Finally get the path // Finally get the path