569 lines
17 KiB
PHP
569 lines
17 KiB
PHP
<?php
|
|
//
|
|
// test-geofence.php
|
|
//
|
|
|
|
// 2 * radius of the Earth and circumference at the equator, from Wikipedia
|
|
define('M_R_EARTH', 6378137.0);
|
|
define('M_2R_EARTH', 12756274.0);
|
|
define('M_CIRC_EARTH', 40075160.0);
|
|
// Flattening of the Earth, also from Wikipedia (assuming proximity of the
|
|
// two points p and q)
|
|
define('M_Y_FLATTENING', 0.0033528); // * cos(y)
|
|
|
|
set_time_limit(0);
|
|
|
|
if( isset($argc) && $argc > 1 ) {
|
|
// called from the command-line
|
|
parse_str(implode("&", $argv), $_GET);
|
|
}
|
|
else {
|
|
header("Content-Type: text/plain");
|
|
header('Expires: ' . date("r"));
|
|
}
|
|
|
|
//
|
|
// Check inputs for SQL statement injection and such.
|
|
// Items not tested below are not vulnerable for SQL statement injection, e.g.
|
|
// a time is always converted using 'strtotime()' and other items are only
|
|
// used in the PHP but never in the composition of an SQL statement
|
|
// [security audit 2013-10-23]
|
|
//
|
|
if(
|
|
(isset($_GET['zkl']) && !is_numeric($_GET['zkl'])) ||
|
|
(isset($_GET['logfile']) && !preg_match('/^[0-9]+,[0-9]+,[0-9]+$/', $_GET['logfile']) && !in_array($_GET['logfile'], array('log_tcp','log_versienummer','log_realtime','log_secure_zkl'))) ||
|
|
(isset($_GET['db']) && dirname($_GET['db']) != ".")
|
|
) {
|
|
// don't do anything fancy or interruptive as fiddling with the GET parameters
|
|
// is intended by the author
|
|
die("Parameter error");
|
|
}
|
|
|
|
require_once("support.inc.php");
|
|
|
|
// read the database information
|
|
if( isset($_GET['db']) ) $db_info = read_database(DBCONFIG_DIR, $_GET['db']);
|
|
else $db_info = array();
|
|
if( !isset($db_info['host']) ) $db_info['host'] = "localhost";
|
|
if( !isset($db_info['user']) ) $db_info['user'] = "root";
|
|
if( !isset($db_info['passwd']) ) $db_info['passwd'] = "";
|
|
if( !isset($db_info['db']) ) $db_info['db'] = "di_zkl";
|
|
|
|
// open the database
|
|
$db_handle = mysql_connect($db_info['host'], $db_info['user'], $db_info['passwd']);
|
|
if( $db_handle === FALSE ) {
|
|
echo mysql_error();
|
|
exit(1);
|
|
}
|
|
mysql_select_db($db_info['db'], $db_handle);
|
|
if( $db_info['main'] ) {
|
|
$db_main_info = read_database(DBCONFIG_DIR, $db_info['main']);
|
|
$db_main_handle = mysql_connect($db_main_info['host'], $db_main_info['user'], $db_main_info['passwd'], true);
|
|
if( $db_main_handle === FALSE ) {
|
|
echo mysql_error();
|
|
exit(1);
|
|
}
|
|
mysql_select_db($db_main_info['database'], $db_main_handle);
|
|
}
|
|
else {
|
|
$db_main_handle = $db_data_handle;
|
|
$db_main_info = $db_info;
|
|
}
|
|
|
|
// logfile to use
|
|
$zkl = $_GET['zkl'];
|
|
list($sdcard,$rpgmcount,$startup) = explode(',', $_GET['logfile']);
|
|
|
|
echo "logfile: " . $_GET['logfile'] . "\n";
|
|
echo str_repeat("-", 9 + strlen($_GET['logfile'])) . "\n";
|
|
|
|
// process log data
|
|
global $designs;
|
|
$designs = array();
|
|
$query = "SELECT * ";
|
|
$query .= "FROM log_zkl ";
|
|
$query .= "WHERE ";
|
|
$query .= " zkl=" . $zkl . " AND ";
|
|
$query .= " sdcard=" . $sdcard . " AND ";
|
|
$query .= " rpgmcount=" . $rpgmcount . " AND ";
|
|
$query .= " startup=" . $startup . " AND ";
|
|
$query .= " (";
|
|
$query .= " (";
|
|
$query .= " major=0xB AND ";
|
|
$query .= " minor BETWEEN 0x80 AND 0x8F";
|
|
$query .= " ) OR (";
|
|
$query .= " major=0xD AND ";
|
|
$query .= " minor=0x30";
|
|
$query .= " )";
|
|
$query .= " ) ";
|
|
$query .= "ORDER BY id";
|
|
$result = mysql_run($query, $db_handle);
|
|
while( $row = mysql_fetch_assoc($result) ) {
|
|
//echo "LOG " . $row['id'] . " " . $row['tijd'] . " " . sprintf("%X.%02X", $row['major'], $row['minor']) . "\n";
|
|
if( $row['major'] == 0xB ) {
|
|
switch( $row['minor'] ) {
|
|
case 0x80:
|
|
// design
|
|
$gquery = "SELECT * FROM log_geofence WHERE id=" . $row['id'];
|
|
$grow = mysql_fetch_assoc(mysql_run($gquery, $db_handle));
|
|
$designs[$grow['design']] = array();
|
|
$designs[$grow['design']]['name'] = $grow['naam'];
|
|
$designs[$grow['design']]['n'] = $grow['n_objects'];
|
|
$designs[$grow['design']]['inside'] = 0;
|
|
echo " []-+ CREATE " . $designs[$grow['design']]['name'] . "\n";
|
|
break;
|
|
case 0x81:
|
|
// object
|
|
$gquery = "SELECT * FROM log_geofence_object WHERE id=" . $row['id'];
|
|
$grow = mysql_fetch_assoc(mysql_run($gquery, $db_handle));
|
|
$designs[$grow['design']][$grow['object']] = array();
|
|
$designs[$grow['design']][$grow['object']]['n'] = $grow['n_points'];
|
|
$designs[$grow['design']][$grow['object']]['type'] = $grow['type'];
|
|
$designs[$grow['design']][$grow['object']]['r'] = $grow['radius'];
|
|
echo " | ADD (" . $grow['design'] . "," . $grow['object'] . "), " . $grow['type'] . ", r=" . $grow['radius'] . ", n=" . $grow['n_points'] . "\n";
|
|
break;
|
|
case 0x82:
|
|
// point
|
|
$gquery = "SELECT * FROM log_geofence_point WHERE id=" . $row['id'];
|
|
$grow = mysql_fetch_assoc(mysql_run($gquery, $db_handle));
|
|
$p = array();
|
|
$p['x'] = deg2rad($grow['longitude']);
|
|
$p['y'] = deg2rad($grow['latitude']);
|
|
$designs[$grow['design']][$grow['object']][] = $p;
|
|
geofence_update_bbox($grow['design'], $grow['object'], $p);
|
|
break;
|
|
case 0x87:
|
|
// delete
|
|
$gquery = "SELECT * FROM log_geofence WHERE id=" . $row['id'];
|
|
$grow = mysql_fetch_assoc(mysql_run($gquery, $db_handle));
|
|
echo " []-- DELETE " . $designs[$grow['design']]['name'] . "\n";
|
|
array_splice($designs, $grow['design'], 1);
|
|
break;
|
|
case 0x88:
|
|
// enter
|
|
$gquery = "SELECT * FROM log_geofence WHERE id=" . $row['id'];
|
|
$grow = mysql_fetch_assoc(mysql_run($gquery, $db_handle));
|
|
echo $row['tijd'] . ": log GEOFENCE ENTER " . $designs[$grow['design']]['name'] . "\n";
|
|
break;
|
|
case 0x89:
|
|
// exit
|
|
$gquery = "SELECT * FROM log_geofence WHERE id=" . $row['id'];
|
|
$grow = mysql_fetch_assoc(mysql_run($gquery, $db_handle));
|
|
echo $row['tijd'] . ": log GEOFENCE EXIT " . $designs[$grow['design']]['name'] . "\n";
|
|
break;
|
|
default:
|
|
break;
|
|
}
|
|
}
|
|
else if( $row['major'] == 0xD ) {
|
|
$gquery = "SELECT * FROM log_gps WHERE id=" . $row['id'];
|
|
$grow = mysql_fetch_assoc(mysql_run($gquery, $db_handle));
|
|
if( $grow['fix'] ) {
|
|
$p = array(
|
|
'x' => deg2rad($grow['longitude']),
|
|
'y' => deg2rad($grow['latitude'])
|
|
);
|
|
geofence_test($p, $row['tijd'], $grow['speed'], $grow['heading']);
|
|
}
|
|
else {
|
|
echo $row['tijd'] . ": fix lost\n";
|
|
}
|
|
}
|
|
}
|
|
|
|
function print_pt($p)
|
|
{
|
|
// print in 'latitude,longitude' order
|
|
return sprintf("(%.6f,%.6f)", rad2deg($p['y']), rad2deg($p['x']));
|
|
}
|
|
|
|
function print_rect($rect)
|
|
{
|
|
return print_pt($rect['p1']) . "-" . print_pt($rect['p2']);
|
|
}
|
|
|
|
function geofence_normalize($rect)
|
|
{
|
|
if( $rect['p1']['x'] > $rect['p2']['x'] ) {
|
|
$t = $rect['p1']['x'];
|
|
$rect['p1']['x'] = $rect['p2']['x'];
|
|
$rect['p2']['x'] = $t;
|
|
}
|
|
if( $rect['p1']['y'] > $rect['p2']['y'] ) {
|
|
$t = $rect['p1']['y'];
|
|
$rect['p1']['y'] = $rect['p2']['y'];
|
|
$rect['p2']['y'] = $t;
|
|
}
|
|
|
|
return $rect;
|
|
}
|
|
|
|
function bbox_get($p, $r)
|
|
{
|
|
$bbox = array();
|
|
|
|
if( $r == 0.0 ) {
|
|
$bbox['p1']['x'] = $bbox['p2']['x'] = $p['x'];
|
|
$bbox['p1']['y'] = $bbox['p2']['y'] = $p['y'];
|
|
|
|
return $bbox;
|
|
}
|
|
else {
|
|
$r = ($r / M_CIRC_EARTH) * 2.0 * M_PI;
|
|
$sin_px = sin($p['x']);
|
|
$cos_px = cos($p['x']);
|
|
//$sin_py = sin($p['y']);
|
|
$cos_py = cos($p['y']);
|
|
$r -= $r * M_Y_FLATTENING * $cos_py;
|
|
$sin_r = sin($r);
|
|
$cos_r = cos($r);
|
|
$bbox['p1']['x'] = asin($sin_px * $cos_r - $cos_px * $sin_r);
|
|
$bbox['p2']['x'] = asin($sin_px * $cos_r + $cos_px * $sin_r);
|
|
$bbox['p1']['y'] = $p['y'] - asin( $sin_r / $cos_px);
|
|
$bbox['p2']['y'] = $p['y'] - asin(-$sin_r / $cos_px);
|
|
|
|
return geofence_normalize($bbox);
|
|
}
|
|
}
|
|
|
|
function bbox_set($bbox, $rect)
|
|
{
|
|
$empty = !isset($bbox);
|
|
|
|
if( $empty || $rect['p1']['x'] < $bbox['p1']['x'] ) $bbox['p1']['x'] = $rect['p1']['x'];
|
|
if( $empty || $rect['p1']['y'] < $bbox['p1']['y'] ) $bbox['p1']['y'] = $rect['p1']['y'];
|
|
if( $empty || $rect['p2']['x'] > $bbox['p2']['x'] ) $bbox['p2']['x'] = $rect['p2']['x'];
|
|
if( $empty || $rect['p2']['y'] > $bbox['p2']['y'] ) $bbox['p2']['y'] = $rect['p2']['y'];
|
|
|
|
return $bbox;
|
|
}
|
|
|
|
function geofence_update_bbox($i, $j, $p)
|
|
{
|
|
global $designs;
|
|
|
|
$r = $designs[$i][$j]['r'];
|
|
|
|
switch( $designs[$i][$j]['type'] ) {
|
|
case 'point':
|
|
case 'line':
|
|
case 'track':
|
|
$bbox = bbox_get($p, $r);
|
|
break;
|
|
default:
|
|
$bbox = bbox_get($p, 0.0);
|
|
break;
|
|
}
|
|
|
|
$designs[$i][$j]['bbox'] = bbox_set($designs[$i][$j]['bbox'], $bbox);
|
|
$designs[$i]['bbox'] = bbox_set($designs[$i]['bbox'], $bbox);
|
|
}
|
|
|
|
function georect_within($rect, $p)
|
|
{
|
|
$inside =
|
|
$p['x'] >= $rect['p1']['x'] &&
|
|
$p['x'] <= $rect['p2']['x'] &&
|
|
$p['y'] >= $rect['p1']['y'] &&
|
|
$p['y'] <= $rect['p2']['y'];
|
|
|
|
// if( $inside ) {
|
|
// echo "Inside rect: " . print_pt($p) . " - " . print_rect($rect) . "\n";
|
|
// }
|
|
// else {
|
|
// echo "Outside rect: " . print_pt($p) . " - " . print_rect($rect) . "\n";
|
|
// }
|
|
|
|
return $inside;
|
|
}
|
|
|
|
function geopos_dist($p, $q)
|
|
{
|
|
// calculate the sine and cosine of the co-ordinates
|
|
$sin_px = sin($p['x']);
|
|
$cos_px = cos($p['x']);
|
|
$sin_py = sin($p['y']);
|
|
$cos_py = cos($p['y']);
|
|
$sin_qx = sin($q['x']);
|
|
$cos_qx = cos($q['x']);
|
|
$sin_qy = sin($q['y']);
|
|
$cos_qy = cos($q['y']);
|
|
|
|
// intermediate values
|
|
$a = $cos_qy * $cos_qx - $cos_py * $cos_px;
|
|
$b = $cos_qy * $sin_qx - $cos_py * $sin_px;
|
|
$c = $sin_qy - $sin_py ;
|
|
|
|
// compensate radius for the flattening of the earth
|
|
$r_x2 = M_2R_EARTH;
|
|
$r_x2 -= $r_x2 * $cos_qy * M_Y_FLATTENING;
|
|
|
|
return
|
|
$r_x2 *
|
|
asin(
|
|
0.5 * sqrt($a * $a + $b * $b + $c * $c)
|
|
);
|
|
}
|
|
|
|
function geoline_dist($p1, $p2, $q)
|
|
{
|
|
$x2_x1 = $p2['x'] - $p1['x'];
|
|
$y2_y1 = $p2['y'] - $p1['y'];
|
|
$x1_x0 = $p1['x'] - $q['x'];
|
|
$y1_y0 = $p1['y'] - $q['y'];
|
|
|
|
// distance in radians
|
|
$d = abs(($x2_x1 * $y1_y0) - ($x1_x0 * $y2_y1)) / sqrt(($x2_x1 * $x2_x1) + ($y2_y1 * $y2_y1));
|
|
|
|
// compensate radius for the flattening of the earth
|
|
$r = M_R_EARTH;
|
|
$r -= $r * cos($q['y']) * M_Y_FLATTENING;
|
|
|
|
return $r * $d;
|
|
}
|
|
|
|
function geoline_project_pt($p1, $p2, $q)
|
|
{
|
|
$x2_x1 = $p2['x'] - $p1['x'];
|
|
$y2_y1 = $p2['y'] - $p1['y'];
|
|
$x0_x1 = $q['x'] - $p1['x'];
|
|
$y0_y1 = $q['y'] - $p1['y'];
|
|
$x0_x2 = $q['x'] - $p2['x'];
|
|
$y0_y2 = $q['y'] - $p2['y'];
|
|
|
|
return (($x0_x1 * $x2_x1) + ($y0_y1 * $y2_y1)) / (($x2_x1 * $x2_x1) + ($y2_y1 * $y2_y1));
|
|
}
|
|
|
|
function geofence_test_point($i, $j, $p)
|
|
{
|
|
global $designs;
|
|
$has_match = FALSE;
|
|
|
|
$r = $designs[$i][$j]['r'];
|
|
|
|
$d = geopos_dist($designs[$i][$j][0], $p);
|
|
|
|
if( $d <= $r ) {
|
|
echo " + point " . print_pt($designs[$i][$j][0]) . " matches (d=" . sprintf("%.1f", $d) . ")\n";
|
|
return TRUE;
|
|
}
|
|
else if( $d <= ($r * 1.5) ) {
|
|
// near miss
|
|
echo " - point " . print_pt($designs[$i][$j][0]) . " does NOT match (d=" . sprintf("%.1f", $d) . ")\n";
|
|
return FALSE;
|
|
}
|
|
}
|
|
|
|
function geofence_test_lines($i, $j, $p)
|
|
{
|
|
global $designs;
|
|
$has_match = FALSE;
|
|
|
|
$r = $designs[$i][$j]['r'];
|
|
|
|
//
|
|
// TRIAL
|
|
//
|
|
// Test lines but endcap "butt" instead of "round"
|
|
//
|
|
for( $k = 1; $k < $designs[$i][$j]['n'] - 1; $k++ ) {
|
|
$d = geopos_dist($designs[$i][$j][$k], $p);
|
|
|
|
if( $d <= $r ) {
|
|
if( !$has_match ) {
|
|
echo " + point " . print_pt($designs[$i][$j][$k]) . " matches (d=" . sprintf("%.1f", $d) . ")\n";
|
|
$has_match = TRUE;
|
|
}
|
|
else {
|
|
echo " point " . print_pt($designs[$i][$j][$k]) . " matches (d=" . sprintf("%.1f", $d) . ") NOT TESTED\n";
|
|
}
|
|
}
|
|
else if( $d <= ($r * 1.5) ) {
|
|
// near miss
|
|
echo " - point " . print_pt($designs[$i][$j][$k]) . " does NOT match (d=" . sprintf("%.1f", $d) . ")\n";
|
|
}
|
|
}
|
|
|
|
for( $k = 1; $k < $designs[$i][$j]['n']; $k++ ) {
|
|
if(
|
|
!(
|
|
$designs[$i][$j][$k - 1]['x'] == $designs[$i][$j][$k]['x'] &&
|
|
$designs[$i][$j][$k - 1]['y'] == $designs[$i][$j][$k]['y']
|
|
)
|
|
) {
|
|
$d_p1_p0 = geoline_project_pt($designs[$i][$j][$k - 1], $designs[$i][$j][$k], $p);
|
|
$d = geoline_dist($designs[$i][$j][$k - 1], $designs[$i][$j][$k], $p);
|
|
|
|
if(
|
|
0.0 <= $d_p1_p0 &&
|
|
$d_p1_p0 <= 1.0 &&
|
|
$d <= $r
|
|
) {
|
|
if( !$has_match ) {
|
|
echo " + line " . print_pt($designs[$i][$j][$k - 1]) . "-" . print_pt($designs[$i][$j][$k]) . " matches (d=" . sprintf("%.1f, %.2f%%", $d, $d_p1_p0 * 100.0) . ")\n";
|
|
$has_match = TRUE;
|
|
}
|
|
else {
|
|
echo " line " . print_pt($designs[$i][$j][$k - 1]) . "-" . print_pt($designs[$i][$j][$k]) . " matches (d=" . sprintf("%.1f, %.2f%%", $d, $d_p1_p0 * 100.0) . ") NOT TESTED\n";
|
|
}
|
|
}
|
|
else if(
|
|
-0.5 <= $d_p1_p0 &&
|
|
$d_p1_p0 <= 1.5 &&
|
|
$d <= ($r * 1.5)
|
|
) {
|
|
// near miss
|
|
echo " - line " . print_pt($designs[$i][$j][$k - 1]) . "-" . print_pt($designs[$i][$j][$k]) . " does NOT match (d=" . sprintf("%.1f, %.2f%%", $d, $d_p1_p0 * 100.0) . ")\n";
|
|
}
|
|
}
|
|
}
|
|
|
|
return $has_match;
|
|
}
|
|
|
|
// Test if point 'p' lies strictly within the rectangle described by 'points'
|
|
function geofence_test_rect($i, $j, $p)
|
|
{
|
|
global $designs;
|
|
|
|
// the object must have at least two points
|
|
if( $designs[$i][$j]['n'] < 2 ) return FALSE;
|
|
|
|
// create a normalized rectangle from the first two points in the array;
|
|
// excessive points are ignored
|
|
$rect = geofence_normalize(array('p1' => $designs[$i][$j][0], 'p2' => $designs[$i][$j][1]));
|
|
if( georect_within($rect, $p) ) {
|
|
echo " + rect " . print_pt($designs[$i][$j][0]) . "-" . print_pt($designs[$i][$j][1]) . " matches\n";
|
|
return TRUE;
|
|
}
|
|
else {
|
|
echo " - rect " . print_pt($designs[$i][$j][0]) . "-" . print_pt($designs[$i][$j][1]) . " does NOT match\n";
|
|
return FALSE;
|
|
}
|
|
}
|
|
|
|
// Test if point 'p' lies strictly within the polygon described by 'points', using
|
|
// odd/even rule and the crossing algorithm, casting a ray from 'p' to the right
|
|
function geofence_test_polygon($i, $j, $p)
|
|
{
|
|
global $designs;
|
|
|
|
$crossings = 0;
|
|
$p_x = $p['x'];
|
|
$p_y = $p['y'];
|
|
|
|
for( $k = 0; $k < $designs[$i][$j]['n']; $k++ ) {
|
|
// get the vertex
|
|
$p1_x = $designs[$i][$j][$k]['x'];
|
|
$p1_y = $designs[$i][$j][$k]['y'];
|
|
if( $k == $designs[$i][$j]['n'] - 1 ) {
|
|
// last point: close the polygon
|
|
$p2_x = $designs[$i][$j][0]['x'];
|
|
$p2_y = $designs[$i][$j][0]['y'];
|
|
}
|
|
else {
|
|
// next point; also increment the point in the array
|
|
$p2_x = $designs[$i][$j][$k+1]['x'];
|
|
$p2_y = $designs[$i][$j][$k+1]['y'];
|
|
}
|
|
|
|
// the vertex is not interesting if it is fully to the left of 'p'
|
|
if( $p1_x < $p_x && $p2_x < $p_x ) {
|
|
echo " vertex " . print_pt(array('x' => $p1_x, 'y' => $p1_y)) . "-" . print_pt(array('x' => $p2_x, 'y' => $p2_y)) . ": left)\n";
|
|
continue;
|
|
}
|
|
|
|
// nor is it interesting if it is fully below or above 'p'
|
|
if( $p1_y < $p_y && $p2_y < $p_y ) {
|
|
echo " vertex " . print_pt(array('x' => $p1_x, 'y' => $p1_y)) . "-" . print_pt(array('x' => $p2_x, 'y' => $p2_y)) . ": below)\n";
|
|
continue;
|
|
}
|
|
if( $p1_y > $p_y && $p2_y > $p_y ) {
|
|
echo " vertex " . print_pt(array('x' => $p1_x, 'y' => $p1_y)) . "-" . print_pt(array('x' => $p2_x, 'y' => $p2_y)) . ": above)\n";
|
|
continue;
|
|
}
|
|
|
|
// potentially interesting line; is it fully to the right of 'p'?
|
|
if( $p1_x > $p_x && $p2_x > $p_x ) {
|
|
// yup, it crosses the ray casted from 'p' to the right
|
|
echo " + vertex " . print_pt(array('x' => $p1_x, 'y' => $p1_y)) . "-" . print_pt(array('x' => $p2_x, 'y' => $p2_y)) . ": right)\n";
|
|
$crossings++;
|
|
continue;
|
|
}
|
|
|
|
// some extra work is needed to see if the line crosses 'p' on its
|
|
// lefthand side or on its righthand side
|
|
// project point 'p1' such that that it has the same y co-ordinate as 'p'
|
|
$p1_x += ($p_y - $p1_y) * (($p2_x - $p1_x) / ($p2_y - $p1_y));
|
|
|
|
// 'p1' to the left of 'p'? then it does not cross our scanline
|
|
if( $p1_x >= $p_x ) {
|
|
echo " + vertex " . print_pt(array('x' => $p1_x, 'y' => $p1_y)) . "-" . print_pt(array('x' => $p2_x, 'y' => $p2_y)) . ": crosses right)\n";
|
|
$crossings++;
|
|
}
|
|
else {
|
|
echo " vertex " . print_pt(array('x' => $p1_x, 'y' => $p1_y)) . "-" . print_pt(array('x' => $p2_x, 'y' => $p2_y)) . ": crosses left)\n";
|
|
}
|
|
}
|
|
|
|
if( ($crossings & 1) != 0 ) {
|
|
echo " + polygon matches, " . $crossings . " vertices to the right\n";
|
|
return TRUE;
|
|
}
|
|
else {
|
|
echo " - polygon does NOT match, " . $crossings . " vertices to the right\n";
|
|
return FALSE;
|
|
}
|
|
}
|
|
|
|
function geofence_test_object($i, $j, $p)
|
|
{
|
|
global $designs;
|
|
|
|
if( !georect_within($designs[$i][$j]['bbox'], $p) ) return FALSE;
|
|
|
|
switch( $designs[$i][$j]['type'] ) {
|
|
case 'point':
|
|
return geofence_test_point($i, $j, $p);
|
|
case 'line':
|
|
case 'track':
|
|
return geofence_test_lines($i, $j, $p);
|
|
case 'rect':
|
|
return geofence_test_rect($i, $j, $p);
|
|
case 'polygon':
|
|
return geofence_test_polygon($i, $j, $p);
|
|
default:
|
|
echo "Unknown type: " . $designs[$i][$j]['type'] . "\n";
|
|
return FALSE;
|
|
}
|
|
}
|
|
|
|
function geofence_test($p, $tijd, $speed, $tc)
|
|
{
|
|
global $designs;
|
|
|
|
echo $tijd . ": " . print_pt($p) . ", " . $speed . " km/h, tc=" .$tc . "\n";
|
|
|
|
for( $i = 0; $i < count($designs); $i++ ) {
|
|
$inside = 0;
|
|
if( georect_within($designs[$i]['bbox'], $p) ) {
|
|
for( $j = 0; $j < $designs[$i]['n']; $j++ ) {
|
|
if( geofence_test_object($i, $j, $p) ) {
|
|
$inside = 1;
|
|
echo " INSIDE (" . $i . "," . $j . ")\n";
|
|
}
|
|
}
|
|
}
|
|
|
|
if( $inside != $designs[$i]['inside'] ) {
|
|
$designs[$i]['inside'] = $inside;
|
|
|
|
if( $inside )
|
|
echo " ----> ENTER " . $designs[$i]['name'] . "\n";
|
|
else
|
|
echo " <---- EXIT " . $designs[$i]['name'] . "\n";
|
|
}
|
|
}
|
|
}
|
|
|
|
?>
|