我如何收集多个openFile:(NSString *)事件,然后与他们做一些事情? [英] How can I collect multiple openFile:(NSString *) events and then do something with them?

查看:176
本文介绍了我如何收集多个openFile:(NSString *)事件,然后与他们做一些事情?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我正在处理一个Cocoa / Objective C ++实用程序应用程序,并希望处理多个(即时)文件打开。要处理文件打开部分,我在 AppDelegate.mm 文件中有此功能:

   - (BOOL)application:(NSApplication *)app openFile:(NSString *)filename 
{
NSLog(@打开文件%@,文件名)

//这里有更多的C ++代码

return YES;
}

文件正在发送到Quicksilver,我相信会发送文件(Finder的打开与我认为发送所有的文件,所以可能使用 handleOpenApplicationEvent:(NSAppleEventDescriptor *)event 可能会更好) - 但无论如何,应用程序将接收几个文件一个接一个 - 几乎瞬间 - 但不完全一起。以下是Console.app显示的内容:





由于文件是单独发送的,而是一个接一个发送,我的问题是如何收集所有发送的文件一件事与他们?例如,我想收集所有发送的文件路径,然后在对话框中将它们显示在一起。



我可以想到一个可能工作的概念:store接收数组中的每个文件路径。同时,当接收到第一个时,在后台设置1-2秒的延迟,然后有一个对话框显示作为特定变量的一切。这个概念是正确的还是有更好的方法来做到这一点?我是Cocoa / Objective C ++的新手 - 来自PHP / Perl,bash等语言。



我也希望这个帮助应用程序完成,但如果我在等待文件,当我收到最后一个文件时如何终止应用程序?



如果我将 [NSApp terminate:nil]; 添加到 applicationDidFinishLaunching

更新 - 更多注意事项 b

这是使用 openFiles (复数)函数后的控制台:



使用Quicksilver我抓住一些文件,目录,然后选择打开方式,然后选择我正在创建的应用程序(名为darn.app)





工作正常:





...结果在consolea.app中:





我曾询问Quicksilver开发人员,他们确认QS通过Open With操作一次打开一个文件,他们承认这与Finder的不同,但他们认为这是预期的。所以也许Darren是对的 - 一个计时器可能是最好的方式...

解决方案

尝试实现 -application:openFiles:而不是 -application:openFile:

   - (void)application:(NSApplication *)sender openFiles:(NSArray *)filenames 
{
NSLog(@打开多个文件%@,文件名)
}

可处理从Finder接收多个文件。



如果这不适合您的Quicksilver设置,那么定时器可能是最好的方法。



在AppDelegate的-init方法中设置计时器。

  @implementation MyAppDelegate {
NSMutableArray * _files;
}

- (id)init {
if(self = [super init]){
_files = [[NSMutableArray alloc] initWithCapacity:10];

[self performSelector:@selector(processFiles)
withObject:nil
afterDelay:1.0]; //一秒延迟
}
return self;
}

在应用程序中:openFile:收集数组中的文件, 。

   - (BOOL)application:(NSApplication *)app openFile:(NSString *)filename {
NSAssert != nil,@Timer already fired);

[_files addObject:filename];

[NSObject cancelPreviousPerformRequestsWithTarget:self];
[self performSelector:@selector(processFiles)
withObject:nil
afterDelay:1.0];
}

定时器启动时,处理收集的文件,然后退出应用程序。 / p>

   - (void)processFiles 

//处理_files

[ _files release];
_files = nil;
[NSApp terminate:nil];
}


I'm working on an Cocoa / Objective C++ utility application and want to handle multiple (instantaneous) file opens. To handle the file opening part, I have this function in my AppDelegate.mm file:

- (BOOL)application:(NSApplication*)app openFile:(NSString *)filename
{
    NSLog(@"Opening file %@", filename);

    // more C++ code here

    return YES;
}

The files are being sent to Quicksilver, which I believe will send the files one after another to the application (Finder's "Open With" I think sends all the files at once - and so possibly using handleOpenApplicationEvent:(NSAppleEventDescriptor *)event might work better for that) - but regardless, the application will receive several files one after another - almost instantaneously - but not exactly together. Here is what Console.app shows:

Since the files are sent separately, but one right after another, my question is how can I gather all the files that are sent and do one thing with them? For instance, I'd like to gather all the file paths sent and then display them together in a dialog box.

I can think of one concept which might work: store each file path in an array as it is received. At the same time, when the first one is received, set a delay of 1-2 seconds in the background, and then have a dialog box display everything that is a particular variable. Is that concept right or is there a better way to do that? I'm new to Cocoa / Objective C++ - coming from languages like PHP / Perl, bash, etc.

I'd also like to have this helper application terminate when it is finished, but if I'm waiting on files how can I terminate the application when the last of the files are received?

If I add [NSApp terminate:nil]; to the applicationDidFinishLaunching function the application actually terminates after only the first file is received.

Update - More Notes

This is the console after using the openFiles (plural) function:

And with Quicksilver I grab some files, like the ones in the temp directory, and choose "Open With" and then the App I'm creating (named darn.app)

But with Finder it seems to works just fine:

...results in consolea.app:

I did ask the Quicksilver developers and they confirmed that QS does open files one at a time with the Open With action and they acknowledge that this is different than how Finder does it but they see this as the intended. So maybe Darren is right - a timer may be the best way to go...

解决方案

Try implementing -application:openFiles: instead of -application:openFile:

- (void)application:(NSApplication *)sender openFiles:(NSArray *)filenames
{
    NSLog(@"Opening multiple files %@", filenames);
}

That handles receiving multiple files from Finder.

If that doesn't work with your Quicksilver setup then a timer is probably the best way to go.

Set up the timer in the AppDelegate's -init method.

@implementation MyAppDelegate {
    NSMutableArray* _files;
}

- (id)init {
    if (self = [super init]) {
        _files = [[NSMutableArray alloc] initWithCapacity:10];

        [self performSelector:@selector(processFiles) 
                   withObject:nil 
                   afterDelay:1.0]; // one second delay
    }
    return self;
}

In -application:openFile: collect the file in an array and reset the timer.

- (BOOL)application:(NSApplication*)app openFile:(NSString*)filename {
    NSAssert(_files != nil, @"Timer already fired");

    [_files addObject:filename];

    [NSObject cancelPreviousPerformRequestsWithTarget:self];
    [self performSelector:@selector(processFiles) 
               withObject:nil 
               afterDelay:1.0];
} 

When the timer fires, process the collected files and then quit the app.

-(void)processFiles

    // Process the _files

    [_files release];
    _files = nil;
    [NSApp terminate:nil];
}

这篇关于我如何收集多个openFile:(NSString *)事件,然后与他们做一些事情?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆