如何使用 Java 读取 JPEG 文件属性?
声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow
原文地址: http://stackoverflow.com/questions/19224328/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me):
StackOverFlow
How to read JPEG file attributes with Java?
提问by Sujeeth
I want to read information from an image (jpg) which has some extra information included from a digital camera like creation date, focus, flash on off, ... How can I get this information.
我想从一个图像 (jpg) 中读取信息,其中包含来自数码相机的一些额外信息,如创建日期、焦点、闪光灯关闭……我如何获得这些信息。
My first idea was.
我的第一个想法是。
BufferedImage image = ImageIO.read(filePicture);
if (image().getPropertyNames() != null) {
for (int j = 0; j < image().getPropertyNames().length; j++) {
String key = image().getPropertyNames()[j];
String value = (String) image().getProperty(key);
System.out.println(key + ": " + value);
}
}
But the getPropertyNames() returns null!
但是 getPropertyNames() 返回 null!
回答by Daniel Ruf
I would suggest using http://commons.apache.org/proper/commons-imaging/which can read EXIF data and other formats (IPTC, XMP ...)
我建议使用http://commons.apache.org/proper/commons-imaging/它可以读取 EXIF 数据和其他格式(IPTC、XMP ...)
there are also some examples: http://commons.apache.org/proper/commons-imaging/sampleusage.html
还有一些例子:http: //commons.apache.org/proper/commons-imaging/sampleusage.html
What you need: https://svn.apache.org/repos/asf/commons/proper/imaging/trunk/src/test/java/org/apache/commons/imaging/examples/MetadataExample.java
你需要什么:https: //svn.apache.org/repos/asf/commons/proper/imaging/trunk/src/test/java/org/apache/commons/imaging/examples/MetadataExample.java
/*
* Licensed to the Apache Software Foundation (ASF) under one or more
* contributor license agreements. See the NOTICE file distributed with
* this work for additional information regarding copyright ownership.
* The ASF licenses this file to You under the Apache License, Version 2.0
* (the "License"); you may not use this file except in compliance with
* the License. You may obtain a copy of the License at
*
* http://www.apache.org/licenses/LICENSE-2.0
*
* Unless required by applicable law or agreed to in writing, software
* distributed under the License is distributed on an "AS IS" BASIS,
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
* See the License for the specific language governing permissions and
* limitations under the License.
*/
package org.apache.commons.imaging.examples;
import java.io.File;
import java.io.IOException;
import java.util.List;
import org.apache.commons.imaging.ImageReadException;
import org.apache.commons.imaging.Imaging;
import org.apache.commons.imaging.common.ImageMetadata;
import org.apache.commons.imaging.common.ImageMetadata.ImageMetadataItem;
import org.apache.commons.imaging.common.RationalNumber;
import org.apache.commons.imaging.formats.jpeg.JpegImageMetadata;
import org.apache.commons.imaging.formats.tiff.TiffField;
import org.apache.commons.imaging.formats.tiff.TiffImageMetadata;
import org.apache.commons.imaging.formats.tiff.constants.ExifTagConstants;
import org.apache.commons.imaging.formats.tiff.constants.GpsTagConstants;
import org.apache.commons.imaging.formats.tiff.constants.TiffTagConstants;
import org.apache.commons.imaging.formats.tiff.taginfos.TagInfo;
public class MetadataExample {
public static void metadataExample(final File file) throws ImageReadException,
IOException {
// get all metadata stored in EXIF format (ie. from JPEG or TIFF).
final ImageMetadata metadata = Imaging.getMetadata(file);
// System.out.println(metadata);
if (metadata instanceof JpegImageMetadata) {
final JpegImageMetadata jpegMetadata = (JpegImageMetadata) metadata;
// Jpeg EXIF metadata is stored in a TIFF-based directory structure
// and is identified with TIFF tags.
// Here we look for the "x resolution" tag, but
// we could just as easily search for any other tag.
//
// see the TiffConstants file for a list of TIFF tags.
System.out.println("file: " + file.getPath());
// print out various interesting EXIF tags.
printTagValue(jpegMetadata, TiffTagConstants.TIFF_TAG_XRESOLUTION);
printTagValue(jpegMetadata, TiffTagConstants.TIFF_TAG_DATE_TIME);
printTagValue(jpegMetadata,
ExifTagConstants.EXIF_TAG_DATE_TIME_ORIGINAL);
printTagValue(jpegMetadata, ExifTagConstants.EXIF_TAG_DATE_TIME_DIGITIZED);
printTagValue(jpegMetadata, ExifTagConstants.EXIF_TAG_ISO);
printTagValue(jpegMetadata,
ExifTagConstants.EXIF_TAG_SHUTTER_SPEED_VALUE);
printTagValue(jpegMetadata,
ExifTagConstants.EXIF_TAG_APERTURE_VALUE);
printTagValue(jpegMetadata,
ExifTagConstants.EXIF_TAG_BRIGHTNESS_VALUE);
printTagValue(jpegMetadata,
GpsTagConstants.GPS_TAG_GPS_LATITUDE_REF);
printTagValue(jpegMetadata, GpsTagConstants.GPS_TAG_GPS_LATITUDE);
printTagValue(jpegMetadata,
GpsTagConstants.GPS_TAG_GPS_LONGITUDE_REF);
printTagValue(jpegMetadata, GpsTagConstants.GPS_TAG_GPS_LONGITUDE);
System.out.println();
// simple interface to GPS data
final TiffImageMetadata exifMetadata = jpegMetadata.getExif();
if (null != exifMetadata) {
final TiffImageMetadata.GPSInfo gpsInfo = exifMetadata.getGPS();
if (null != gpsInfo) {
final String gpsDescription = gpsInfo.toString();
final double longitude = gpsInfo.getLongitudeAsDegreesEast();
final double latitude = gpsInfo.getLatitudeAsDegreesNorth();
System.out.println(" " + "GPS Description: "
+ gpsDescription);
System.out.println(" "
+ "GPS Longitude (Degrees East): " + longitude);
System.out.println(" "
+ "GPS Latitude (Degrees North): " + latitude);
}
}
// more specific example of how to manually access GPS values
final TiffField gpsLatitudeRefField = jpegMetadata
.findEXIFValueWithExactMatch(GpsTagConstants.GPS_TAG_GPS_LATITUDE_REF);
final TiffField gpsLatitudeField = jpegMetadata
.findEXIFValueWithExactMatch(GpsTagConstants.GPS_TAG_GPS_LATITUDE);
final TiffField gpsLongitudeRefField = jpegMetadata
.findEXIFValueWithExactMatch(GpsTagConstants.GPS_TAG_GPS_LONGITUDE_REF);
final TiffField gpsLongitudeField = jpegMetadata
.findEXIFValueWithExactMatch(GpsTagConstants.GPS_TAG_GPS_LONGITUDE);
if (gpsLatitudeRefField != null && gpsLatitudeField != null
&& gpsLongitudeRefField != null
&& gpsLongitudeField != null) {
// all of these values are strings.
final String gpsLatitudeRef = (String) gpsLatitudeRefField.getValue();
final RationalNumber gpsLatitude[] = (RationalNumber[]) (gpsLatitudeField
.getValue());
final String gpsLongitudeRef = (String) gpsLongitudeRefField
.getValue();
final RationalNumber gpsLongitude[] = (RationalNumber[]) gpsLongitudeField
.getValue();
final RationalNumber gpsLatitudeDegrees = gpsLatitude[0];
final RationalNumber gpsLatitudeMinutes = gpsLatitude[1];
final RationalNumber gpsLatitudeSeconds = gpsLatitude[2];
final RationalNumber gpsLongitudeDegrees = gpsLongitude[0];
final RationalNumber gpsLongitudeMinutes = gpsLongitude[1];
final RationalNumber gpsLongitudeSeconds = gpsLongitude[2];
// This will format the gps info like so:
//
// gpsLatitude: 8 degrees, 40 minutes, 42.2 seconds S
// gpsLongitude: 115 degrees, 26 minutes, 21.8 seconds E
System.out.println(" " + "GPS Latitude: "
+ gpsLatitudeDegrees.toDisplayString() + " degrees, "
+ gpsLatitudeMinutes.toDisplayString() + " minutes, "
+ gpsLatitudeSeconds.toDisplayString() + " seconds "
+ gpsLatitudeRef);
System.out.println(" " + "GPS Longitude: "
+ gpsLongitudeDegrees.toDisplayString() + " degrees, "
+ gpsLongitudeMinutes.toDisplayString() + " minutes, "
+ gpsLongitudeSeconds.toDisplayString() + " seconds "
+ gpsLongitudeRef);
}
System.out.println();
final List<ImageMetadataItem> items = jpegMetadata.getItems();
for (int i = 0; i < items.size(); i++) {
final ImageMetadataItem item = items.get(i);
System.out.println(" " + "item: " + item);
}
System.out.println();
}
}
private static void printTagValue(final JpegImageMetadata jpegMetadata,
final TagInfo tagInfo) {
final TiffField field = jpegMetadata.findEXIFValueWithExactMatch(tagInfo);
if (field == null) {
System.out.println(tagInfo.name + ": " + "Not Found.");
} else {
System.out.println(tagInfo.name + ": "
+ field.getValueDescription());
}
}
}
回答by Drew Noakes
Another simple option is to use metadata-extractor:
另一个简单的选择是使用metadata-extractor:
Metadata metadata = ImageMetadataReader.readMetadata(imagePath);
To iterate all values in the file:
迭代文件中的所有值:
for (Directory directory : metadata.getDirectories()) {
for (Tag tag : directory.getTags()) {
System.out.println(tag);
}
}
You can also read specific values from specific directories:
您还可以从特定目录中读取特定值:
// obtain the Exif SubIFD directory
ExifSubIFDDirectory directory
= metadata.getFirstDirectoryOfType(ExifSubIFDDirectory.class);
// query the datetime tag's value
Date date = directory.getDate(ExifSubIFDDirectory.TAG_DATETIME_ORIGINAL);
The library is available for Maven users too.
该库也可供 Maven 用户使用。
(Full disclosure: I am the author of this library)
(完全披露:我是这个库的作者)
回答by inor
As others have suggested use http://commons.apache.org/proper/commons-imaging
正如其他人建议使用http://commons.apache.org/proper/commons-imaging
Download the jar from: https://repo.adobe.com/nexus/content/repositories/public/org/apache/commons/commons-imaging/1.0-R1534292/
从以下位置下载 jar:https: //repo.adobe.com/nexus/content/repositories/public/org/apache/commons/commons-imaging/1.0-R1534292/
You can see all the tags here: https://commons.apache.org/proper/commons-imaging/javadocs/api-release/org/apache/sanselan/formats/tiff/constants/AllTagConstants.html
您可以在此处查看所有标签:https: //commons.apache.org/proper/commons-imaging/javadocs/api-release/org/apache/sanselan/formats/tiff/constants/AllTagConstants.html
Here is how you would get the manufacturer and the model:
以下是获取制造商和型号的方法:
String fullFileName="D:/test/photos - orig/lg/20170204_143925.jpg";
File file = new File(fullFileName);
// get all metadata stored in EXIF format (ie. from JPEG or TIFF).
final IImageMetadata metadata = Imaging.getMetadata(file);
if (metadata instanceof JpegImageMetadata) {
final JpegImageMetadata jpegMetadata = (JpegImageMetadata) metadata;
String manufacturer = jpegMetadata.findEXIFValueWithExactMatch(TiffTagConstants.TIFF_TAG_MAKE).getStringValue();
String model = jpegMetadata.findEXIFValueWithExactMatch(TiffTagConstants.TIFF_TAG_MODEL).getStringValue();
System.out.println("Manufacturer: "+ manufacturer+", Model: " + model);
}