Подтвердить что ты не робот

Получить тип файла в Cocoa

Мне удалось найти расширенный тип файла указанного файла (изображение JPEG, TIFF Image,...), но я ищу что-то более общее, которое может классифицировать файлы в "больших категонах", таких как изображения, moovies, текстовые файлы,... Есть ли способ сделать это в cocoa (или objective-c)?

Спасибо за вашу помощь,

4b9b3361

Ответ 1

Вы можете использовать Унифицированные идентификаторы типов. Поскольку UTI организованы в иерархии, одна из возможностей состоит в том, чтобы проверить, соответствует ли предпочтительный UTI для данного файла UTI верхнего уровня, например. public.image для изображений или public.movie для фильмов. Структура основных служб включает функции, которые работают с UTI, а также константы, представляющие известные UTI.

Например, работа над расширениями имен файлов:

NSString *file = @"…"; // path to some file
CFStringRef fileExtension = (CFStringRef) [file pathExtension];
CFStringRef fileUTI = UTTypeCreatePreferredIdentifierForTag(kUTTagClassFilenameExtension, fileExtension, NULL);

if (UTTypeConformsTo(fileUTI, kUTTypeImage)) NSLog(@"It an image");
else if (UTTypeConformsTo(fileUTI, kUTTypeMovie)) NSLog(@"It a movie");
else if (UTTypeConformsTo(fileUTI, kUTTypeText)) NSLog(@"It text");

CFRelease(fileUTI);

Если у вас есть тип MIME вместо расширения имени файла, вы можете использовать kUTTagClassMIMEType вместо kUTTagClassFilenameExtension.

Список известных UTI см. этот документ.

Ответ 2

[[NSWorkspace sharedWorkspace] typeOfFile:pathToFile error:nil]

Ответ 3

Пример проверки того, является ли путь типом изображения, может быть изменен в соответствии с другими классами UTI. Обратите внимание на технический комментарий Технический Q & A QA1518 использует FSPathMakeRef, который теперь устарел, чтобы получить uti через LSCopyItemAttributes - решение NSWorkspace выше - лучший способ получить UTI, тогда вам просто нужно добавить код для сравнения со списком UTI: ( соответствующий массив может быть предварительно выделен и инициализирован/выпущен в другом месте, если это необходимо)

- (BOOL)isImageFile:(NSString*)filePath
{
/* get an array of utis to match against, this gets supported CG/NS image formats */

CFArrayRef supportedTypes = CGImageSourceCopyTypeIdentifiers();
CFIndex    typeCount      = CFArrayGetCount(supportedTypes);

/* get the uti of the filepath and check against the list with the UTI API */

BOOL isImage     = NO;
NSString * uti   = [[NSWorkspace sharedWorkspace] typeOfFile:filePath error:nil];

if ( uti != nil){
    for (CFIndex i = 0; i < typeCount; i++)
    {
        CFStringRef supportedUTI = CFArrayGetValueAtIndex(supportedTypes, i);
        if (UTTypeConformsTo(supportedUTI, CFSTR("public.image")))
        {
            if (UTTypeConformsTo((CFStringRef)uti, supportedUTI))
            {
                isImage = YES;
                break;
            }
        }
    } // i
}
/* clean up */
CFRelease(supportedTypes);
return isImage;
}

Ответ 4

Вы также можете определить тип изображения, не полагаясь на расширение пути с помощью CGImageSource (часть рамки ImageIO).

В следующем примере используется URL-адрес файла, но вы также можете создать источник изображения из CFDataRef.

CFStringRef typeOfImageAtURL(NSURL *imageURL) {
    const void * keys[] = { kCGImageSourceShouldCache };
    const void * values[] = { kCFBooleanFalse };
    CFDictionaryRef options = CFDictionaryCreate(kCFAllocatorDefault, keys, values, 1, NULL, NULL);
    CGImageSourceRef imageSource = CGImageSourceCreateWithURL((__bridge CFURLRef)imageURL, options);
    CFStringRef imageType = CGImageSourceGetType(imageSource);
    CFRelease(options);
    CFRelease(imageSource);
    return imageType;
}

Возвращаемое значение будет константой, которую вы можете сравнить с значениями идентификатора однородного типа, указанными в CoreServices/MobileCoreServices (например, kUTTypeJPEG, kUTTypeGIF и т.д.).

Обледенение на торте: вы можете передать опциональную "подсказку" UTI, если у вас есть причина предвидеть один тип файла. Объедините этот подход с Bavarious ', и у вас будет скудная машина для определения формата изображения.