Support geo located images & videos
This commit is contained in:
@@ -76,7 +76,7 @@ class Media extends PhpObject {
|
||||
if($bOwnMedia && empty($this->asMedia) || !$bOwnMedia && empty($this->asMedias) || $bConstraintArray) {
|
||||
if($this->oProject->getProjectId()) {
|
||||
$asParams = array(
|
||||
'select' => array(Db::getId(self::MEDIA_TABLE), 'filename', 'taken_on', 'posted_on', 'timezone', 'width', 'height', 'rotate', 'type AS subtype', 'comment'),
|
||||
'select' => array(Db::getId(self::MEDIA_TABLE), 'filename', 'taken_on', 'posted_on', 'timezone', 'latitude', 'longitude', 'width', 'height', 'rotate', 'type AS subtype', 'comment'),
|
||||
'from' => self::MEDIA_TABLE,
|
||||
'constraint'=> array(Db::getId(Project::PROJ_TABLE) => $this->oProject->getProjectId())
|
||||
);
|
||||
@@ -128,6 +128,9 @@ class Media extends PhpObject {
|
||||
'taken_on' => date(Db::TIMESTAMP_FORMAT, ($asMediaInfo['taken_ts'] > 0)?$asMediaInfo['taken_ts']:$asMediaInfo['file_ts']),
|
||||
'posted_on' => date(Db::TIMESTAMP_FORMAT, $asMediaInfo['file_ts']),
|
||||
'timezone' => $asMediaInfo['timezone'],
|
||||
'latitude' => $asMediaInfo['latitude'],
|
||||
'longitude' => $asMediaInfo['longitude'],
|
||||
'altitude' => $asMediaInfo['altitude'],
|
||||
'width' => $asMediaInfo['width'],
|
||||
'height' => $asMediaInfo['height'],
|
||||
'rotate' => $asMediaInfo['rotate'],
|
||||
@@ -151,21 +154,23 @@ class Media extends PhpObject {
|
||||
{
|
||||
$sMediaPath = self::getMediaPath($sMediaName);
|
||||
$sType = self::getMediaType($sMediaName);
|
||||
|
||||
$iPostedOn = filemtime($sMediaPath);
|
||||
$sTimeZone = date_default_timezone_get();
|
||||
$iWidth = 0;
|
||||
$iHeight = 0;
|
||||
$sRotate = '0';
|
||||
$sTakenOn = '';
|
||||
$fLat = 0;
|
||||
$fLng = 0;
|
||||
$iAlt = 0;
|
||||
switch($sType) {
|
||||
case 'video':
|
||||
$asResult = array();
|
||||
$sParams = implode(' ', array(
|
||||
'-loglevel error', //Remove comments
|
||||
'-select_streams v:0', //First video channel
|
||||
'-show_entries '. //filter tags : Width, Height, Creation Time & Rotation
|
||||
'format_tags=creation_time,com.apple.quicktime.creationdate:'.
|
||||
'-show_entries '. //filter tags : Width, Height, Creation Time, Location & Rotation
|
||||
'format_tags=creation_time,com.apple.quicktime.creationdate,com.apple.quicktime.location.ISO6709:'.
|
||||
'stream_tags=rotate,creation_time:'.
|
||||
'stream=width,height',
|
||||
'-print_format json', //output format: json
|
||||
@@ -181,6 +186,11 @@ class Media extends PhpObject {
|
||||
}
|
||||
else $sTakenOn = $asExif['format']['tags']['creation_time'] ?? $asExif['streams'][0]['tags']['creation_time'];
|
||||
|
||||
//Location
|
||||
if(isset($asExif['format']['tags']['com.apple.quicktime.location.ISO6709'])) {
|
||||
list($fLat, $fLng, $iAlt) = self::getLatLngAltFromISO6709($asExif['format']['tags']['com.apple.quicktime.location.ISO6709']);
|
||||
}
|
||||
|
||||
//Width & Height
|
||||
$iWidth = $asExif['streams'][0]['width'];
|
||||
$iHeight = $asExif['streams'][0]['height'];
|
||||
@@ -209,6 +219,14 @@ class Media extends PhpObject {
|
||||
$sTimeZone = $asExif['EXIF']['OffsetTimeOriginal'] ?? $asExif['EXIF']['UndefinedTag:0x9011'] ?? Spot::getTimeZoneFromDate($sTakenOn) ?? $sTimeZone;
|
||||
}
|
||||
|
||||
//Location
|
||||
if(array_key_exists('GPS', $asExif)) {
|
||||
$asGps = $asExif['GPS'];
|
||||
$fLat = self::getLatLngFromExif($asGps['GPSLatitudeRef'] ?? $asGps['UndefinedTag:0x0001'], $asGps['GPSLatitude'] ?? $asGps['UndefinedTag:0x0002']);
|
||||
$fLng = self::getLatLngFromExif($asGps['GPSLongitudeRef'] ?? $asGps['UndefinedTag:0x0003'], $asGps['GPSLongitude'] ?? $$asGps['UndefinedTag:0x0004']);
|
||||
$iAlt = (($asGps['GPSAltitudeRef'] ?? $asGps['UndefinedTag:0x0005'] ?? '0') == '1'?-1:1) * ($asGps['GPSAltitude'] ?? $asGps['UndefinedTag:0x0006'] ?? 0);
|
||||
}
|
||||
|
||||
//Orientation
|
||||
if(array_key_exists('IFD0', $asExif) && array_key_exists('Orientation', $asExif['IFD0'])) {
|
||||
switch($asExif['IFD0']['Orientation'])
|
||||
@@ -232,6 +250,9 @@ class Media extends PhpObject {
|
||||
|
||||
return array(
|
||||
'timezone' => $sTimeZone,
|
||||
'latitude' => $fLat,
|
||||
'longitude' => $fLng,
|
||||
'altitude' => $iAlt,
|
||||
'taken_ts' => $iTakenOn,
|
||||
'file_ts' => $iPostedOn,
|
||||
'width' => $iWidth,
|
||||
@@ -290,4 +311,29 @@ class Media extends PhpObject {
|
||||
|
||||
return $sType;
|
||||
}
|
||||
}
|
||||
|
||||
private static function getLatLngFromExif($sDirection, $asCoords) {
|
||||
$fCoord = 0;
|
||||
foreach($asCoords as $iIndex=>$sCoord) {
|
||||
$fValue = 0;
|
||||
$asCoordParts = explode('/', $sCoord);
|
||||
switch(count($asCoordParts)) {
|
||||
case 1:
|
||||
$fValue = $asCoordParts[0];
|
||||
break;
|
||||
case 2:
|
||||
$fValue = floatval($asCoordParts[0]) / floatval($asCoordParts[1]);
|
||||
break;
|
||||
}
|
||||
|
||||
$fCoord += $fValue / pow(60, $iIndex);
|
||||
}
|
||||
|
||||
return $fCoord * (($sDirection == 'W' || $sDirection == 'S')?-1:1);
|
||||
}
|
||||
|
||||
private static function getLatLngAltFromISO6709($sIso6709) {
|
||||
preg_match('/^(?P<lat>[\+\-][0,1]?\d{2}\.\d+)(?P<lng>[\+\-][0,1]?\d{2}\.\d+)(?P<alt>[\+\-]\d+)?/', $sIso6709, $asMatches);
|
||||
return array(floatval($asMatches['lat']), floatval($asMatches['lng']), floatval($asMatches['alt'] ?? 0));
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user