4

In my mac app I'm using NSSavePanel - but it's behaving very strange. Sometimes I can't change the default name of the file.

I'm using it like this:

NSSavePanel *savePanel = [NSSavePanel savePanel];
[savePanel setAllowedFileTypes:@[@"jpg"]];
[savePanel setLevel:CGShieldingWindowLevel()];

if([savePanel runModal] == NSFileHandlingPanelOKButton)
{
    //saving file
}

I can't find why sometimes it lets me change the file name and other times no, I can save a file but a changing name in save panel is blocked

Wojtek
  • 1,006
  • 11
  • 30

4 Answers4

1

This is not a proper answer, but may shed some light on the issue (which I'm struggling with as well).

What I have found so far, is that if you do not have an active window when you call

result = panel.runModal() // swift
NSModalResponse result = [panel runModal]; // Obj-C

Then the behavior of NSSavePanel is broken, and although you can click in the name field you can't type there (beeps if you try).

I also found an ugly little workaround. If you allow creating new directories,

    panel.canCreateDirectories = YES;  // Obj-C

and press the button in the save panel to do this - a small sheet (yet another window...) appears on top of the NSSavePanel and if you cancel and dismiss this sheet - you regain ability to type in the name field.

Since OP did not provide any description of the programmatic scenario and environment for his issue, but it seems related since forcing the window-level to be "modal" fixed the issue for him.

In my case (I'm opening NSSavePanel from a menu-bar item pop-over window. Alas the popover closes BEFORE my NSSavePanel manages "to attach to it". Manually setting the level

panel.level = NSWindow.Level.modalPanel // Swift
panel.level = NSModalPanelWindowLevel;  // Obj-C

did NOT help resolve the issue.

Motti Shneor
  • 2,095
  • 1
  • 18
  • 24
0

Have you tried providing a default name?

[savePanel setNameFieldStringValue:@"New File.txt"];
Rupert Pupkin
  • 742
  • 6
  • 9
0

Swift 4

let panel = NSSavePanel()
panel.nameFieldStringValue = "filename.txt" // <-- user editable prompt 

if panel.runModal() == NSApplication.ModalResponse.OK, let url = panel.url {
    // use url path here
}
marc-medley
  • 8,931
  • 5
  • 60
  • 66
0

This is so strange but I would like to share my solution. As @Rupert Pupkin described, I already used nameFieldStringValue but there was strange behaviour of NSSavePanel, it was not changing the name sometimes, and sometimes was changing. So I see I did not describe level of my NSSavePanel

savePanel.nameFieldStringValue = "YourFileName"
savePanel.level = NSWindow.Level.modalPanel

This two lines of code with together worked for me.

My current NSSavePanel code is like that:

let savePanel = NSSavePanel()
savePanel.title = "Download File"
savePanel.prompt = "Download"
savePanel.message = "Choose a directory to save your scanned document"
savePanel.nameFieldStringValue = "myfile"
savePanel.level = NSWindow.Level.modalPanel

savePanel.showsTagField = false
savePanel.isExtensionHidden = false
savePanel.canCreateDirectories = true

Hope that helps!

eemrah
  • 1,603
  • 3
  • 19
  • 37