it-swarm.com.ru

Проблема чтения метаданных JPEG (ориентация)

У меня есть изображение JPEG, которое было снято на iphone. На моем настольном компьютере (Windows Photo Viewer, Google Chrome и т.д.) Ориентация неверна.

Я работаю над веб-приложением ASP.NET MVC 3, где мне нужно загрузить фотографии (в настоящее время используется plupload).

У меня есть некоторый серверный код для обработки изображений, включая чтение данных EXIF.

Я попытался прочитать поле PropertyTagOrientation в метаданных EXIF ​​(используя GDI - Image.PropertyItems), но поле отсутствует.

Так что это либо определенные метаданные iphone, либо некоторые другие метаданные.

Я использовал другой инструмент, такой как Aurigma Photo Uploader, и он правильно читает метаданные и поворачивает изображение. Как оно работает?

Кто-нибудь знает, какие другие метаданные JPEG могут содержать информацию, требуемую для того, чтобы знать, что она должна быть повернута, которая используется Aurigma?

Вот код, который я использую для чтения данных EXIF:

var image = Image.FromStream(fileStream);

foreach (var prop in image.PropertyItems)
{
   if (prop.Id == 112 || prop.Id == 5029)
   {
      // do my rotate code - e.g "RotateFlip"
      // Never get's in here - can't find these properties.
   }
}

Есть идеи?

48
RPM1984

Похоже, вы забыли, что значения идентификатора ориентации, которые вы искали, находятся в шестнадцатеричном формате. Там, где вы используете 112, вы должны были использовать 0x112. 

Эта статья объясняет, как Windows справляется с ориентацией, и эта кажется довольно актуальной для того, что вы делаете.

17
spender

Вот фрагмент, адресованный 8 значениям ориентации.

Сначала несколько заметок:

EXIF id 0x0112 предназначен для ориентации. Это полезная ссылка на идентификатор EXIF ​​ http://www.sno.phy.queensu.ca/~phil/exiftool/TagNames/EXIF.html

0x0112 - это шестнадцатеричный эквивалент 274. Тип данных PropertyItem.Id - это int, что означает, что здесь полезно 274.

Кроме того, 5029, вероятно, должно быть 0x5029 или 20521, что соответствует ThumbnailOrientation, хотя, вероятно, здесь не то, что требуется.

Ориент Изображение:

Примечание: img является System.Drawing.Image или наследуется от него, как System.Drawing.Bitmap.

if (Array.IndexOf(img.PropertyIdList, 274) > -1)
{
    var orientation = (int)img.GetPropertyItem(274).Value[0];
    switch (orientation)
    {
        case 1:
            // No rotation required.
            break;
        case 2:
            img.RotateFlip(RotateFlipType.RotateNoneFlipX);
            break;
        case 3:
            img.RotateFlip(RotateFlipType.Rotate180FlipNone);
            break;
        case 4:
            img.RotateFlip(RotateFlipType.Rotate180FlipX);
            break;
        case 5:
            img.RotateFlip(RotateFlipType.Rotate90FlipX);
            break;
        case 6:
            img.RotateFlip(RotateFlipType.Rotate90FlipNone);
            break;
        case 7:
            img.RotateFlip(RotateFlipType.Rotate270FlipX);
            break;
        case 8:
            img.RotateFlip(RotateFlipType.Rotate270FlipNone);
            break;
    }
    // This EXIF data is now invalid and should be removed.
    img.RemovePropertyItem(274);
}
110
ReenignE

От этот пост похоже, вам нужно проверить ID 274

foreach (PropertyItem p in properties) {
      if (p.Id == 274) {
            Orientation = (int)p.Value[0];
         if (Orientation == 6)
            oldImage.RotateFlip(RotateFlipType.Rotate90FlipNone);
         if (Orientation == 8)
            oldImage.RotateFlip(RotateFlipType.Rotate270FlipNone);
      break;
      }
}
15
Bala R

Я объединил данные ответы и комментарии и придумал это:

    MemoryStream stream = new MemoryStream(data);
    Image image = Image.FromStream(stream);

    foreach (var prop in image.PropertyItems) {
        if ((prop.Id == 0x0112 || prop.Id == 5029 || prop.Id == 274)) {
            var value = (int)prop.Value[0];
            if (value == 6) {
                image.RotateFlip(RotateFlipType.Rotate90FlipNone);
                break;
            } else if (value == 8) {
                image.RotateFlip(RotateFlipType.Rotate270FlipNone);
                break;
            } else if (value == 3) {
                image.RotateFlip(RotateFlipType.Rotate180FlipNone);
                break;
            } 
        }
    }
12
Ron Burgundy

Размещение здесь на тот случай, если у кого-то возникнет такая же проблема. У меня были проблемы при чтении ориентации при использовании WFP и GDI. Единственное, что сработало, было использовать: https://github.com/dlemstra/Magick.NET

Код довольно прост:

var img = new MagickImage(inputStream);
img.AutoOrient();   // Fix orientation
img.Strip();        // remove all EXIF information
img.Write(outputPath);
0
Diego Jancic