mirror of
https://github.com/xuthus83/pigallery2.git
synced 2024-11-03 21:04:03 +08:00
parent
83eeaf638f
commit
7653f2ce23
@ -1,7 +1,8 @@
|
||||
import {NextFunction, Request, Response} from 'express';
|
||||
import * as fs from 'fs';
|
||||
import { Config } from '../../common/config/private/Config';
|
||||
import { GPXProcessing } from '../model/fileprocessing/GPXProcessing';
|
||||
import {Config} from '../../common/config/private/Config';
|
||||
import {GPXProcessing} from '../model/fileprocessing/GPXProcessing';
|
||||
import {ErrorCodes, ErrorDTO} from '../../common/entities/Error';
|
||||
|
||||
export class MetaFileMWs {
|
||||
public static async compressGPX(
|
||||
@ -17,22 +18,31 @@ export class MetaFileMWs {
|
||||
return res.redirect(req.originalUrl.slice(0, -1 * '\\bestFit'.length));
|
||||
}
|
||||
const fullPath = req.resultPipe as string;
|
||||
try {
|
||||
const compressedGPX = GPXProcessing.generateConvertedPath(
|
||||
fullPath,
|
||||
);
|
||||
|
||||
const compressedGPX = GPXProcessing.generateConvertedPath(
|
||||
fullPath,
|
||||
);
|
||||
// check if converted photo exist
|
||||
if (fs.existsSync(compressedGPX) === true) {
|
||||
req.resultPipe = compressedGPX;
|
||||
return next();
|
||||
}
|
||||
|
||||
// check if converted photo exist
|
||||
if (fs.existsSync(compressedGPX) === true) {
|
||||
req.resultPipe = compressedGPX;
|
||||
return next();
|
||||
if (Config.MetaFile.GPXCompressing.onTheFly === true) {
|
||||
req.resultPipe = await GPXProcessing.compressGPX(fullPath);
|
||||
return next();
|
||||
}
|
||||
} catch (err) {
|
||||
|
||||
return next(
|
||||
new ErrorDTO(
|
||||
ErrorCodes.METAFILE_ERROR,
|
||||
'Error during compressingGPX: ' + fullPath,
|
||||
err
|
||||
)
|
||||
);
|
||||
}
|
||||
|
||||
if (Config.MetaFile.GPXCompressing.onTheFly === true) {
|
||||
req.resultPipe = await GPXProcessing.compressGPX(fullPath);
|
||||
return next();
|
||||
}
|
||||
|
||||
// not converted and won't be now
|
||||
return res.redirect(req.originalUrl.slice(0, -1 * '\\bestFit'.length));
|
||||
}
|
||||
|
@ -82,48 +82,49 @@ export class GPXProcessing {
|
||||
await fsp.mkdir(outDir, {recursive: true});
|
||||
const gpxStr = await fsp.readFile(filePath);
|
||||
const gpxObj = await (new xml2js.Parser()).parseStringPromise(gpxStr);
|
||||
const items: gpxEntry[] = gpxObj.gpx.trk[0].trkseg[0].trkpt;
|
||||
const items: gpxEntry[] = gpxObj.gpx?.trk?.[0]?.trkseg[0]?.trkpt;
|
||||
|
||||
const distance = (entry1: gpxEntry, entry2: gpxEntry) => {
|
||||
const lat1 = parseFloat(entry1.$.lat);
|
||||
const lon1 = parseFloat(entry1.$.lon);
|
||||
const lat2 = parseFloat(entry2.$.lat);
|
||||
const lon2 = parseFloat(entry2.$.lon);
|
||||
if (items) { // only compress paths
|
||||
const distance = (entry1: gpxEntry, entry2: gpxEntry) => {
|
||||
const lat1 = parseFloat(entry1.$.lat);
|
||||
const lon1 = parseFloat(entry1.$.lon);
|
||||
const lat2 = parseFloat(entry2.$.lat);
|
||||
const lon2 = parseFloat(entry2.$.lon);
|
||||
|
||||
// credits to: https://www.movable-type.co.uk/scripts/latlong.html
|
||||
const R = 6371e3; // metres
|
||||
const φ1 = lat1 * Math.PI / 180; // φ, λ in radians
|
||||
const φ2 = lat2 * Math.PI / 180;
|
||||
const Δφ = (lat2 - lat1) * Math.PI / 180;
|
||||
const Δλ = (lon2 - lon1) * Math.PI / 180;
|
||||
// credits to: https://www.movable-type.co.uk/scripts/latlong.html
|
||||
const R = 6371e3; // metres
|
||||
const φ1 = lat1 * Math.PI / 180; // φ, λ in radians
|
||||
const φ2 = lat2 * Math.PI / 180;
|
||||
const Δφ = (lat2 - lat1) * Math.PI / 180;
|
||||
const Δλ = (lon2 - lon1) * Math.PI / 180;
|
||||
|
||||
const a = Math.sin(Δφ / 2) * Math.sin(Δφ / 2) +
|
||||
Math.cos(φ1) * Math.cos(φ2) *
|
||||
Math.sin(Δλ / 2) * Math.sin(Δλ / 2);
|
||||
const c = 2 * Math.atan2(Math.sqrt(a), Math.sqrt(1 - a));
|
||||
const a = Math.sin(Δφ / 2) * Math.sin(Δφ / 2) +
|
||||
Math.cos(φ1) * Math.cos(φ2) *
|
||||
Math.sin(Δλ / 2) * Math.sin(Δλ / 2);
|
||||
const c = 2 * Math.atan2(Math.sqrt(a), Math.sqrt(1 - a));
|
||||
|
||||
const d = R * c; // in metres
|
||||
return d;
|
||||
};
|
||||
const gpxEntryFilter = (value: gpxEntry, i: number, list: gpxEntry[]) => {
|
||||
if (i === 0 || i >= list.length - 1) { // always keep the first and last items
|
||||
return true;
|
||||
}
|
||||
const timeDelta = (Date.parse(list[i].time[0]) - Date.parse(list[i - 1].time[0])); // mill sec.
|
||||
const dist = distance(list[i - 1], list[i]); // meters
|
||||
const d = R * c; // in metres
|
||||
return d;
|
||||
};
|
||||
const gpxEntryFilter = (value: gpxEntry, i: number, list: gpxEntry[]) => {
|
||||
if (i === 0 || i >= list.length - 1) { // always keep the first and last items
|
||||
return true;
|
||||
}
|
||||
const timeDelta = (Date.parse(list[i].time[0]) - Date.parse(list[i - 1].time[0])); // mill sec.
|
||||
const dist = distance(list[i - 1], list[i]); // meters
|
||||
|
||||
return !(timeDelta < Config.MetaFile.GPXCompressing.minTimeDistance &&
|
||||
dist < Config.MetaFile.GPXCompressing.minDistance);
|
||||
};
|
||||
|
||||
gpxObj.gpx.trk[0].trkseg[0].trkpt = items.filter(gpxEntryFilter).map((v) => {
|
||||
v.$.lon = parseFloat(v.$.lon).toFixed(6);
|
||||
v.$.lat = parseFloat(v.$.lat).toFixed(6);
|
||||
delete v.ele;
|
||||
delete v.extensions;
|
||||
return v;
|
||||
});
|
||||
return !(timeDelta < Config.MetaFile.GPXCompressing.minTimeDistance &&
|
||||
dist < Config.MetaFile.GPXCompressing.minDistance);
|
||||
};
|
||||
|
||||
gpxObj.gpx.trk[0].trkseg[0].trkpt = items.filter(gpxEntryFilter).map((v) => {
|
||||
v.$.lon = parseFloat(v.$.lon).toFixed(6);
|
||||
v.$.lat = parseFloat(v.$.lat).toFixed(6);
|
||||
delete v.ele;
|
||||
delete v.extensions;
|
||||
return v;
|
||||
});
|
||||
}
|
||||
await fsp.writeFile(outPath, (new xml2js.Builder({renderOpts: {pretty: false}})).buildObject(gpxObj));
|
||||
|
||||
return outPath;
|
||||
|
@ -7,24 +7,25 @@ export enum ErrorCodes {
|
||||
PERMISSION_DENIED = 4,
|
||||
CREDENTIAL_NOT_FOUND = 5,
|
||||
|
||||
USER_CREATION_ERROR = 6,
|
||||
USER_CREATION_ERROR = 20,
|
||||
|
||||
GENERAL_ERROR = 7,
|
||||
THUMBNAIL_GENERATION_ERROR = 8,
|
||||
PHOTO_GENERATION_ERROR = 9,
|
||||
PERSON_ERROR = 10,
|
||||
SERVER_ERROR = 11,
|
||||
GENERAL_ERROR = 31,
|
||||
THUMBNAIL_GENERATION_ERROR = 32,
|
||||
PHOTO_GENERATION_ERROR = 33,
|
||||
PERSON_ERROR = 34,
|
||||
METAFILE_ERROR = 35,
|
||||
SERVER_ERROR = 36,
|
||||
|
||||
USER_MANAGEMENT_DISABLED = 12,
|
||||
USER_MANAGEMENT_DISABLED = 40,
|
||||
|
||||
INPUT_ERROR = 13,
|
||||
INPUT_ERROR = 50,
|
||||
|
||||
SETTINGS_ERROR = 14,
|
||||
TASK_ERROR = 15,
|
||||
JOB_ERROR = 16,
|
||||
LocationLookUp_ERROR = 17,
|
||||
SETTINGS_ERROR = 60,
|
||||
TASK_ERROR = 61,
|
||||
JOB_ERROR = 62,
|
||||
LocationLookUp_ERROR = 63,
|
||||
|
||||
ALBUM_ERROR = 18,
|
||||
ALBUM_ERROR = 70,
|
||||
}
|
||||
|
||||
export class ErrorDTO {
|
||||
|
Loading…
Reference in New Issue
Block a user