Получить уведомление о ходе выполнения задачи от NSTask

Любое тело имеет представление о получении уведомления от NSTask, пока выполняется NSTask. Я распаковываю zip-файл, используя NSTask, и мне нужно показать ход распаковки данных в NSProgressBar. Я не нашел никакой идеи для выполнения такой задачи. Так что я показываю значение в строке состояния. Нужна помощь для выполнения этой задачи. Заранее спасибо.

2 ответа

Решение

Использование NSFileHandleReadCompletionNotification, NSTaskDidTerminateNotification уведомления.

task=[[NSTask alloc] init];

[task setLaunchPath:Path];

NSPipe *outputpipe=[[NSPipe alloc]init];

NSPipe *errorpipe=[[NSPipe alloc]init];

NSFileHandle *output,*error;

[task setArguments: arguments];

[task setStandardOutput:outputpipe];

[task setStandardError:errorpipe];

output=[outputpipe fileHandleForReading];

error=[errorpipe  fileHandleForReading];

[task launch]; 


[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(receivedData:)  name: NSFileHandleReadCompletionNotification object:output];

[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(receivedError:)  name: NSFileHandleReadCompletionNotification object:error];

[[NSNotificationCenter defaultCenter] addObserver:self selector:@selector(TaskCompletion:)  name: NSTaskDidTerminateNotification object:task];

//[input writeData:[NSMutableData initWithString:@"test"]];
[output readInBackgroundAndNotify];

[error readInBackgroundAndNotify];


[task waitUntilExit];

[outputpipe release];

[errorpipe release];
[task release];
[pool release];


/* Called when there is some data in the output pipe */

-(void) receivedData:(NSNotification*) rec_not

{

    NSData *dataOutput=[[rec_not userInfo] objectForKey:NSFileHandleNotificationDataItem];

    [[rec_not object] readInBackgroundAndNotify];

    [strfromdata release];

}

/* Called when there is some data in the error pipe */

-(void) receivedError:(NSNotification*) rec_not

{
    NSData *dataOutput=[[rec_not userInfo] objectForKey:NSFileHandleNotificationDataItem];

    if( !dataOutput)

        NSLog(@">>>>>>>>>>>>>>Empty Data");

    [[rec_not object] readInBackgroundAndNotify];


}

/* Called when the task is complete */

-(void) TaskCompletion :(NSNotification*) rec_not

{   

}

Чтобы показать прогресс, вам нужно выяснить две вещи:

  • Сколько файлов в архиве или сколько байт они займут после завершения распаковки
  • Сколько файлов или байтов вы уже распаковали

Вы узнаете об этом, прочитав выходные данные задачи распаковки. Ответ Параг Бафны - это начало; в receivedData:вам нужно будет проанализировать вывод, чтобы определить, какой прогресс только что произошел, а затем добавить этот прогресс к вашему текущему счету прогресса (например, ++_filesUnzippedSoFar).

Первая часть, выяснение общего размера работы, сложнее. В основном вам нужно запустить unzip перед запуском unzip: первый, с -l (это строчная буква L), чтобы перечислить содержимое архива; второе - распаковать его. Первый, вы читаете вывод, чтобы определить, сколько файлов / байтов содержит архив; второй, вы читаете вывод, чтобы определить значение для продвижения индикатора выполнения.

Установка свойств индикатора выполнения является простой частью; те буквально просто doubleValue а также maxValue, Выяснить, где вы работаете, - это сложная часть, и она очень специфична для предметной области - вам нужно прочитать вывод unzip (дважды, в разных формах), понять, что он говорит вам, и перевести его в информацию о ходе выполнения.

В NSTask нет ничего, что могло бы вам в этом помочь. Часть NSTask этого начинается и заканчивается на standardOutput имущество. Он не знает ни о zip-файлах, ни о архивах, ни о содержимом архивов, ни даже о прогрессе, поскольку ничего из этого не относится к большинству задач. Это все зависит от вашей задачи, а это значит, что вы должны написать код, чтобы сделать это.

Другие вопросы по тегам