Fix Recording file format
This commit is contained in:
@@ -0,0 +1,132 @@
|
||||
<?php
|
||||
|
||||
class Recording
|
||||
{
|
||||
private const ident = "VGAR";
|
||||
|
||||
private const header_unpack = "Z5ident/Cversion";
|
||||
|
||||
private const segment_unpack = "Vtime/Saltitude/Sgroundspeed/elatitude/elongitude";
|
||||
|
||||
private string $file_name;
|
||||
|
||||
public function __construct(string $file)
|
||||
{
|
||||
$this->file_name = $file;
|
||||
}
|
||||
|
||||
public function geoJSON()
|
||||
{
|
||||
$geoJSON = [
|
||||
"type" => "FeatureCollection",
|
||||
"features" => [
|
||||
0 => [
|
||||
"type" => "Feature",
|
||||
"properties" => [
|
||||
"stroke" => "#ff0000",
|
||||
"stroke-width" => 2,
|
||||
"stroke-opacity" => 1
|
||||
],
|
||||
"geometry" => [
|
||||
"type" => "LineString",
|
||||
"coordinates" => []
|
||||
]
|
||||
]
|
||||
]
|
||||
];
|
||||
$segments = $this->read();
|
||||
$geoJSON["features"][0]["geometry"]["coordinates"] = array_map(function ($segment) {
|
||||
return array($segment["longitude"], $segment["latitude"]);
|
||||
}, $segments);
|
||||
|
||||
return $geoJSON;
|
||||
}
|
||||
|
||||
/**
|
||||
* Reads recording
|
||||
*
|
||||
* Array of objects with
|
||||
* @return time Segment time (number)
|
||||
* @return altitude Altitude
|
||||
* @return groundspeed Ground speed
|
||||
* @return latitude Latitude
|
||||
* @return longitude Longitude
|
||||
*/
|
||||
public function read()
|
||||
{
|
||||
$file = fopen($this->file_name, "rb");
|
||||
flock($file, LOCK_SH);
|
||||
|
||||
$segments = [];
|
||||
|
||||
$version = $this->read_header($file);
|
||||
|
||||
if ($version == 1) {
|
||||
while (($segment = $this->read_segment_1($file)) != false) {
|
||||
array_push($segments, $segment);
|
||||
}
|
||||
}
|
||||
|
||||
flock($file, LOCK_UN);
|
||||
fclose($file);
|
||||
|
||||
return $segments;
|
||||
}
|
||||
|
||||
/**
|
||||
* Reads one segment entry
|
||||
*
|
||||
* @param resource $file File handle
|
||||
*
|
||||
* If not EOF
|
||||
* @return time Segment time (number)
|
||||
* @return altitude Altitude
|
||||
* @return groundspeed Ground speed
|
||||
* @return latitude Latitude
|
||||
* @return longitude Longitude
|
||||
* Else
|
||||
* @return false
|
||||
*
|
||||
* @throws InvalidArgumentException If file is not a resource
|
||||
*/
|
||||
private function read_segment_1($file)
|
||||
{
|
||||
if (false === is_resource($file)) {
|
||||
throw new InvalidArgumentException(sprintf('Argument must be a valid resource type. %s given.', gettype($file)));
|
||||
}
|
||||
$data = fread($file, 24);
|
||||
if ($data) {
|
||||
return unpack(Recording::segment_unpack, $data);
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
/**
|
||||
* Reads the file header
|
||||
*
|
||||
* @param resource file File handle
|
||||
*
|
||||
* @return version File version
|
||||
*
|
||||
* @throws InvalidArgumentException If file is not a resource
|
||||
* @throws UnexpectedValueException If ident mismatches
|
||||
*/
|
||||
private function read_header($file)
|
||||
{
|
||||
if (false === is_resource($file)) {
|
||||
throw new InvalidArgumentException(sprintf('Argument must be a valid resource type. %s given.', gettype($file)));
|
||||
}
|
||||
|
||||
$header = unpack(Recording::header_unpack, fread($file, 6));
|
||||
|
||||
if ($header["ident"] !== Recording::ident) {
|
||||
throw
|
||||
new UnexpectedValueException(sprintf("Ident mismatch. Got %s, expected %s", $header["ident"], Recording::ident));
|
||||
}
|
||||
|
||||
return $header["version"];
|
||||
}
|
||||
}
|
||||
|
||||
$r = new Recording("/mnt/f/X-Plane 11/Resources/plugins/GAConnector/flight.rec");
|
||||
print_r(json_encode($r->geoJSON()));
|
||||
Reference in New Issue
Block a user