Получить базовые NSData из UIImage

104

Я могу создавать UIImageс NSDataпомощью методов [UIImage imageWithData:]или [UIImage initWithData:].

Интересно, смогу ли я получить NSDataобратно от существующего UIImage? Что-то вродеNSData *myData = [myImage getData];

Евгений
источник

Ответы:

191
NSData *imageData = UIImageJPEGRepresentation(image, 0.7); // 0.7 is JPG quality

или

NSData *imageData = UIImagePNGRepresentation(image);

В зависимости от того, нужны ли вам данные в формате PNG или JPG.

Кэролайн
источник
84
Я не знаю, почему за этот ответ так часто голосуют и почему его принимают. OP попросил извлечь данные, которые были предоставлены изначально. Использование UIImageJPEGRepresentationили UIImagePNGRepresentation приведет к изменению данных и выполнению повторного преобразования. Есть ли способ действительно добиться того, о чем просили?
Patrik
6
Этот ответ не годится, потому что он снизит качество изображения, если оно уже находится в формате с потерями.
1dayitwillmake
@CipherCom Я понимаю, что вы говорите о возвращении точных данных. Однако я думаю, что для большинства людей, которые сталкиваются с вопросом, этот ответ будет идеальным для их нужд ... отсюда и положительные голоса. Если вы встретите ответ для получения исходных данных, поделитесь, пожалуйста;)
tybro0103 06
@ 1dayitwillmake Даже репп PNG? Не в моей области знаний, но я думал, что PNG не теряются?
tybro0103 06
@ Боб Сприн Это не поможет. Свойство CIImage устанавливается, только если оно было инициализировано с помощью imageWithCIImage :. Также это не непосредственно используемые данные, а скорее другой объект представления изображения.
King-Wizard
22

При инициализации UIImageобъекта с помощью init(data: originalData), originalDataони будут преобразованы в необработанные данные в каком-то внутреннем формате. Эти данные можно получить позже с помощью

let rawData = myImage.cgImage?.dataProvider?.data as Data?

Однако, поскольку rawDataэто необработанный файл, он будет даже больше, чем при использовании UIImagePNGRepresentation.

Yesleon
источник
как мне это сделать в Objective-C
h3dkandi 01
NSData * rawData = (__bridge NSData *) CGDataProviderCopyData (CGImageGetDataProvider (image.CGImage));
ZardozSpeaks
@Zardoz Говорит, что вариант obj-c вполне жизнеспособен для включения в качестве редактирования в этот ответ.
Kamil.S 07
6

Вы можете ожидать, что UIImage - это объект, отформатированный для отображения, и поэтому не будут использовать исходные данные (которые, вероятно, находятся в формате PNG или JPEG), а скорее будут массивом пикселей или каким-либо другим внутренним форматом. Другими словами, UIImage(data: foo)не удержит foo.

  1. Если вы просто хотите использовать его в другом месте своей программы, исходный UIImage подойдет (я предполагаю, что здесь это не совсем так)

  2. Если вы хотите сериализовать, UIImagePNGRepresentation(...)будет работать, но будет увеличен, если оригинал был в формате JPEG; UIImageJPEGRepresentation(...)часто приводит к небольшому увеличению размера данных и с небольшими потерями, если исходный файл был в формате PNG. Можно выбрать один, исходя из способа отображения изображения и формата, который вы ожидаете предоставить. Если вы используете PNG в и хотите PNG, вы должны получить файл хорошего размера и почти идентичные данные, за исключением специальных фрагментов PNG.

  3. Если вы хотите получить точную копию исходных данных (например, для сохранения файла после миниатюры или в SHA1), вам необходимо сохранить ее отдельно. Вы можете сделать что-то вроде:

    var image:UIImage
    var imageData:NSData {
        didSet {
            image = UIImage(data: imageData)
        }
    }
    
Джим Дрисколл
источник
4

Просто потому, что наткнулся на это и мне нравится быстрый :)

Вот быстрый перевод сообщения Каройлин.

var imageData = UIImagePNGRepresentation(image)

Или

var imageData = UIImageJPEGRepresentation(image, 0.7) 
nsij22
источник
Вопрос не касался Свифта.
Cross_
3

Swift 4.2

let dataPng = image.pngData() // return image as PNG. May return nil if image has no CGImageRef or invalid bitmap format

let dataJpg = image.jpegData(compressionQuality: 1) // return image as JPEG. May return nil if image has no CGImageRef or invalid bitmap format. compression is 0(most)..1(least)
Масловса
источник
-2

Все изменилось с тех пор, как был дан ответ выше, для тех, кто все еще ищет, потому что они разделяют озабоченность CipherCom: iOS 5 добавила свойство CIImage .

Rafe
источник
Я не вижу способа использовать CIImage для получения базовых NSData ... Я что-то упускаю?
tybro0103 06
4
Это не поможет. Свойство CIImageустанавливается только в том случае, если оно было инициализировано с помощью imageWithCIImage:. Также это не непосредственно используемые данные, а скорее другой объект представления изображения.
Patrik