aiekick/ImGuiFileDialog

Support for multi layer extension like file.ext1.ext2

APassbyDreg opened this issue ยท 26 comments

Current implementation failed to match multi layer extensions like .ext1.ext2 in filters.

  • If I use .a.b in the filter, the file won't match because only the last extension is recognized and matched
  • If I use regex (.*\\.a\\.b) in the filter, the returned path from GetFilePathName() will be like filepath_no_ext.a(.*\\.a\\.b)

Possible solutions:

  • Directly match if the filename ends with filter
  • Regex should be handled seperately

Other Issues:

  • IGFD::FileManager::GetResultingFileName add regex to the end of selected filename directly. This generates error file path.

If you need to have many extensions for a filter, you must use collection filters. This is explained in the doc.

If you speak about collections filter of regex filter, im currently working on it.

If this is not your case so i dont undestand your post.

What I'm trying to have is not a filter with extension .a or .b, but a filter with extension .a.b, which matches files like file.a.b. As an example, the files.associations setting of vscode can match such files using "*.a.b": "jsonc".

ok thanks for the explain. will working on that feature.

btw, im focused on antoher porject for the moment, so will have some delay

This would be great. I could use this feature as well.

can you test now ? i think your issue is fixed

Thanks. After a bit of puzzling with the regex I got it to work now.

nice to hear, but i speak first to @APassbyDreg who opened this issue :)

Thanks for the fix. It does work well with regex filters, but that needs additional care with the returned GetFilePathName() path because it doesn't include the extension as regular filters do. Hopefully, the multi-layer extensions can be treated as regular ones like this:

m_fileDialogInstance.OpenDialog( "ChooseFileDlgKey", "Choose File", ".ge.mat,.*", workdir.string().c_str());

I managed to work around this by directly checking if the filename ends with the filter in IsCoveredByFilters and skipping the replacement if the filename already matched the filter.

Ok cool.

You can check all the covered case where there is no replacepent in the function "ReplaceExtentionWithCurrentFilter" of the filter manager

Not sure to understand your last point.

You consider its fixed or you have another case who is not working. Normally what you do with "IsCoveredByFilter" is no more needed. No. ?

I'm not sure whether this is a new case or a bug in the existing code, but it seems that this line of code cannot work correctly:

m_fileDialogInstance.OpenDialog( "ChooseFileDlgKey", "Choose File", ".ge.mat,.*", workdir.string().c_str());


The files I want to show are not showing in the dialog with the .ge.mat filter.

It seems that currently the ReplaceExtentionWithCurrentFilter function does treat the multi-level extension as a regular filter. However, using multi-level extension as regular filter is not working as shown above. That's why I modified the IsCoveredByFilter to allow files ending with the filter directly pass the check and show in the dialog.

Ha ok , i fixed the return of file path name. But not changed anything in the filtering

So its a bug i guess. I not understood that was a bug in display

It seems that the input file extension vExt of IsCoveredByFilter just recognizes the last extension (which is a result of line 1440 ImGuiFileDialog.cpp). Multi-level extensions are filtered out because they cannot satisfy the prSelectedFilter.exist(vExt, vIsCaseInsensitive) condition and thus not shown in the dialog.

This issue changes the previous way to define the "extension" of a file. So there might be a lot of related code to check. That's why I work around it by just adding one simple rule to allow filenames ending with the filter directly pass the check (but this may cause extra problems, I haven't tested it).

Not sure why you say "This issue changes the previous way to define the "extension" of a file". For me we just need to adapt the filtering like i done yesterday with getFilePathName. Or maybe i miss something

As mentioned above, currently the extension of a file is defined to be the characters after the last dot character (line 1440 of ImGuiFileDialog.cpp). Under such context, the extension of a file named file.a.b is b. However, if multi-level extension is supported (at least, as I expected), the extension of that file should be a.b.

If I use ".a.b" as a filter, when judging whether the file file.a.b matches the filter in function IsCoveredByFilter, the vExt pass to prSelectedFilter.exist(vExt, vIsCaseInsensitive) is b, but not a.b, so the function will return false and filter out file.a.b from the display.

That's why I say "This issue changes the previous way to define the "extension" of a file". I have come up with two options to fix this:

  1. change the previous way to define the "extension" of a file: that is to say, the definition of extension should be modified to be "characters after any dot character". This should enable file file.a.b to match with both .b and .a.b filters.
  2. take the brutal force design to bypass this problem through directly checking if the filename ends with a filter. However, this requires more effort to deal with corner cases like invalid input filter or filename ends with a regex-like string.

im working on a other way. (not commited)

i extract the file extention according to the count of dots in the filter extention.

if i have files : toto.a.b, toto.b
with filter ".a.b" we will have files : toto.a.b
with filter .b we will have files : toto.a.b toto.b
with filter .a we will have no files

i apply the same for filter collections but this is failing
with filter {.a.b, .b}
we will have files : toto.a.b only,
because he use for extraction the max dot per filter of the whole collection. so here 2
a solution could be to use internally regex for all filter.. but cna be slow i guess :(

your issue is fixed to me now.
can you confirm ?

The files are correctly shown, but another bug occurs: the filter does not appear in the selection box. Not sure what is causing that.

notice that the selected filter is empty in the bottom right selection box.

Another problem is that if I enter a file name, the returned path from GetFilePathName doesn't include the .ge.mat extension, which is inconsistent with the behavior for regular extensions like .json etc.

arf, can you show me your opendialog command . i not see this bug in my sample app

My mistake, I forget to switch back from the regex filter to the plain filter. Currently the .ge.mat works well. Instead, it's a bug related to the regex filter. The regex filters are not shown in the filter selection box.

yes when there is a regex i dont know what to do. its not human readable.
one time i renamed "regex", but why that instead of another ? :)
regex have no sense in simple filter.
so finally i display the regex..

can we close this isuue ? its ok for you ?

The double extensions work now even without regexp. However, I fear you broke the SetFileStyle in the process:
ImGuiFileDialog::Instance()->SetFileStyle(IGFD_FileStyleByExtention, ".gif", ImVec4(0.0f, 1.0f, 0.5f, 0.9f), "[GIF]"); I no longer see the coloring (or icon). Not for single extensions nor for double extensions.

thanks. will check that

fixed :) a copy / past mistake :)

Hehe. Sounds familiar. Thanks.