- package osm.jp.gpx;
-
- import java.io.*;
- import java.nio.channels.FileChannel;
- import java.text.DateFormat;
- import java.text.DecimalFormat;
- import java.text.ParseException;
- import java.text.SimpleDateFormat;
- import java.util.ArrayList;
- import java.util.Arrays;
- import java.util.Calendar;
- import java.util.Comparator;
- import java.util.Date;
- import java.util.Map;
- import java.util.ResourceBundle;
- import java.util.TimeZone;
- import java.util.logging.LogManager;
- import java.util.logging.Logger;
-
- import javax.xml.parsers.*;
- import javax.xml.transform.TransformerException;
-
- import org.apache.commons.imaging.ImageReadException;
- import org.apache.commons.imaging.ImageWriteException;
- import org.apache.commons.imaging.Imaging;
- import org.apache.commons.imaging.common.ImageMetadata;
- import org.apache.commons.imaging.common.RationalNumber;
- import org.apache.commons.imaging.formats.jpeg.JpegImageMetadata;
- import org.apache.commons.imaging.formats.jpeg.exif.ExifRewriter;
- 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.write.TiffOutputDirectory;
- import org.apache.commons.imaging.formats.tiff.write.TiffOutputSet;
- import org.w3c.dom.*;
- import org.xml.sax.SAXException;
-
- public class ImportPicture extends Thread {
-
- /**
- * 実行中に発生したExceptionを保持する場所
- */
- public Exception ex = null;
-
- /**
- * ログ設定プロパティファイルのファイル内容
- */
- protected static final String LOGGING_PROPERTIES_DATA
- = "handlers=java.util.logging.ConsoleHandler\n"
- + ".level=FINEST\n"
- + "java.util.logging.ConsoleHandler.level=INFO\n"
- + "java.util.logging.ConsoleHandler.formatter=osm.jp.gpx.YuuLogFormatter";
-
- /**
- * static initializer によるログ設定の初期化
- */
- public static final Logger LOGGER = Logger.getLogger("CommandLogging");
- static {
- InputStream inStream = null;
- try {
- inStream = new ByteArrayInputStream(LOGGING_PROPERTIES_DATA.getBytes("UTF-8"));
- try {
- LogManager.getLogManager().readConfiguration(inStream);
- // "ログ設定: LogManagerを設定しました。"
- LOGGER.config("LoggerSettings: LogManager setuped.");
- }
- catch (IOException e) {
- // LogManager設定の際に例外が発生しました.
- String str = "LoggerSettings: Exception occered:" + e.toString();
- LOGGER.warning(str);
- }
- }
- catch (UnsupportedEncodingException e) {
- String str = "LoggerSettings: Not supported 'UTF-8' encoding: " + e.toString();
- LOGGER.severe(str);
- }
- finally {
- try {
- if (inStream != null) {
- inStream.close();
- }
- } catch (IOException e) {
- String str = "LoggerSettings: Exception occored: "+ e.toString();
- LOGGER.warning(str);
- }
- }
- }
-
- /** メイン
- * 画像ファイルをGPXファイルに取り込みます。
- *
- * ・画像ファイルの更新日付をその画像の撮影日時とします。(Exi情報は無視します)
- * ※ 対象とするファイルは'*.jpg'のみ
- * ・精確な時刻との時差を入力することで、撮影日時を補正します。
- * ・画像ファイルの更新日付リストをCSV形式のファイルとして出力する。
- * ・・結果は、取り込み元のGPXファイルとは別に、元ファイル名にアンダーバー「_」を付加した.ファイルに出力します。
- *
- * exp) $ java -cp .:AdjustTime.jar:commons-imaging-1.0-SNAPSHOT.jar [AdjustTime.ini]
- * exp) > java -cp .;AdjustTime.jar;commons-imaging-1.0-SNAPSHOT.jar [AdjustTime.ini]
- *
- * @param argv
- * argv[0] = INIファイルのパス名
- *
- * argv[-] = dummy
- * argv[0] = 画像ファイルが格納されているディレクトリ --> imgDir
- * argv[1] = 時刻補正の基準とする画像ファイル --> baseFile
- * argv[2] = 基準画像ファイルの精確な撮影日時 "yyyy-MM-dd'T'HH:mm:ss" --> timeStr
- * argv[3] = 出力先フォルダ --> outDir
- * argv[4] = 撮影位置をロギングしたGPXファイル --> gpxDir
- *
- * @throws IOException
- * @throws ImageReadException
- */
- public static void main(String[] argv) throws Exception
- {
- ImportPicture obj = new ImportPicture();
- obj.setUp(((argv.length < 1) ? AppParameters.FILE_PATH : argv[0]));
- }
-
- public File gpxDir;
- public File imgDir;
- public File outDir;
- public long delta = 0;
- public boolean exif = false;
- public boolean exifBase = false;
- public ArrayList<File> gpxFiles = new ArrayList<>();
- public AppParameters params;
- public boolean param_GpxSplit = false;
- public static boolean param_GpxNoFirstNode = false;
- public boolean param_GpxReuse = false;
- public boolean param_GpxOutputWpt = true;
- public boolean param_ImgOutputAll = false;
- public String param_GpxSourceFolder = ".";
-
- public static final String TIME_FORMAT_STRING = "yyyy-MM-dd'T'HH:mm:ss'Z'";
- private static final String EXIF_DATE_TIME_FORMAT_STRING = "yyyy:MM:dd HH:mm:ss";
- public ResourceBundle i18n = ResourceBundle.getBundle("i18n");
-
- public void setUp(String paramFilePath) throws Exception {
- System.out.println("Param File = '"+ paramFilePath +"'");
- this.params = new AppParameters(paramFilePath);
-
- Date imgtime;
-
- System.out.println(" - param: "+ AppParameters.IMG_TIME +"="+ this.params.getProperty(AppParameters.IMG_TIME) );
- System.out.println(" - param: "+ AppParameters.IMG_BASE_FILE +"="+ this.params.getProperty(AppParameters.IMG_BASE_FILE) );
- System.out.println(" - param: "+ AppParameters.GPX_BASETIME +"="+ this.params.getProperty(AppParameters.GPX_BASETIME) );
- System.out.println(" - param: "+ AppParameters.IMG_SOURCE_FOLDER +"="+ this.params.getProperty(AppParameters.IMG_SOURCE_FOLDER) );
- System.out.println(" - param: "+ AppParameters.IMG_OUTPUT_FOLDER +"="+ this.params.getProperty(AppParameters.IMG_OUTPUT_FOLDER) );
- System.out.println(" - param: "+ AppParameters.IMG_OUTPUT +"="+ this.params.getProperty(AppParameters.IMG_OUTPUT));
- System.out.println(" - param: "+ AppParameters.IMG_OUTPUT_ALL +"="+ this.param_ImgOutputAll);
- System.out.println(" - param: "+ AppParameters.IMG_OUTPUT_EXIF +"= "+ String.valueOf(this.exif));
- System.out.println(" - param: "+ AppParameters.GPX_SOURCE_FOLDER +"="+ this.param_GpxSourceFolder);
- System.out.println(" - param: "+ AppParameters.GPX_OUTPUT_WPT +"="+ this.param_GpxOutputWpt);
- System.out.println(" - param: "+ AppParameters.GPX_OVERWRITE_MAGVAR +"="+ Complementation.param_GpxOverwriteMagvar);
- System.out.println(" - param: "+ AppParameters.GPX_OUTPUT_SPEED +"="+ Complementation.param_GpxOutputSpeed);
- System.out.println(" - param: "+ AppParameters.GPX_GPXSPLIT +"="+ this.param_GpxSplit);
- System.out.println(" - param: "+ AppParameters.GPX_NO_FIRST_NODE +"="+ ImportPicture.param_GpxNoFirstNode);
- System.out.println(" - param: "+ AppParameters.GPX_REUSE +"="+ this.param_GpxReuse);
-
- this.ex = null;
- // argv[0] --> AppParameters.IMG_SOURCE_FOLDER に置き換え
- this.imgDir = new File(this.params.getProperty(AppParameters.IMG_SOURCE_FOLDER));
-
- // 基準時刻(ファイル更新日時 | EXIF撮影日時)
- this.exifBase = (this.params.getProperty(AppParameters.GPX_BASETIME).equals("EXIF_TIME"));
-
- // 基準時刻ファイルの「更新日時」を使って時刻合わせを行う。
- // argv[1] --> AppParameters.IMG_BASE_FILE に置き換え
- imgtime = this.adjustTime(new File(this.imgDir, this.params.getProperty(AppParameters.IMG_BASE_FILE)));
-
- // 出力ファイル
- // argv[3] --> AppParameters.IMG_OUTPUT に置き換え
- this.outDir = new File(this.params.getProperty(AppParameters.IMG_OUTPUT_FOLDER));
-
- // その他のパラメータを読み取る
- String paramStr = this.params.getProperty(AppParameters.GPX_GPXSPLIT);
- if ((paramStr != null) && (paramStr.equals(Boolean.toString(true)))) {
- this.param_GpxSplit = true;
- }
-
- paramStr = this.params.getProperty(AppParameters.GPX_NO_FIRST_NODE);
- if ((paramStr != null) && (paramStr.equals(Boolean.toString(true)))) {
- ImportPicture.param_GpxNoFirstNode = true;
- }
-
- paramStr = this.params.getProperty(AppParameters.GPX_REUSE);
- if ((paramStr != null) && (paramStr.equals(Boolean.toString(true)))) {
- this.param_GpxReuse = true;
- }
-
- paramStr = this.params.getProperty(AppParameters.IMG_OUTPUT_ALL);
- if ((paramStr != null) && (paramStr.equals(Boolean.toString(true)))) {
- this.param_ImgOutputAll = true;
- }
-
- paramStr = this.params.getProperty(AppParameters.GPX_OUTPUT_WPT);
- if ((paramStr != null) && (paramStr.equals(Boolean.toString(true)))) {
- this.param_GpxOutputWpt = true;
- }
-
- paramStr = this.params.getProperty(AppParameters.GPX_OVERWRITE_MAGVAR);
- if ((paramStr != null) && (paramStr.equals(Boolean.toString(true)))) {
- Complementation.param_GpxOverwriteMagvar = true;
- }
-
- paramStr = this.params.getProperty(AppParameters.GPX_OUTPUT_SPEED);
- if ((paramStr != null) && (paramStr.equals(Boolean.toString(true)))) {
- Complementation.param_GpxOutputSpeed = true;
- }
-
- paramStr = this.params.getProperty(AppParameters.GPX_SOURCE_FOLDER);
- if (paramStr != null) {
- this.param_GpxSourceFolder = paramStr;
- this.gpxDir = new File(this.param_GpxSourceFolder);
- if (!this.gpxDir.exists()) {
- // GPXファイルまたはディレクトリが存在しません。('%s')
- System.out.println(
- String.format(i18n.getString("msg.100"), paramStr)
- );
- return;
- }
- }
- else {
- this.gpxDir = this.imgDir;
- }
-
- // 指定されたディレクトリ内のGPXファイルすべてを対象とする
- if (this.gpxDir.isDirectory()) {
- File[] files = this.gpxDir.listFiles();
- if (files == null) {
- // 対象となるGPXファイルがありませんでした。('%s')
- System.out.println(
- String.format(i18n.getString("msg.110"), this.gpxDir.getAbsolutePath())
- );
- return;
- }
- if (this.param_ImgOutputAll && (files.length > 1)) {
- // "複数のGPXファイルがあるときには、'IMG.OUTPUT_ALL'オプションは指定できません。"
- System.out.println(
- i18n.getString("msg.120")
- );
- return;
- }
-
- java.util.Arrays.sort(
- files, new java.util.Comparator<File>() {
- @Override
- public int compare(File file1, File file2){
- return file1.getName().compareTo(file2.getName());
- }
- }
- );
- for (File file : files) {
- if (file.isFile()) {
- String filename = file.getName().toUpperCase();
- if (filename.toUpperCase().endsWith(".GPX")) {
- if (!filename.toUpperCase().endsWith("_.GPX") || this.param_GpxReuse) {
- this.gpxFiles.add(file);
- }
- }
- }
- }
- }
- else {
- this.gpxFiles.add(this.gpxDir);
- }
-
- paramStr = this.params.getProperty(AppParameters.IMG_OUTPUT_EXIF);
- if ((paramStr != null) && (paramStr.equals(Boolean.toString(true)))) {
- this.exif = true;
- }
-
- String timeStr = this.params.getProperty(AppParameters.IMG_TIME);
- try {
- Date t = toUTCDate(timeStr);
- this.delta = t.getTime() - imgtime.getTime();
- }
- catch (ParseException e) {
- // "'%s'の書式が違います(%s)"
- System.out.println(
- String.format(
- i18n.getString("msg.130"),
- timeStr,
- TIME_FORMAT_STRING
- )
- );
- return;
- }
-
- this.start();
- try {
- this.join();
- } catch(InterruptedException end) {}
- if (this.ex != null) {
- throw this.ex;
- }
- }
-
- /**
- * @code{
- <wpt lat="35.25714922" lon="139.15490497">
- <ele>62.099998474121094</ele>
- <time>2012-06-11T00:44:38Z</time>
- <hdop>0.75</hdop>
- <name><![CDATA[写真]]></name>
- <cmt><![CDATA[精度: 3.0m]]></cmt>
- <link href="2012-06-11_09-44-38.jpg">
- <text>2012-06-11_09-44-38.jpg</text>
- </link>
- <sat>9</sat>
- </wpt>
- * }
- */
- @Override
- public void run() {
- try {
- if (params.getProperty(AppParameters.IMG_OUTPUT).equals(Boolean.toString(true))) {
- outDir = new File(outDir, imgDir.getName());
- }
- else {
- outDir = gpxDir;
- }
- for (File gpxFile : this.gpxFiles) {
- procGPXfile(new GpxFile(gpxFile));
- }
- }
- catch(ParserConfigurationException | DOMException | SAXException | IOException | ParseException | ImageReadException | ImageWriteException | IllegalArgumentException | TransformerException e) {
- e.printStackTrace();
- this.ex = new Exception(e);
- }
- }
-
- /**
- * 個別のGPXファイルを処理する
- *
- * @throws ParserConfigurationException
- * @throws IOException
- * @throws SAXException
- * @throws ParseException
- * @throws ImageWriteException
- * @throws ImageReadException
- * @throws TransformerException
- */
- void procGPXfile(GpxFile gpxFile) throws ParserConfigurationException, SAXException, IOException, ParseException, ImageReadException, ImageWriteException, TransformerException {
- System.gc();
-
- System.out.println("time difference: "+ (delta / 1000) +"(sec)");
- System.out.println(" Target GPX: ["+ gpxFile.getAbsolutePath() +"]");
- System.out.println(" EXIF: "+ (exif ? ("convert to '" + outDir.getAbsolutePath() +"'") : "off"));
- System.out.println();
-
- // imgDir内の画像ファイルを処理する
- System.out.println("|--------------------------------|--------------------|--------------------|--------------|--------------|--------|------|------|");
- System.out.println("| name | Camera Time | GPStime | Latitude | Longitude | ele |magvar| km/h |");
- System.out.println("|--------------------------------|--------------------|--------------------|--------------|--------------|--------|------|------|");
- boolean out = proc(imgDir, delta, gpxFile.mapTRKSEG, exif, gpxFile);
- System.out.println("|--------------------------------|--------------------|--------------------|--------------|--------------|--------|------|------|");
- if (out) {
- // GPX出力
- gpxFile.output(outDir);
- }
- }
-
- /**
- * 再帰メソッド
- * @throws ParseException
- * @throws IOException
- * @throws ImageReadException
- * @throws ImageWriteException
- */
- boolean proc(File dir, long delta, ElementMapTRKSEG mapTRKSEG, boolean exifWrite, GpxFile gpxFile) throws ParseException, ImageReadException, IOException, ImageWriteException {
- boolean ret = false;
- File[] files = dir.listFiles(new JpegFileFilter());
- Arrays.sort(files, new FileSort());
- for (File image : files) {
- System.out.print(String.format("|%-32s|", image.getName()));
- if (image.isDirectory()) {
- ret = proc(image, delta, mapTRKSEG, exifWrite, gpxFile);
- continue;
- }
-
- String imageName = image.getName();
- if (!checkFile(imageName)) {
- System.out.println(String.format("%20s ", "it is not image file."));
- continue;
- }
-
- Discripter result = procImageFile(image, delta, mapTRKSEG, exifWrite, gpxFile);
- ret |= result.ret;
- switch (result.control) {
- case Discripter.CONTINUE:
- continue;
- case Discripter.BREAK:
- break;
- }
- }
- return ret;
- }
-
- class Discripter {
- static final int NEXT = 0;
- static final int CONTINUE = -1;
- static final int BREAK = 1;
-
- public boolean ret;
- public int control;
- public Discripter(boolean ret) {
- this.ret = ret;
- this.control = Discripter.NEXT;
- }
- }
-
- Discripter procImageFile(File imageFile, long delta, ElementMapTRKSEG mapTRKSEG, boolean exifWrite, GpxFile gpxFile) throws ParseException, ImageReadException, IOException, ImageWriteException {
- Discripter result = new Discripter(false);
-
- // itime <-- 画像ファイルの撮影時刻
- // ファイルの更新日時/EXIFの撮影日時
- Date itime = new Date(imageFile.lastModified());
- if (this.exifBase) {
- ImageMetadata meta = Imaging.getMetadata(imageFile);
- JpegImageMetadata jpegMetadata = (JpegImageMetadata)meta;
- if (jpegMetadata == null) {
- // "'%s'にEXIF情報がありません"
- System.out.println(
- String.format(
- i18n.getString("msg.140"),
- imageFile.getAbsolutePath()
- )
- );
- result.control = Discripter.CONTINUE;
- return result;
- }
- TiffImageMetadata exif = jpegMetadata.getExif();
- if (exif == null) {
- // "'%s'にEXIF情報がありません"
- System.out.println(
- String.format(
- i18n.getString("msg.140"),
- imageFile.getAbsolutePath()
- )
- );
- result.control = Discripter.CONTINUE;
- return result;
- }
- String dateTimeOriginal = exif.getFieldValue(ExifTagConstants.EXIF_TAG_DATE_TIME_ORIGINAL)[0];
- itime = ImportPicture.toEXIFDate(dateTimeOriginal);
- }
- System.out.print(String.format("%20s|", toUTCString(itime)));
-
- // uktime <-- 画像撮影時刻に対応するGPX時刻(補正日時)
- Date correctedtime = new Date(itime.getTime() + delta);
- System.out.print(String.format("%20s|", toUTCString(correctedtime)));
-
- // 時刻uktimeにおける<magver>をtrkptに追加する
- String eleStr = "-";
- String magvarStr = "-";
- String speedStr = "-";
- TagTrkpt trkptT = null;
-
- for (Map.Entry<Date,ElementMapTRKPT> map : mapTRKSEG.entrySet()) {
- ElementMapTRKPT mapTRKPT = map.getValue();
- trkptT = mapTRKPT.getValue(correctedtime);
- if (trkptT != null) {
- break;
- }
- }
-
- if (trkptT == null) {
- System.out.print(String.format("%-14s|%-14s|", "", ""));
- System.out.println(String.format("%8s|%6s|%6s|", "", "", ""));
- if (!this.param_ImgOutputAll) {
- result.control = Discripter.CONTINUE;
- return result;
- }
- }
- else {
- double latitude = trkptT.lat;
- double longitude = trkptT.lon;
-
- if (trkptT.eleStr != null) {
- eleStr = trkptT.eleStr;
- }
-
- if (trkptT.magvarStr != null) {
- magvarStr = trkptT.magvarStr;
- }
-
- if (trkptT.speedStr != null) {
- speedStr = trkptT.speedStr;
- }
- System.out.print(String.format("%14.10f|%14.10f|", latitude, longitude));
- System.out.println(String.format("%8s|%6s|%6s|", eleStr, magvarStr, speedStr));
- }
-
- result.ret = true;
- outDir.mkdir();
-
- if (exifWrite) {
- exifWrite(imageFile, correctedtime, trkptT);
-
- if (Boolean.parseBoolean(params.getProperty(AppParameters.GPX_OUTPUT_WPT))) {
- if (trkptT != null) {
- Element temp = gpxFile.createWptTag(imageFile, imgDir, itime.getTime(), trkptT.trkpt);
- gpxFile.gpx.appendChild(temp);
- }
- }
- }
- else {
- if (this.param_ImgOutputAll) {
- // EXIFの変換を伴わない単純なファイルコピー
- FileInputStream sStream = new FileInputStream(imageFile);
- FileInputStream dStream = new FileInputStream(new File(outDir, imageFile.getName()));
- FileChannel srcChannel = sStream.getChannel();
- FileChannel destChannel = dStream.getChannel();
- try {
- srcChannel.transferTo(0, srcChannel.size(), destChannel);
- }
- finally {
- srcChannel.close();
- destChannel.close();
- sStream.close();
- dStream.close();
- }
- }
- }
- result.control = Discripter.NEXT;
- return result;
- }
-
- void exifWrite(File imageFile, Date correctedtime, TagTrkpt trkptT) throws ImageReadException, IOException, ImageWriteException {
- DecimalFormat yearFormatter = new DecimalFormat("0000");
- DecimalFormat monthFormatter = new DecimalFormat("00");
- DecimalFormat dayFormatter = new DecimalFormat("00");
-
- TiffOutputSet outputSet = null;
-
- ImageMetadata meta = Imaging.getMetadata(imageFile);
- JpegImageMetadata jpegMetadata = (JpegImageMetadata)meta;
- if (jpegMetadata != null) {
- TiffImageMetadata exif = jpegMetadata.getExif();
- if (exif != null) {
- outputSet = exif.getOutputSet();
- }
- }
-
- if (outputSet == null) {
- outputSet = new TiffOutputSet();
- }
-
- //---- EXIF_TAG_DATE_TIME_ORIGINAL / 「撮影日時/オリジナル画像の生成日時」----
- TiffOutputDirectory exifDir = outputSet.getOrCreateExifDirectory();
- {
- Calendar cal = Calendar.getInstance();
- cal.setTimeZone(TimeZone.getTimeZone("UTC"));
- cal.setTime(correctedtime);
- exifDir.removeField(ExifTagConstants.EXIF_TAG_DATE_TIME_ORIGINAL);
- exifDir.add(ExifTagConstants.EXIF_TAG_DATE_TIME_ORIGINAL, ImportPicture.toEXIFString(cal.getTime()));
- }
-
- //---- EXIF GPS_TIME_STAMP ----
- TiffOutputDirectory gpsDir = outputSet.getOrCreateGPSDirectory();
- {
- Calendar cal = Calendar.getInstance(TimeZone.getTimeZone("UTC"));
- cal.setTimeZone(TimeZone.getTimeZone("GMT+00"));
- cal.setTime(correctedtime);
- final String yearStr = yearFormatter.format(cal.get(Calendar.YEAR));
- final String monthStr = monthFormatter.format(cal.get(Calendar.MONTH) + 1);
- final String dayStr = dayFormatter.format(cal.get(Calendar.DAY_OF_MONTH));
- final String dateStamp = yearStr +":"+ monthStr +":"+ dayStr;
-
- gpsDir.removeField(GpsTagConstants.GPS_TAG_GPS_TIME_STAMP);
- gpsDir.add(
- GpsTagConstants.GPS_TAG_GPS_TIME_STAMP,
- RationalNumber.valueOf(cal.get(Calendar.HOUR_OF_DAY)),
- RationalNumber.valueOf(cal.get(Calendar.MINUTE)),
- RationalNumber.valueOf(cal.get(Calendar.SECOND))
- );
- gpsDir.removeField(GpsTagConstants.GPS_TAG_GPS_DATE_STAMP);
- gpsDir.add(GpsTagConstants.GPS_TAG_GPS_DATE_STAMP, dateStamp);
- }
-
- if (trkptT != null) {
- //---- EXIF GPS elevation/ALTITUDE ----
- if (trkptT.eleStr != null) {
- final double altitude = Double.parseDouble(trkptT.eleStr);
- gpsDir.removeField(GpsTagConstants.GPS_TAG_GPS_ALTITUDE);
- gpsDir.add(GpsTagConstants.GPS_TAG_GPS_ALTITUDE, RationalNumber.valueOf(altitude));
- }
-
- //---- EXIF GPS magvar/IMG_DIRECTION ----
- if (trkptT.magvarStr != null) {
- final double magvar = Double.parseDouble(trkptT.magvarStr);
- gpsDir.removeField(GpsTagConstants.GPS_TAG_GPS_IMG_DIRECTION);
- gpsDir.add(GpsTagConstants.GPS_TAG_GPS_IMG_DIRECTION, RationalNumber.valueOf(magvar));
- }
-
- //---- EXIF GPS_ ----
- outputSet.setGPSInDegrees(trkptT.lon, trkptT.lat);
- }
-
- ExifRewriter rewriter = new ExifRewriter();
- try (FileOutputStream fos = new FileOutputStream(new File(outDir, imageFile.getName()))) {
- rewriter.updateExifMetadataLossy(imageFile, fos, outputSet);
- }
- }
-
- // 基準時刻ファイルの「更新日時」を使って時刻合わせを行う。
- // argv[1] --> AppParameters.IMG_BASE_FILE に置き換え
- // File baseFile = new File(this.imgDir, this.params.getProperty(AppParameters.IMG_BASE_FILE));
- private Date adjustTime(File baseFile) throws ImageReadException, IOException, ParseException {
- if (exifBase) {
- ImageMetadata meta = Imaging.getMetadata(baseFile);
- JpegImageMetadata jpegMetadata = (JpegImageMetadata)meta;
- if (jpegMetadata == null) {
- // "'%s'にEXIF情報がありません"
- System.out.println(
- String.format(
- i18n.getString("msg.140"),
- baseFile.getAbsolutePath()
- )
- );
- return null;
- }
- TiffImageMetadata exif = jpegMetadata.getExif();
- if (exif == null) {
- // "'%s'にEXIF情報がありません"
- System.out.println(
- String.format(
- i18n.getString("msg.140"),
- baseFile.getAbsolutePath()
- )
- );
- return null;
- }
- String dateTimeOriginal = exif.getFieldValue(ExifTagConstants.EXIF_TAG_DATE_TIME_ORIGINAL)[0];
- return new Date(ImportPicture.toEXIFDate(dateTimeOriginal).getTime());
- }
- else {
- return new Date(baseFile.lastModified());
- }
- }
-
- /**
- * 対象は '*.JPG' のみ対象とする
- * @return
- * @param name
- */
- public static boolean checkFile(String name) {
- return ((name != null) && name.toUpperCase().endsWith(".JPG"));
- }
-
- /**
- * DateをEXIFの文字列に変換する。
- * 注意:EXiFの撮影時刻はUTC時間ではない
- * @param localdate
- * @return
- */
- public static String toEXIFString(Date localdate) {
- DateFormat dfUTC = new SimpleDateFormat(EXIF_DATE_TIME_FORMAT_STRING);
- return dfUTC.format(localdate);
- }
-
- /**
- * EXIFの文字列をDateに変換する。
- * 注意:EXiFの撮影時刻はUTC時間ではない
- * @param timeStr
- * @return
- * @throws ParseException
- */
- public static Date toEXIFDate(String timeStr) throws ParseException {
- DateFormat dfUTC = new SimpleDateFormat(EXIF_DATE_TIME_FORMAT_STRING);
- //dfUTC.setTimeZone(TimeZone.getTimeZone("UTC"));
- return dfUTC.parse(timeStr);
- }
-
- public static String toUTCString(Date localdate) {
- DateFormat dfUTC = new SimpleDateFormat(TIME_FORMAT_STRING);
- dfUTC.setTimeZone(TimeZone.getTimeZone("UTC"));
- return dfUTC.format(localdate);
- }
-
- public static Date toUTCDate(String timeStr) throws ParseException {
- DateFormat dfUTC = new SimpleDateFormat(TIME_FORMAT_STRING);
- dfUTC.setTimeZone(TimeZone.getTimeZone("UTC"));
- return dfUTC.parse(timeStr);
- }
-
- static String getShortPathName(File dir, File iFile) {
- String dirPath = dir.getAbsolutePath();
- String filePath = iFile.getAbsolutePath();
- if (filePath.startsWith(dirPath)) {
- return filePath.substring(dirPath.length()+1);
- }
- else {
- return filePath;
- }
- }
-
- /**
- * ファイル名の順序に並び替えるためのソートクラス
- *
- * @author hayashi
- */
- static class FileSort implements Comparator<File> {
- @Override
- public int compare(File src, File target){
- int diff = src.getName().compareTo(target.getName());
- return diff;
- }
- }
-
- /**
- * JPEGファイルフィルター
- * @author yuu
- */
- class JpegFileFilter implements FilenameFilter {
- @Override
- public boolean accept(File dir, String name) {
- return name.toUpperCase().matches(".*\\.JPG$");
- }
- }
- }