diff --git a/public_html/config.js b/public_html/config.js index fe54a9e..73733bb 100644 --- a/public_html/config.js +++ b/public_html/config.js @@ -102,7 +102,7 @@ SiteCirclesDistances = new Array(100,150,200); ShowClocks = false; // Controls page title, righthand pane when nothing is selected -PageName = "FlightAware dump1090"; +PageName = "PiAware Skyview"; // Show country flags by ICAO addresses? ShowFlags = true; diff --git a/public_html/formatter.js b/public_html/formatter.js index 8d6dca9..d25460b 100644 --- a/public_html/formatter.js +++ b/public_html/formatter.js @@ -6,7 +6,7 @@ var DEGREES='\u00b0' var UP_TRIANGLE='\u25b2'; // U+25B2 BLACK UP-POINTING TRIANGLE var DOWN_TRIANGLE='\u25bc'; // U+25BC BLACK DOWN-POINTING TRIANGLE -var TrackDirections = ["North","Northeast","East","Southeast","South","Southwest","West","Northwest"]; +var TrackDirections = ["North","NE","East","SE","South","SW","West","NW"]; var UnitLabels = { 'altitude': { metric: "m", imperial: "ft", nautical: "ft"}, @@ -31,7 +31,7 @@ function format_track_brief(track) { return ""; } - return Math.round(track); + return Math.round(track) + DEGREES; } // track in degrees (0..359) @@ -54,7 +54,7 @@ function format_altitude_brief(alt, vr, displayUnits) { return "ground"; } - alt_text = Math.round(convert_altitude(alt, displayUnits)) + NBSP; + alt_text = Math.round(convert_altitude(alt, displayUnits)).toLocaleString() + NBSP; // Vertical Rate Triangle var verticalRateTriangle = ""; @@ -80,7 +80,7 @@ function format_altitude_long(alt, vr, displayUnits) { return "on ground"; } - alt_text = Math.round(convert_altitude(alt, displayUnits)) + NBSP + get_unit_label("altitude", displayUnits); + alt_text = Math.round(convert_altitude(alt, displayUnits)).toLocaleString() + NBSP + get_unit_label("altitude", displayUnits); if (vr > 128) { return UP_TRIANGLE + NBSP + alt_text; @@ -142,12 +142,16 @@ function format_distance_brief(dist, displayUnits) { } // dist in meters -function format_distance_long(dist, displayUnits) { +function format_distance_long(dist, displayUnits, fixed) { if (dist === null) { return "n/a"; } - var dist_text = convert_distance(dist, displayUnits).toFixed(1) + NBSP + get_unit_label("distance", displayUnits); + if (typeof fixed === 'undefined') { + fixed = 1; + } + + var dist_text = convert_distance(dist, displayUnits).toFixed(fixed) + NBSP + get_unit_label("distance", displayUnits); return dist_text; } diff --git a/public_html/images/alt_legend_feet.svg b/public_html/images/alt_legend_feet.svg new file mode 100644 index 0000000..3fd6af3 --- /dev/null +++ b/public_html/images/alt_legend_feet.svg @@ -0,0 +1 @@ +alt_legend_feet \ No newline at end of file diff --git a/public_html/images/alt_legend_meters.svg b/public_html/images/alt_legend_meters.svg new file mode 100644 index 0000000..6e23702 --- /dev/null +++ b/public_html/images/alt_legend_meters.svg @@ -0,0 +1 @@ +alt_Legend_meters \ No newline at end of file diff --git a/public_html/images/box-checked.png b/public_html/images/box-checked.png new file mode 100644 index 0000000..1a5cc83 Binary files /dev/null and b/public_html/images/box-checked.png differ diff --git a/public_html/images/box-checked@2x.png b/public_html/images/box-checked@2x.png new file mode 100644 index 0000000..8a75b86 Binary files /dev/null and b/public_html/images/box-checked@2x.png differ diff --git a/public_html/images/box-checked@3x.png b/public_html/images/box-checked@3x.png new file mode 100644 index 0000000..ae85a45 Binary files /dev/null and b/public_html/images/box-checked@3x.png differ diff --git a/public_html/images/box-empty.png b/public_html/images/box-empty.png new file mode 100644 index 0000000..46f6236 Binary files /dev/null and b/public_html/images/box-empty.png differ diff --git a/public_html/images/box-empty@2x.png b/public_html/images/box-empty@2x.png new file mode 100644 index 0000000..3990ff5 Binary files /dev/null and b/public_html/images/box-empty@2x.png differ diff --git a/public_html/images/box-empty@3x.png b/public_html/images/box-empty@3x.png new file mode 100644 index 0000000..7aa7e2b Binary files /dev/null and b/public_html/images/box-empty@3x.png differ diff --git a/public_html/images/close-settings.png b/public_html/images/close-settings.png new file mode 100644 index 0000000..6c65377 Binary files /dev/null and b/public_html/images/close-settings.png differ diff --git a/public_html/images/close-settings@2x.png b/public_html/images/close-settings@2x.png new file mode 100644 index 0000000..1f45474 Binary files /dev/null and b/public_html/images/close-settings@2x.png differ diff --git a/public_html/images/close-settings@3x.png b/public_html/images/close-settings@3x.png new file mode 100644 index 0000000..b71c832 Binary files /dev/null and b/public_html/images/close-settings@3x.png differ diff --git a/public_html/images/column-adjust.png b/public_html/images/column-adjust.png new file mode 100644 index 0000000..3623751 Binary files /dev/null and b/public_html/images/column-adjust.png differ diff --git a/public_html/images/column-adjust@2x.png b/public_html/images/column-adjust@2x.png new file mode 100644 index 0000000..a789469 Binary files /dev/null and b/public_html/images/column-adjust@2x.png differ diff --git a/public_html/images/column-adjust@3x.png b/public_html/images/column-adjust@3x.png new file mode 100644 index 0000000..fafdadc Binary files /dev/null and b/public_html/images/column-adjust@3x.png differ diff --git a/public_html/images/fa_logo_color.png b/public_html/images/fa_logo_color.png new file mode 100644 index 0000000..8136fbf Binary files /dev/null and b/public_html/images/fa_logo_color.png differ diff --git a/public_html/images/fa_logo_color@2x.png b/public_html/images/fa_logo_color@2x.png new file mode 100644 index 0000000..76face9 Binary files /dev/null and b/public_html/images/fa_logo_color@2x.png differ diff --git a/public_html/images/fa_logo_color@3x.png b/public_html/images/fa_logo_color@3x.png new file mode 100644 index 0000000..2f24989 Binary files /dev/null and b/public_html/images/fa_logo_color@3x.png differ diff --git a/public_html/images/ff-sv-logo.png b/public_html/images/ff-sv-logo.png new file mode 100644 index 0000000..1c9a263 Binary files /dev/null and b/public_html/images/ff-sv-logo.png differ diff --git a/public_html/images/ff-sv-logo@2x.png b/public_html/images/ff-sv-logo@2x.png new file mode 100644 index 0000000..c1a1e76 Binary files /dev/null and b/public_html/images/ff-sv-logo@2x.png differ diff --git a/public_html/images/ff-sv-logo@3x.png b/public_html/images/ff-sv-logo@3x.png new file mode 100644 index 0000000..66178d9 Binary files /dev/null and b/public_html/images/ff-sv-logo@3x.png differ diff --git a/public_html/images/map-icon.png b/public_html/images/map-icon.png new file mode 100644 index 0000000..0d75237 Binary files /dev/null and b/public_html/images/map-icon.png differ diff --git a/public_html/images/map-icon@2x.png b/public_html/images/map-icon@2x.png new file mode 100644 index 0000000..ef0622b Binary files /dev/null and b/public_html/images/map-icon@2x.png differ diff --git a/public_html/images/map-icon@3x.png b/public_html/images/map-icon@3x.png new file mode 100644 index 0000000..3b51d7e Binary files /dev/null and b/public_html/images/map-icon@3x.png differ diff --git a/public_html/images/pa-sv-logo.png b/public_html/images/pa-sv-logo.png new file mode 100644 index 0000000..1b95e8c Binary files /dev/null and b/public_html/images/pa-sv-logo.png differ diff --git a/public_html/images/pa-sv-logo@2x.png b/public_html/images/pa-sv-logo@2x.png new file mode 100644 index 0000000..a875af6 Binary files /dev/null and b/public_html/images/pa-sv-logo@2x.png differ diff --git a/public_html/images/pa-sv-logo@3x.png b/public_html/images/pa-sv-logo@3x.png new file mode 100644 index 0000000..125e0c7 Binary files /dev/null and b/public_html/images/pa-sv-logo@3x.png differ diff --git a/public_html/images/settings-icon.png b/public_html/images/settings-icon.png new file mode 100644 index 0000000..2f95e58 Binary files /dev/null and b/public_html/images/settings-icon.png differ diff --git a/public_html/images/settings-icon@2x.png b/public_html/images/settings-icon@2x.png new file mode 100644 index 0000000..2f90256 Binary files /dev/null and b/public_html/images/settings-icon@2x.png differ diff --git a/public_html/images/settings-icon@3x.png b/public_html/images/settings-icon@3x.png new file mode 100644 index 0000000..dc5a58b Binary files /dev/null and b/public_html/images/settings-icon@3x.png differ diff --git a/public_html/images/table-icon.png b/public_html/images/table-icon.png new file mode 100644 index 0000000..2eed5f8 Binary files /dev/null and b/public_html/images/table-icon.png differ diff --git a/public_html/images/table-icon@2x.png b/public_html/images/table-icon@2x.png new file mode 100644 index 0000000..d7c7b3f Binary files /dev/null and b/public_html/images/table-icon@2x.png differ diff --git a/public_html/images/table-icon@3x.png b/public_html/images/table-icon@3x.png new file mode 100644 index 0000000..495700c Binary files /dev/null and b/public_html/images/table-icon@3x.png differ diff --git a/public_html/images/zoom-in.png b/public_html/images/zoom-in.png new file mode 100644 index 0000000..9ba05d7 Binary files /dev/null and b/public_html/images/zoom-in.png differ diff --git a/public_html/images/zoom-in@2x.png b/public_html/images/zoom-in@2x.png new file mode 100644 index 0000000..40b1a97 Binary files /dev/null and b/public_html/images/zoom-in@2x.png differ diff --git a/public_html/images/zoom-in@3x.png b/public_html/images/zoom-in@3x.png new file mode 100644 index 0000000..38de4f2 Binary files /dev/null and b/public_html/images/zoom-in@3x.png differ diff --git a/public_html/images/zoom-out.png b/public_html/images/zoom-out.png new file mode 100644 index 0000000..f64b25e Binary files /dev/null and b/public_html/images/zoom-out.png differ diff --git a/public_html/images/zoom-out@2x.png b/public_html/images/zoom-out@2x.png new file mode 100644 index 0000000..684b701 Binary files /dev/null and b/public_html/images/zoom-out@2x.png differ diff --git a/public_html/images/zoom-out@3x.png b/public_html/images/zoom-out@3x.png new file mode 100644 index 0000000..f0d3b19 Binary files /dev/null and b/public_html/images/zoom-out@3x.png differ diff --git a/public_html/index.html b/public_html/index.html index 8a61ddc..1a2acbc 100644 --- a/public_html/index.html +++ b/public_html/index.html @@ -23,7 +23,7 @@ - FlightAware dump1090 + PiAware Skyview @@ -46,74 +46,220 @@ + +
+ + +
+
+ n/a + n/a +
+
+
+
Aircraft Type:
+
n/a
+
+
+
Altitude:
+
n/a
+
+
+
Speed:
+
n/a
+
+
+
+ +
+
+
+
+
Overlay Toggles
+
+
+
+
NEXRAD Weather
+
+
+
+
Site Position and Range Rings
+
+
+
+
Selected Aircraft Trail
+
+
+
+
Aircraft Positions
+
+
+
+
Altitude Chart
+
+
+
+
+
View Toggles
+
+
+
+
Show Anonymous MLAT Tracks
+
+
+
+
Show Ground Vehicles and Other Non-Aircraft Positions
+
+
+
+
All Aircraft Trails
+
+
+
+
Group by Data Type
+
+
+
+
-
- -
-
- -
+
+ +
+
+ +
+
+ +
- + to @@ -189,15 +322,15 @@ Speed () Vertical Rate () Distance () - Track + Heading Msgs Age RSSI Latitude Longitude Data Source - Airframes.org Link - FlightAware Link + Airframes.org + FlightAware Photos @@ -226,6 +359,16 @@ +
+
+
ADS-B
+
+
MLAT
+
+
Other
+
+
TIS-B
+
diff --git a/public_html/markers.js b/public_html/markers.js index 3be6cf7..eb09c23 100755 --- a/public_html/markers.js +++ b/public_html/markers.js @@ -1,220 +1,212 @@ // -*- mode: javascript; indent-tabs-mode: nil; c-basic-offset: 8 -*- "use strict"; -// From the original planeObject.js: -var _generic_plane_svg = "M 0,0 " + - "M 1.9565564,41.694305 C 1.7174505,40.497708 1.6419973,38.448747 " + - "1.8096508,37.70494 1.8936398,37.332056 2.0796653,36.88191 2.222907,36.70461 " + - "2.4497603,36.423844 4.087816,35.47248 14.917931,29.331528 l 12.434577," + - "-7.050718 -0.04295,-7.613412 c -0.03657,-6.4844888 -0.01164,-7.7625804 " + - "0.168134,-8.6194061 0.276129,-1.3160905 0.762276,-2.5869575 1.347875," + - "-3.5235502 l 0.472298,-0.7553719 1.083746,-0.6085497 c 1.194146,-0.67053522 " + - "1.399524,-0.71738842 2.146113,-0.48960552 1.077005,0.3285939 2.06344," + - "1.41299352 2.797602,3.07543322 0.462378,1.0469993 0.978731,2.7738408 " + - "1.047635,3.5036272 0.02421,0.2570284 0.06357,3.78334 0.08732,7.836246 0.02375," + - "4.052905 0.0658,7.409251 0.09345,7.458546 0.02764,0.04929 5.600384,3.561772 " + - "12.38386,7.805502 l 12.333598,7.715871 0.537584,0.959688 c 0.626485,1.118378 " + - "0.651686,1.311286 0.459287,3.516442 -0.175469,2.011604 -0.608966,2.863924 " + - "-1.590344,3.127136 -0.748529,0.200763 -1.293144,0.03637 -10.184829,-3.07436 " + - "C 48.007733,41.72562 44.793806,40.60197 43.35084,40.098045 l -2.623567," + - "-0.916227 -1.981212,-0.06614 c -1.089663,-0.03638 -1.985079,-0.05089 -1.989804," + - "-0.03225 -0.0052,0.01863 -0.02396,2.421278 -0.04267,5.339183 -0.0395,6.147742 " + - "-0.143635,7.215456 -0.862956,8.845475 l -0.300457,0.680872 2.91906,1.361455 " + - "c 2.929379,1.366269 3.714195,1.835385 4.04589,2.41841 0.368292,0.647353 " + - "0.594634,2.901439 0.395779,3.941627 -0.0705,0.368571 -0.106308,0.404853 " + - "-0.765159,0.773916 L 41.4545,62.83158 39.259237,62.80426 c -6.030106,-0.07507 " + - "-16.19508,-0.495041 -16.870991,-0.697033 -0.359409,-0.107405 -0.523792," + - "-0.227482 -0.741884,-0.541926 -0.250591,-0.361297 -0.28386,-0.522402 -0.315075," + - "-1.52589 -0.06327,-2.03378 0.23288,-3.033615 1.077963,-3.639283 0.307525," + - "-0.2204 4.818478,-2.133627 6.017853,-2.552345 0.247872,-0.08654 0.247455," + - "-0.102501 -0.01855,-0.711959 -0.330395,-0.756986 -0.708622,-2.221756 -0.832676," + - "-3.224748 -0.05031,-0.406952 -0.133825,-3.078805 -0.185533,-5.937448 -0.0517," + - "-2.858644 -0.145909,-5.208974 -0.209316,-5.222958 -0.06341,-0.01399 -0.974464," + - "-0.0493 -2.024551,-0.07845 L 23.247235,38.61921 18.831373,39.8906 C 4.9432155," + - "43.88916 4.2929558,44.057819 3.4954426,43.86823 2.7487826,43.690732 2.2007966," + - "42.916622 1.9565564,41.694305 z"; -// Rescaled from "Helicopter bottom view silhouette" -// http://www.flaticon.com/free-icon/helicopter-bottom-view-silhouette_26901 -// by Freepik (http://www.flaticon.com/authors/freepik) -// licensed under CC BY 3.0 (https://creativecommons.org/licenses/by/3.0/) - -// 44x64 -var _rotorcraft_svg = - "M 43.89309,0.4301 c -0.60546,-0.60546 -1.62623,-0.56506 -2.2813,0.0897 L 25.82444,16.3061 C 24.95171,-1.27473 21.64491,1.24212 21.64491,1.24212 c 0,0 -3.20153,-2.80873 -4.13518,14.07519 L 2.71103,0.51862 C 2.05636,-0.13606 1.03533,-0.17646 0.43,0.42902 c -0.60546,0.6052 -0.56506,1.6261 0.0896,2.28104 l 16.81957,16.81931 c -0.0454,1.63425 -0.072,3.41089 -0.0796,5.34281 l -0.90497,0.90496 h -1.94113 v 1.94113 L 0.51882,41.61319 c -0.6548,0.65454 -0.69533,1.67531 -0.09,2.28077 0.60533,0.60546 1.62636,0.5648 2.28104,-0.0896 L 14.41335,32.10074 v 1.94073 h 3.09928 c 0,0 1.25961,6.97312 2.03417,8.65159 0.77495,1.67913 0.032,17.17487 2.09799,17.17487 0.38346,0 0.66928,-0.53374 0.88615,-1.41331 l 6.34515,-2.71897 v -1.03314 h -5.85155 c 0.34017,-4.67077 0.24161,-10.97316 0.71942,-12.00945 0.77416,-1.67847 2.03285,-8.65159 2.03285,-8.65159 h 3.09928 v -2.974 l 12.73545,12.73689 c 0.65507,0.65442 1.67584,0.69495 2.2813,0.0896 0.60546,-0.60533 0.56479,-1.62623 -0.0901,-2.28077 L 28.876,26.68527 v -0.90813 h -0.90799 l -1.94284,-1.9431 c -0.009,-1.15407 -0.0263,-2.25524 -0.0496,-3.29693 l 17.82849,-17.826 c 0.65389,-0.65494 0.69442,-1.67702 0.0891,-2.28103 z " + - "M 18.80421,51.60336 h -0.5165 c -0.42794,0 -0.77495,0.34754 -0.77495,0.77521 v 10.84709 c 0,0.42768 0.34701,0.77469 0.77495,0.77469 h 0.5165 c 0.42768,0 0.77469,-0.34701 0.77469,-0.77469 V 52.37857 c 0,-0.42781 -0.34701,-0.77521 -0.77469,-0.77521 z"; - -// Modified version of "Beechcraft Bonanza V35B" -// https://commons.wikimedia.org/wiki/File:Beechcraft_Bonanza_V35B.svg -// by Kaboldy (https://commons.wikimedia.org/wiki/User:Kaboldy) -// licensed under CC BY-SA 3.0 (https://creativecommons.org/licenses/by-sa/3.0/deed.en) - -// 64x49 -var _beechcraft_svg = - "m 31.9375,0.21875 c -0.06777,0.0107988 -0.115451,0.0391469 -0.15625,0.0625 C 31.672725,0.37187346 31.571656,0.508205 31.5,0.625 c -0.03614,0.0602071 -0.06208,0.095702 -0.09375,0.15625 -0.07403,0.15902301 -0.135583,0.3268225 -0.1875,0.5 -0.04551,0.1172902 -0.09299,0.229501 -0.125,0.34375 C 31.061962,1.7428305 31.051772,1.8837099 31.03125,2 31.013723,2.1172825 31.001884,2.2232944 31,2.34375 a 0.050005,0.050005 0 0 0 0,0.03125 0.050005,0.050005 0 0 0 0,0.03125 c -0.0082,0.022808 -0.04473,0.016331 -0.0625,0.03125 -0.02369,0.019892 -0.05403,0.050775 -0.09375,0.0625 -0.07944,0.02345 -0.16785,0.042313 -0.25,0.0625 -0.142298,0.027931 -0.321549,0.011037 -0.5,0.03125 -0.178451,0.020213 -0.362341,0.079026 -0.5,0.1875 -0.232524,0.2710695 -0.269126,0.6354569 -0.375,0.9375 -0.515728,1.9222735 -0.692683,3.8981369 -0.8125,5.875 -0.0025,0.039801 -0.0291,0.08613 -0.03125,0.125 -5.12e-4,0.00925 5.69e-4,0.022042 0,0.03125 l -3.75,1.59375 -0.03125,0 -0.03125,0 L 1.03125,13.125 1,13.125 a 0.050005,0.050005 0 0 0 -0.03125,0 c -0.0142757,0.0014 -0.0171094,0.02929 -0.03125,0.03125 -0.49350918,0.06826 -0.88359986,0.49922 -0.90625,1 A 0.050005,0.050005 0 0 0 0,14.1875 c -2.5577425e-5,0.01009 -2.9111128e-4,0.02111 0,0.03125 A 0.050005,0.050005 0 0 0 0,14.25 l 0,5.0625 a 0.050005,0.050005 0 0 0 0,0.03125 0.050005,0.050005 0 0 0 0,0.03125 c 2.7397524e-4,0.0076 0.03048716,-0.0075 0.03125,0 a 0.050005,0.050005 0 0 0 0,0.03125 0.050005,0.050005 0 0 0 0.03125,0 c 0.02951574,0.118004 0.10643771,0.204628 0.21875,0.25 0.008119,0.0033 -0.008332,0.02849 0,0.03125 a 0.050005,0.050005 0 0 0 0,0.03125 c 0.007096,0.0018 0.0240449,-0.0015 0.03125,0 a 0.050005,0.050005 0 0 0 0.03125,0 L 28.4375,24.3125 c 0.07632,1.73868 0.196986,3.45307 0.375,5.1875 0.345732,3.673262 0.848433,7.32759 1.4375,10.96875 l -6.96875,1.375 -0.0625,0 a 0.050005,0.050005 0 0 0 -0.03125,0 0.050005,0.050005 0 0 0 0,0.03125 c -0.291266,0.06923 -0.590135,0.19983 -0.78125,0.4375 -0.282641,0.328422 -0.401461,0.745626 -0.46875,1.15625 -0.09612,0.640251 -0.04006,1.301405 0.03125,1.9375 0.08652,0.703658 0.205326,1.376189 0.375,2.0625 0.02,0.08426 0.07303,0.168374 0.09375,0.25 a 0.050005,0.050005 0 0 0 0,0.03125 0.050005,0.050005 0 0 0 0,0.03125 0.050005,0.050005 0 0 0 0,0.03125 0.050005,0.050005 0 0 0 0.03125,0 l 0.0625,0 4.59375,0.46875 0,0.1875 0,0.03125 a 0.050005,0.050005 0 0 0 0,0.03125 0.050005,0.050005 0 0 0 0.03125,0.03125 l 0.03125,0 3.96875,0.375 0.0625,0 a 0.050005,0.050005 0 0 0 0.03125,0 0.050005,0.050005 0 0 0 0,-0.03125 0.050005,0.050005 0 0 0 0,-0.03125 0.050005,0.050005 0 0 0 0,-0.03125 l 0.28125,-1.125 c 0.08761,0.449359 0.164528,0.858018 0.25,1.28125 0.002,0.01 -0.002,0.02127 0,0.03125 0.0054,0.0158 0.0258,0.01691 0.03125,0.03125 0.02181,0.05737 0.03806,0.120629 0.0625,0.15625 0.03055,0.04453 0.07454,0.09409 0.125,0.09375 0.05046,-3.37e-4 0.09462,-0.04919 0.125,-0.09375 0.0243,-0.03565 0.04084,-0.09925 0.0625,-0.15625 0.0054,-0.01425 0.02586,-0.01557 0.03125,-0.03125 a 0.050005,0.050005 0 0 0 0,-0.03125 l 0.25,-1.28125 0.28125,1.125 a 0.050005,0.050005 0 0 0 0,0.03125 l 0,0.03125 a 0.050005,0.050005 0 0 0 0,0.03125 0.050005,0.050005 0 0 0 0.03125,0 l 0.0625,0 3.96875,-0.375 a 0.050005,0.050005 0 0 0 0.03125,0 0.050005,0.050005 0 0 0 0.03125,-0.03125 0.050005,0.050005 0 0 0 0,-0.03125 l 0,-0.03125 0,-0.21875 4.59375,-0.4375 a 0.050005,0.050005 0 0 0 0.03125,0 0.050005,0.050005 0 0 0 0.03125,0 0.050005,0.050005 0 0 0 0.03125,0 0.050005,0.050005 0 0 0 0,-0.03125 0.050005,0.050005 0 0 0 0,-0.03125 0.050005,0.050005 0 0 0 0,-0.03125 c 0.09927,-0.372978 0.201637,-0.747919 0.28125,-1.125 0.09782,-0.502873 0.206978,-1.018007 0.25,-1.53125 8.56e-4,-0.01021 -8.2e-4,-0.02104 0,-0.03125 0.04501,-0.499379 0.03422,-1.031912 -0.03125,-1.53125 -0.06791,-0.423874 -0.1758,-0.848192 -0.46875,-1.1875 -0.191021,-0.237794 -0.489803,-0.368516 -0.78125,-0.4375 -0.01389,-0.0033 -0.01729,-0.02834 -0.03125,-0.03125 l -0.0625,0 -7,-1.375 c 0.578605,-3.59278 1.088587,-7.220459 1.4375,-10.84375 0.185606,-1.784156 0.327336,-3.55267 0.40625,-5.34375 l 28.09375,-4.5625 a 0.050005,0.050005 0 0 0 0.03125,0 c 0.01603,-0.0032 0.01585,-0.02623 0.03125,-0.03125 a 0.050005,0.050005 0 0 0 0,-0.03125 c 0.113013,-0.04503 0.18958,-0.131349 0.21875,-0.25 0.0077,-0.03145 0.06397,-0.02794 0.0625,-0.0625 a 0.050005,0.050005 0 0 0 0,-0.03125 l 0,-5.0625 0,-0.03125 c 6.4e-4,-0.02413 -0.03014,-0.03866 -0.03125,-0.0625 -0.02337,-0.501664 -0.410965,-0.931701 -0.90625,-1 -0.0096,-0.0013 -0.02158,0.001 -0.03125,0 a 0.050005,0.050005 0 0 0 0,-0.03125 0.050005,0.050005 0 0 0 -0.03125,0 l -0.03125,0 -23.53125,-1.78125 -0.03125,0 -0.03125,0 -3.78125,-1.5625 0,-0.03125 C 35.517489,8.2805897 35.403194,6.8282343 35.15625,5.375 34.999455,4.539239 34.823204,3.7020107 34.5,2.90625 34.396263,2.7291587 34.223707,2.6576159 34.03125,2.625 33.838793,2.5923841 33.615271,2.5934384 33.46875,2.5625 33.373159,2.539039 33.279419,2.5226169 33.1875,2.5 33.095581,2.4773831 33.02499,2.4607373 33,2.375 c 2e-5,-0.010496 1.57e-4,-0.020774 0,-0.03125 -0.0022,-0.1473663 -0.0087,-0.2950936 -0.03125,-0.4375 -0.02326,-0.1199278 -0.06228,-0.2252731 -0.09375,-0.34375 -0.04357,-0.1647004 -0.09116,-0.3418053 -0.15625,-0.5 -0.04566,-0.13569283 -0.124489,-0.25424267 -0.1875,-0.375 -0.04296,-0.0733644 -0.0692,-0.1478646 -0.125,-0.21875 C 32.363928,0.40814747 32.294741,0.35866921 32.25,0.3125 32.21883,0.28842774 32.193993,0.26948756 32.15625,0.25 c -0.02455,-0.0127106 -0.06329,0.007373 -0.09375,0 -0.01015,-0.002458 -0.02048,0.001121 -0.03125,0 a 0.050005,0.050005 0 0 0 0,-0.03125 c -0.01089,-8.0895e-4 -0.01977,-9.7401e-4 -0.03125,0 4.14e-4,-4.837e-5 -0.01894,5.0367e-4 -0.03125,0 -0.01231,-5.0367e-4 -0.01037,-0.0122022 -0.03125,0 z"; - -// From https://commons.wikimedia.org/wiki/File:Silhouette_An-124.svg -// (which puts the original SVG in the public domain) -var _heavy_svg = - "m28.64874,12.035023l0,8.801421l-4.585627,3.066495c0.126825,-0.257055 0.094102,-0.531839 0.095802,-0.802796l-0.015437,-3.087446l-2.230453,-0.012673l0.019009,3.599141c0.000513,0.577993 0.076338,0.923195 0.589296,1.241956l-5.533809,3.630512c0.166511,-0.256275 0.153699,-0.551367 0.153699,-0.841892l-0.005929,-3.270195l-2.160751,-0.012672l-0.006337,3.637159c0.016349,0.5301 0.096662,1.090947 0.576623,1.419379l-11.976014,7.825597c-2.106287,1.48859 -1.705322,3.044253 -1.56512,4.587637l26.645047,-9.048544l0,13.750239l0.722364,5.062875l-8.681027,6.387208c-1.239945,1.059417 -1.080616,2.171837 -0.842757,3.256969l11.278998,-2.946479c0.130159,3.116897 1.559821,3.171571 1.780561,0.006336l11.278998,2.94648c0.23786,-1.085133 0.397189,-2.197552 -0.842756,-3.256969l-8.681026,-6.387207l0.722362,-5.062875l0,-13.750239l26.645048,9.042207c0.140203,-1.543381 0.541167,-3.092711 -1.56512,-4.581301l-11.976015,-7.825597c0.47996,-0.328434 0.553938,-0.889279 0.570286,-1.419379l0,-3.63716l-2.160751,0.012673l-0.005378,3.328244c-0.002334,0.294243 0.007077,0.545056 0.178191,0.817583l-5.565189,-3.664251c0.512962,-0.318761 0.59512,-0.663963 0.595633,-1.241956l0.019009,-3.599141l-2.230454,0.012673l-0.015793,3.100403c0.001462,0.282341 -0.019949,0.535579 0.124839,0.794638l-4.614307,-3.071294l0,-8.801421c-1.111672,-11.152869 -5.489391,-11.217579 -6.735717,-0.006336z"; - -// From https://discussions.flightaware.com/ads-b-flight-tracking-f21/some-custom-svg-plane-icons-t37783.html -// by Peter Lowden -// licensed under CC BY 4.0 (https://creativecommons.org/licenses/by/4.0/) - -// NB: scales are not accurate, they have been tweaked for the sake -// of usability -var _a320 = { - key: "a320", - scale: 0.45, - size: [64, 64], - anchor: [32, 28], - path: "m 32,1 2,1 2,3 0,18 4,1 0,-4 3,0 0,5 17,6 0,3 -15,-2 -9,0 0,12 -2,6 7,3 0,2 -8,-1 -1,2 -1,-2 -8,1 0,-2 7,-3 -2,-6 0,-12 -9,0 -15,2 0,-3 17,-6 0,-5 3,0 0,4 4,-1 0,-18 2,-3 2,-1z" -}; - -var _b777 = { - key: "b777", - scale: 0.60, - size: [64, 64], - anchor: [32, 32], - path: "m 32,1 2,1 1,2 0,20 4,4 0,-4 3,0 0,4 -1,2 17,12 0,2 -16,-5 -7,0 0,13 -1,5 7,5 0,2 -8,-2 -1,2 -1,-2 -8,2 0,-2 7,-5 -1,-5 0,-13 -7,0 -16,5 0,-2 17,-12 -1,-2 0,-4 3,0 0,4 4,-4 0,-20 1,-2 2,-1z" -}; - -var _dash8 = { - key: "dash8", - scale: 0.45, - size: [64, 64], - anchor: [32, 30], - path: "m 32,1 3,4 0,20 4,0 0,-5 1,-1 1,1 0,5 17,2 0,3 -17,2 0,3 -1,1 -1,-1 0,-3 -4,0 0,15 -1,8 6,0 1,1 0,3 -8,0 -1,1 -1,-1 -8,0 0,-3 1,-1 6,0 -1,-8 0,-15 -4,0 0,3, -1,1 -1,-1 0,-3 -17,-2 0,-3 17,-2 0,-5 1,-1 1,1 0,5 4,0 0,-20 3,-4z" -}; - -var _b200 = { - key: "b200", - scale: 0.375, - size: [64, 64], - anchor: [32, 19], - path: "m 32,1 1,0 1,2 1,4 0,5 5,0 0,-5 -1,-1 2,-2 2,2 -1,1 0,5 17,2 0,3 -17,3 0,1 -2,0 0,-1 -5,0 0,5 -2,8 6,3 0,2 -6,-1 -1,0 -6,1 0,-2 6,-3 -2,-8 0,-5 -5,0 0,1, -2,0 0,-1 -17,-3 0,-3 17,-2 0,-5 -1,-1 2,-2 2,2 -1,1 0,5 5,0 0,-5 1,-4 1,-2 z" -}; - -var _g650 = { - key: "g650", - scale: 0.44, - size: [64, 64], - anchor: [32, 26], - path: "m 32,1 1,0 1,2 1,4 0,10 21,17 0,5 -2,-2 -16,-8 -3,0 0,3 2,0 1,1 0,5 -1,1 0,3 -2,0 0,1 7,5 0,3 -9,-3 -1,0 -9,3 0,-3 7,-5 0,-1 -2,0 0,-3 -1,-1 0,-5 1,-1 2,0 0,-3 -3,0 -16,8 -2,2 0,-5 21,-17 0,-10 1,-4 1,-2z" -}; - -var _c130 = { - key: "c130", - scale: 0.60, - size: [64, 64], - anchor: [32, 17], - path: "m 31,1 1,0 1,1 1,2 0,8 3,0 0,-3 1,-1 1,1 0,3 6,0 0,-3 1,-1 1,1 0,3 10,1 0,2 -1,1 -17,3 -5,0 0,10 -1,1 8,2 0,1 -1,1 -8,0 -1,1 -1,-1 -8,0 -1,-1 0,-1 8,-2 -1,-1 0,-10 -5,0 -17,-3 -1,-1 0,-2 10,-1 0,-3 1,-1 1,1 0,3 6,0 0,-3 1,-1 1,1 0,3 3,0 0,-8 1,-2 1,-1 z" -}; - -var _balloon = { - key: "balloon", - scale: 0.50, - size: [64, 64], - anchor: [32, 32], - path: "m 27,1 10,0 3,1 3,1 1,1 2,1 6,6 1,2 1,1 1,3 1,3 0,10 -1,3 -1,3 -1,1 -1,2 -6,6 -2,1 -1,1 -2,1 -2,1 -2,8 -1,0 2,-8 -3,1 -6,0 -3,-1 2,8 9,0 0,6 -10,0 0,-6 -2,-8 -2,-1 -2,-1 -1,-1 -2,-1 -6,-6 -1,-2 -1,-1 -1,-3 -1,-3 0,-10 1,-3 1,-3 1,-1 1,-2 6,-6 2,-1 1,-1 3,-1 3,-1 z", - noRotate: true, - markerRadius: 32 -}; - -var _helicopter = { - key : "helicopter", - scale : 0.40, - size : [64, 64], - anchor : [22, 32], - path : _rotorcraft_svg -}; - -var _single_prop = { - key : "single_prop", - scale : 0.35, - size : [64, 64], - anchor : [32, 25], - path : _beechcraft_svg -}; - -// by Oliver Jowett -// licensed under CC BY 4.0 (https://creativecommons.org/licenses/by/4.0/) -var _a380 = { - key: "a380", - scale: 0.75, - size: [64, 64], - anchor: [32, 30], - path: "m 32,59 -1,-4 -4,1 -7,3 -1,0 1,-3 1,-1 7,-6 2,-2 -1,-5 0,-9 -1,-2 -2,0 -6,2 -5,2 -5,2 -9,4 0,1 0,-3 1,-2 9,-7 -1,-1 0,-4 1,-1 1,0 1,1 0,3 1,0 5,-4 0,-5 1,-1 1,0 1,1 0,3 6,-5 1,-2 0,-7 1,-5 1,-2 1,-1 1,1 1,2 1,5 0,7 1,2 6,5 0,-3 1,-1 1,0 1,1 0,5 5,4 1,0 0,-3 1,-1 1,0 1,1 0,4 -1,1 9,7 1,2 0,3 0,-1 -9,-4 -5,-2 -5,-2 -6,-2 -2,0 -1,2 0,9 -1,5 2,2 7,6 1,1 1,3 -1,0 -7,-3 -4,-1 -1,4 z" -}; - -var _b738 = { - key: "b738", - scale: 0.53, - size: [64, 64], - anchor: [32, 32], - path: "m 32,61 -1,-1 -9,2 -2,1 0,-2 9,-6 1,-1 -1,-9 0,-11 -7,0 -1,1 0,-1 -3,1 -1,1 0,-1 -3,1 -9,3 -1,1 0,-2 1,-2 17,-9 1,-1 -1,-2 0,-3 1,-1 2,0 1,1 0,3 3,-2 0,-13 1,-5 1,-3 1,-1 1,1 1,3 1,5 0,13 3,2 0,-3 1,-1 2,0 1,1 0,3 -1,2 1,1 17,9 1,2 0,2 -1,-1 -9,-3 -3,-1 0,1 -1,-1 -3,-1 0,1 -1,-1 -7,0 0,11 -1,9 1,1 9,6 0,2 -2,-1 -9,-2 -1,1 z" -}; - -var _b744 = { - key: "b744", - scale: 0.71, - size: [64, 64], - anchor: [32, 32], - path: "m 32,61.4 -0.6,-3 -8.9,2.4 0,-2.1 7.6,-6.8 -0.5,-4.2 -0.4,-4.3 0,-11.7 -2.1,0.7 -0.3,1.2 -0.2,-1 -1.8,0.6 -0.3,1 -0.2,-0.9 -3.2,1.1 -0.7,0.4 -0.3,1.1 -0.2,-0.8 -2.2,1.3 -0.3,1.2 -0.2,-0.9 -8.9,5 -2.7,2.1 -0.7,1.5 0,-1.3 0.6,-2.3 0,-1.2 8.5,-7.1 -0.5,-3.3 0.2,-1.3 1.9,0 0.2,1.3 -0.4,2 6.2,-5.7 -0.6,-3.2 0.2,-1.3 1.9,0 0.2,1.3 -0.3,2 6.2,-5.8 0,-6.5 0.3,-3.78 0.7,-4.2 0.8,-2.1 1,-1.1 1,1.1 0.8,2.1 0.7,4.2 0.3,3.78 0,6.5 6.2,5.8 -0.3,-2 0.2,-1.3 1.9,0 0.2,1.3 -0.6,3.2 6.2,5.7 -0.4,-2 0.2,-1.3 1.9,0 0.2,1.3 -0.5,3.3 8.5,7.1 0,1.2 0.6,2.3 0,1.3 -0.7,-1.5 -2.7,-2.1 -8.9,-5 -0.2,0.9 -0.3,-1.2 -2.2,-1.3 -0.2,0.8 -0.3,-1.1 -0.7,-0.4 -3.2,-1.1 -0.2,0.9 -0.3,-1 -1.8,-0.6 -0.2,1 -0.3,-1.2 -2.1,-0.7 0,11.7 -0.4,4.3 -0.5,4.2 7.6,6.8 0,2.1 -8.9,-2.4 -0.6,3 z" -}; +// FA icons +var shapes = { + 'airliner': { + svg: 'airliner_live', + size: [25,26] + }, + 'balloon': { + svg: 'balloon_live', + size: [9,13], + noRotate: true + }, + 'cessna': { + svg: 'cessna_live', + size: [17,13] + }, + 'heavy_2e': { + svg: 'heavy_2e_live', + size: [28,29] + }, + 'heavy_4e': { + svg: 'heavy_4e_live', + size: [28,30] + }, + 'helicopter': { + svg: 'helicopter_live', + size: [16,18] + }, + 'hi_perf': { + svg: 'hi_perf_live', + size: [15,21] + }, + 'jet_nonswept': { + svg: 'jet_nonswept_live', + size: [18,18] + }, + 'jet_swept': { + svg: 'jet_swept_live', + size: [18,24] + }, + 'twin_large': { + svg: 'twin_large_live', + size: [21,20] + }, + 'twin_small': { + svg: 'twin_small_live', + size: [19,16] + }, + 'ground_emergency': { + svg: 'emergency_dark', + size: [6, 15] + }, + 'ground_service': { + svg: 'service_dark', + size: [6, 15] + }, + 'ground_unknown': { + svg: 'unknown_dark', + size: [6, 15] + }, + 'ground_fixed': { + svg: 'fixed_dark', + size: [12, 12] + }, + 'unknown': { + svg: 'unknown_live', + size: [17,17] + } +} var TypeDesignatorIcons = { - 'A318': _a320, // shortened a320 - 'A319': _a320, // shortened a320 - 'A320': _a320, - 'A321': _a320, // stretched a320 + 'A318': 'airliner', // shortened a320 + 'A319': 'airliner', // shortened a320 + 'A320': 'airliner', + 'A321': 'airliner', // stretched a320 - 'A388': _a380, + 'A388': 'heavy_4e', // dubious since these are old-generation 737s // but the shape is similar - 'B731': _b738, - 'B732': _b738, - 'B733': _b738, - 'B734': _b738, - 'B735': _b738, + 'B731': 'airliner', + 'B732': 'airliner', + 'B733': 'airliner', + 'B734': 'airliner', + 'B735': 'airliner', // these probably need reworking // since they vary in length - 'B736': _b738, - 'B737': _b738, - 'B738': _b738, - 'B739': _b738, + 'B736': 'airliner', + 'B737': 'airliner', + 'B738': 'airliner', + 'B739': 'airliner', - 'B741': _b744, - 'B742': _b744, - 'B743': _b744, - 'B744': _b744, - 'B74D': _b744, - 'B74S': _b744, - 'B74R': _b744, - 'BLCF': _b744, - 'BSCA': _b744, // hah! - 'B748': _b744, + 'B741': 'heavy_4e', + 'B742': 'heavy_4e', + 'B743': 'heavy_4e', + 'B744': 'heavy_4e', + 'B74D': 'heavy_4e', + 'B74S': 'heavy_4e', + 'B74R': 'heavy_4e', + 'BLCF': 'heavy_2e', + 'BSCA': 'heavy_4e', // hah! + 'B748': 'heavy_4e', - 'B772': _b777, // all pretty similar except for length - 'B77W': _b777, - 'B773': _b777, - 'B77L': _b777, + 'B772': 'heavy_2e', // all pretty similar except for length + 'B77W': 'heavy_2e', + 'B773': 'heavy_2e', + 'B77L': 'heavy_2e', - 'DH8A': _dash8, - 'DH8B': _dash8, - 'DH8C': _dash8, - 'DH8D': _dash8, + 'DH8A': 'twin_small', + 'DH8B': 'twin_small', + 'DH8C': 'twin_small', + 'DH8D': 'twin_small', - 'BE20': _b200, + 'E170': 'jet_swept', + 'E45X': 'jet_swept', + 'B712': 'jet_swept', + 'C650': 'jet_swept', + 'C750': 'jet_swept', + 'E135': 'jet_swept', + 'E145': 'jet_swept', + 'CL30': 'jet_swept', + 'CL35': 'jet_swept', + 'CL60': 'jet_swept', + 'GL5T': 'jet_swept', + 'GLF2': 'jet_swept', // close enough + 'GLF3': 'jet_swept', + 'GLF4': 'jet_swept', + 'GLF5': 'jet_swept', + 'GLF6': 'jet_swept', + 'CRJ1': 'jet_swept', + 'CRJ2': 'jet_swept', + 'CRJ7': 'jet_swept', + 'CRJ9': 'jet_swept', + 'H25A': 'jet_swept', + 'H25B': 'jet_swept', + 'H25C': 'jet_swept', + 'MD80': 'jet_swept', + 'MD81': 'jet_swept', + 'MD82': 'jet_swept', + 'MD83': 'jet_swept', + 'MD87': 'jet_swept', + 'MD88': 'jet_swept', - 'GLF5': _g650, // close enough - 'GLF6': _g650, - 'C130': _c130, - 'C30J': _c130 + + 'A37': 'hi_perf', + 'A700': 'hi_perf', + 'LEOP': 'hi_perf', + 'ME62': 'hi_perf', + 'T2': 'hi_perf', + 'T37': 'hi_perf', + 'T38': 'hi_perf', + 'A10': 'hi_perf', + 'A148': 'hi_perf', + 'A3': 'hi_perf', + 'A6': 'hi_perf', + 'AJET': 'hi_perf', + 'AT3': 'hi_perf', + 'CKUO': 'hi_perf', + 'EUFI': 'hi_perf', + 'F1': 'hi_perf', + 'F100': 'hi_perf', + 'F111': 'hi_perf', + 'F117': 'hi_perf', + 'F14': 'hi_perf', + 'F15': 'hi_perf', + 'F18': 'hi_perf', + 'F22': 'hi_perf', + 'F22A': 'hi_perf', + 'F4': 'hi_perf', + 'F5': 'hi_perf', + 'FOUG': 'hi_perf', + 'J8A': 'hi_perf', + 'J8B': 'hi_perf', + 'JH7': 'hi_perf', + 'LTNG': 'hi_perf', + 'METR': 'hi_perf', + 'MG19': 'hi_perf', + 'MG25': 'hi_perf', + 'MG29': 'hi_perf', + 'MG31': 'hi_perf', + 'MG44': 'hi_perf', + 'MIR4': 'hi_perf', + 'MT2': 'hi_perf', + 'Q5': 'hi_perf', + 'RFAL': 'hi_perf', + 'S3': 'hi_perf', + 'S37': 'hi_perf', + 'SR71': 'hi_perf', + 'SU15': 'hi_perf', + 'SU24': 'hi_perf', + 'SU25': 'hi_perf', + 'SU27': 'hi_perf', + 'T22M': 'hi_perf', + 'T4': 'hi_perf', + 'TOR': 'hi_perf', + 'TU22': 'hi_perf', + 'VAUT': 'hi_perf', + 'WB57': 'hi_perf', + 'Y130': 'hi_perf', + 'YK28': 'hi_perf', + // 'BE20': _b200, + + // 'C130': _c130, + // 'C30J': _c130 }; // Maps ICAO aircraft type description codes (e.g. "L2J") to aircraft icons. This is used if the ICAO type designator (e.g. "B731") @@ -225,98 +217,81 @@ var TypeDesignatorIcons = { // a dash (e.g. "L2J-M"). var TypeDescriptionIcons = { - 'H': _helicopter, + 'H': 'helicopter', - 'L1P': _single_prop, - 'L1T': _single_prop, + 'L1P': 'cessna', + 'L1T': 'cessna', + 'L1J': 'hi_perf', - 'L2T': _dash8, + 'L2T': 'twin_small', + 'L2P': 'twin_large', - 'L2J-L': _g650, - 'L2J-M': _a320, - 'L2J-H': _b777, + 'L2J-L': 'jet_swept', + 'L2J-M': 'airliner', + 'L2J-H': 'heavy_2e', - 'L4T': _c130, - 'L4J-H': _b744 + 'L4T': 'heavy_4e', + 'L4J-H': 'heavy_4e' }; var CategoryIcons = { - "A1" : _single_prop, + "A1" : 'cessna', - "A2" : _g650, + "A2" : 'jet_nonswept', - "A3" : _a320, + "A3" : 'airliner', - "A5" : _b777, + "A5" : 'heavy_4e', - "A7" : _helicopter, + "A7" : 'helicopter', - "B2" : _balloon -}; + "B2" : 'balloon', -var DefaultIcon = { - key : "default", - scale : 0.4, - size : [64, 64], - anchor : [32, 32], - path : _generic_plane_svg + 'C0' : 'ground_unknown', + + 'C1' : 'ground_emergency', + + 'C2' : 'ground_service', + + 'C3' : 'ground_fixed' }; function getBaseMarker(category, typeDesignator, typeDescription, wtc) { if (typeDesignator in TypeDesignatorIcons) { - return TypeDesignatorIcons[typeDesignator]; + return shapes[TypeDesignatorIcons[typeDesignator]]; } if (typeDescription !== undefined && typeDescription !== null && typeDescription.length === 3) { if (wtc !== undefined && wtc !== null && wtc.length === 1) { var typeDescriptionWithWtc = typeDescription + "-" + wtc; if (typeDescriptionWithWtc in TypeDescriptionIcons) { - return TypeDescriptionIcons[typeDescriptionWithWtc]; + return shapes[TypeDescriptionIcons[typeDescriptionWithWtc]]; } } if (typeDescription in TypeDescriptionIcons) { - return TypeDescriptionIcons[typeDescription]; + return shapes[TypeDescriptionIcons[typeDescription]]; } var basicType = typeDescription.charAt(0); if (basicType in TypeDescriptionIcons) { - return TypeDescriptionIcons[basicType]; + return shapes[TypeDescriptionIcons[basicType]]; } } if (category in CategoryIcons) { - return CategoryIcons[category]; + return shapes[CategoryIcons[category]]; } - return DefaultIcon; + return shapes['unknown']; } -function svgPathToSvg(path, size, stroke, width, fill, transparentBorderWidth) { - var svg = ''; - svg += ' 0) { - // If the border is 100% transparent, OpenLayers will ignore it completely - see - // https://github.com/openlayers/ol3/issues/2961. The stroke opacity is set to 1% as a workaround. - // This is transparent enough to be invisible to the user. - svg += ''; - } - svg += ''; - return svg; +function svgPathToSvg(path, stroke, fill, selected_stroke) { + path = path.replace('aircraft_color_fill', fill).replace('aircraft_color_stroke', stroke).replace('add_stroke_selected', selected_stroke); + return path; } -function svgPathToURI(path, size, stroke, width, fill, transparentBorderWidth) { - return "data:image/svg+xml;base64," + btoa(svgPathToSvg(path, size, stroke, width, fill, transparentBorderWidth)); +function svgPathToURI(path, stroke, fill, selected_stroke) { + return "data:image/svg+xml;base64," + btoa(svgPathToSvg(path, stroke, fill, selected_stroke)); } diff --git a/public_html/planeObject.js b/public_html/planeObject.js index ddd2130..a0df910 100644 --- a/public_html/planeObject.js +++ b/public_html/planeObject.js @@ -86,6 +86,20 @@ PlaneObject.prototype.isFiltered = function() { return planeAltitude < this.filter.minAltitude || planeAltitude > this.filter.maxAltitude; } + // filter out ground vehicles + if (typeof this.filter.groundVehicles !== 'undefined' && this.filter.groundVehicles === 'filtered') { + if (typeof this.category === 'string' && this.category.startsWith('C')) { + return true; + } + } + + // filter out blocked MLAT flights + if (typeof this.filter.blockedMLAT !== 'undefined' && this.filter.blockedMLAT === 'filtered') { + if (typeof this.icao === 'string' && this.icao.startsWith('~')) { + return true; + } + } + return false; } @@ -115,7 +129,8 @@ PlaneObject.prototype.updateTrack = function(estimate_time) { head_update: this.last_position_time, tail_update: this.last_position_time, estimated: false, - ground: (this.altitude === "ground") + ground: (this.altitude === "ground"), + altitude: this.altitude }; this.track_linesegs.push(newseg); this.history_size ++; @@ -137,6 +152,7 @@ PlaneObject.prototype.updateTrack = function(estimate_time) { this.track_linesegs.push({ fixed: new ol.geom.LineString([projPrev, projHere]), feature: null, head_update: this.last_position_time, + altitude: 0, estimated: true }); this.history_size += 2; } else { @@ -157,14 +173,15 @@ PlaneObject.prototype.updateTrack = function(estimate_time) { head_update: this.last_position_time, tail_update: this.last_position_time, estimated: false, - ground: (this.altitude === "ground") }; + ground: (this.altitude === "ground"), + altitude: this.altitude }; this.track_linesegs.push(lastseg); this.history_size ++; // continue } if ( (lastseg.ground && this.altitude !== "ground") || - (!lastseg.ground && this.altitude === "ground") ) { + (!lastseg.ground && this.altitude === "ground") || this.altitude !== lastseg.altitude ) { //console.log(this.icao + " ground state changed"); // Create a new segment as the ground state changed. // assume the state changed halfway between the two points @@ -176,6 +193,7 @@ PlaneObject.prototype.updateTrack = function(estimate_time) { head_update: this.last_position_time, tail_update: this.last_position_time, estimated: false, + altitude: this.altitude, ground: (this.altitude === "ground") }); this.history_size += 3; return true; @@ -236,33 +254,11 @@ PlaneObject.prototype.getMarkerColor = function() { var h, s, l; - if (this.altitude === null) { - h = ColorByAlt.unknown.h; - s = ColorByAlt.unknown.s; - l = ColorByAlt.unknown.l; - } else if (this.altitude === "ground") { - h = ColorByAlt.ground.h; - s = ColorByAlt.ground.s; - l = ColorByAlt.ground.l; - } else { - s = ColorByAlt.air.s; - l = ColorByAlt.air.l; + var colorArr = this.getAltitudeColor(); - // find the pair of points the current altitude lies between, - // and interpolate the hue between those points - var hpoints = ColorByAlt.air.h; - h = hpoints[0].val; - for (var i = hpoints.length-1; i >= 0; --i) { - if (this.altitude > hpoints[i].alt) { - if (i == hpoints.length-1) { - h = hpoints[i].val; - } else { - h = hpoints[i].val + (hpoints[i+1].val - hpoints[i].val) * (this.altitude - hpoints[i].alt) / (hpoints[i+1].alt - hpoints[i].alt) - } - break; - } - } - } + h = colorArr[0]; + s = colorArr[1]; + l = colorArr[2]; // If we have not seen a recent position update, change color if (this.seen_pos > 15) { @@ -300,71 +296,91 @@ PlaneObject.prototype.getMarkerColor = function() { return 'hsl(' + (h/5).toFixed(0)*5 + ',' + (s/5).toFixed(0)*5 + '%,' + (l/5).toFixed(0)*5 + '%)' } +PlaneObject.prototype.getAltitudeColor = function(altitude) { + var h, s, l; + + if (typeof altitude === 'undefined') { + altitude = this.altitude; + } + + if (altitude === null) { + h = ColorByAlt.unknown.h; + s = ColorByAlt.unknown.s; + l = ColorByAlt.unknown.l; + } else if (this.altitude === "ground") { + h = ColorByAlt.ground.h; + s = ColorByAlt.ground.s; + l = ColorByAlt.ground.l; + } else { + s = ColorByAlt.air.s; + l = ColorByAlt.air.l; + + // find the pair of points the current altitude lies between, + // and interpolate the hue between those points + var hpoints = ColorByAlt.air.h; + h = hpoints[0].val; + for (var i = hpoints.length-1; i >= 0; --i) { + if (altitude > hpoints[i].alt) { + if (i == hpoints.length-1) { + h = hpoints[i].val; + } else { + h = hpoints[i].val + (hpoints[i+1].val - hpoints[i].val) * (altitude - hpoints[i].alt) / (hpoints[i+1].alt - hpoints[i].alt) + } + break; + } + } + } + + if (h < 0) { + h = (h % 360) + 360; + } else if (h >= 360) { + h = h % 360; + } + + if (s < 5) s = 5; + else if (s > 95) s = 95; + + if (l < 5) l = 5; + else if (l > 95) l = 95; + + return [h, s, l]; +} + PlaneObject.prototype.updateIcon = function() { var scaleFactor = Math.max(0.2, Math.min(1.2, 0.15 * Math.pow(1.25, ZoomLvl))).toFixed(1); var col = this.getMarkerColor(); var opacity = 1.0; var outline = (this.position_from_mlat ? OutlineMlatColor : OutlineADSBColor); + var add_stroke = (this.selected && !SelectedAllPlanes) ? ' stroke="black" stroke-width="1px"' : ''; var baseMarker = getBaseMarker(this.category, this.icaotype, this.typeDescription, this.wtc); - var weight = ((this.selected && !SelectedAllPlanes ? 2 : 1) / baseMarker.scale / scaleFactor).toFixed(1); var rotation = (this.track === null ? 0 : this.track); - var transparentBorderWidth = (32 / baseMarker.scale / scaleFactor).toFixed(1); + //var transparentBorderWidth = (32 / baseMarker.scale / scaleFactor).toFixed(1); - var svgKey = col + '!' + outline + '!' + baseMarker.key + '!' + weight + "!" + scaleFactor; + var svgKey = col + '!' + outline + '!' + baseMarker.svg + '!' + add_stroke + "!" + scaleFactor; var styleKey = opacity + '!' + rotation; if (this.markerStyle === null || this.markerIcon === null || this.markerSvgKey != svgKey) { //console.log(this.icao + " new icon and style " + this.markerSvgKey + " -> " + svgKey); var icon = new ol.style.Icon({ - anchor: baseMarker.anchor, - anchorXUnits: 'pixels', - anchorYUnits: 'pixels', - scale: baseMarker.scale * scaleFactor, + anchor: [0.5, 0.5], + anchorXUnits: 'fraction', + anchorYUnits: 'fraction', + scale: 1.2 * scaleFactor, imgSize: baseMarker.size, - src: svgPathToURI(baseMarker.path, baseMarker.size, outline, weight, col, transparentBorderWidth), + src: svgPathToURI(baseMarker.svg, outline, col, add_stroke), rotation: (baseMarker.noRotate ? 0 : rotation * Math.PI / 180.0), opacity: opacity, rotateWithView: (baseMarker.noRotate ? false : true) }); - if (baseMarker.noRotate) { - // the base marker won't be rotated - this.markerStaticIcon = icon; - this.markerStaticStyle = new ol.style.Style({ - image: this.markerStaticIcon - }); - - // create an arrow that we will rotate around the base marker - // to indicate heading - - var offset = baseMarker.markerRadius * baseMarker.scale + 6; - var size = offset * 2; - - var arrowPath = "M " + offset + ",0 m 4,4 -8,0 4,-4 z"; - this.markerIcon = new ol.style.Icon({ - anchor: [offset, offset], - anchorXUnits: 'pixels', - anchorYUnits: 'pixels', - scale: 1.0 * scaleFactor, - imgSize: [size, size], - src: svgPathToURI(arrowPath, [size, size], outline, 1, outline, 0), - rotation: rotation * Math.PI / 180.0, - opacity: opacity, - rotateWithView: true - }); - this.markerStyle = new ol.style.Style({ - image: this.markerIcon - }); - } else { - this.markerIcon = icon; - this.markerStyle = new ol.style.Style({ - image: this.markerIcon - }); - this.markerStaticIcon = null; - this.markerStaticStyle = new ol.style.Style({}); - } + this.markerIcon = icon; + this.markerStyle = new ol.style.Style({ + image: this.markerIcon + }); + this.markerStaticIcon = null; + this.markerStaticStyle = new ol.style.Style({}); this.markerStyleKey = styleKey; this.markerSvgKey = svgKey; @@ -500,6 +516,18 @@ PlaneObject.prototype.updateMarker = function(moved) { } }; + +// return the styling of the lines based on altitude +PlaneObject.prototype.altitudeLines = function(altitude) { + var colorArr = this.getAltitudeColor(altitude); + return new ol.style.Style({ + stroke: new ol.style.Stroke({ + color: 'hsl(' + (colorArr[0]/5).toFixed(0)*5 + ',' + (colorArr[1]/5).toFixed(0)*5 + '%,' + (colorArr[2]/5).toFixed(0)*5 + '%)', + width: 2 + }) + }) +} + // Update our planes tail line, PlaneObject.prototype.updateLines = function() { if (!this.selected) @@ -542,7 +570,7 @@ PlaneObject.prototype.updateLines = function() { var lastfixed = lastseg.fixed.getCoordinateAt(1.0); var geom = new ol.geom.LineString([lastfixed, ol.proj.fromLonLat(this.position)]); this.elastic_feature = new ol.Feature(geom); - this.elastic_feature.setStyle(this.altitude === 'ground' ? groundStyle : airStyle); + this.elastic_feature.setStyle(this.altitudeLines(lastseg.altitude)); if (oldElastic < 0) { PlaneTrailFeatures.push(this.elastic_feature); @@ -557,10 +585,8 @@ PlaneObject.prototype.updateLines = function() { seg.feature = new ol.Feature(seg.fixed); if (seg.estimated) { seg.feature.setStyle(estimateStyle); - } else if (seg.ground) { - seg.feature.setStyle(groundStyle); } else { - seg.feature.setStyle(airStyle); + seg.feature.setStyle(this.altitudeLines(seg.altitude)); } PlaneTrailFeatures.push(seg.feature); diff --git a/public_html/script.js b/public_html/script.js index 687b978..bc3fcbb 100644 --- a/public_html/script.js +++ b/public_html/script.js @@ -12,7 +12,10 @@ var PlanesOrdered = []; var PlaneFilter = {}; var SelectedPlane = null; var SelectedAllPlanes = false; +var HighlightedPlane = null; var FollowSelected = false; +var infoBoxOriginalPosition = {}; +var customAltitudeColors = true; var SpecialSquawks = { '7500' : { cssClass: 'squawk7500', markerColor: 'rgb(255, 85, 85)', text: 'Aircraft Hijacking' }, @@ -45,6 +48,11 @@ var MessageRate = 0; var NBSP='\u00a0'; +var layers; + +// piaware vs flightfeeder +var isFlightFeeder = false; + function processReceiverUpdate(data) { // Loop through all the planes in the data packet var now = data.now; @@ -150,6 +158,7 @@ function fetchData() { selectNewPlanes(); refreshTableInfo(); refreshSelected(); + refreshHighlighted(); if (ReceiverClock) { var rcv = new Date(now * 1000); @@ -180,39 +189,12 @@ var PositionHistorySize = 0; function initialize() { // Set page basics document.title = PageName; - $("#infoblock_name").text(PageName); + + flightFeederCheck(); PlaneRowTemplate = document.getElementById("plane_row_template"); - if (!ShowClocks) { - $('#timestamps').css('display','none'); - } else { - // Create the clocks. - new CoolClock({ - canvasId: "utcclock", - skinId: "classic", - displayRadius: 40, - showSecondHand: true, - gmtOffset: "0", // this has to be a string! - showDigital: false, - logClock: false, - logClockRev: false - }); - - ReceiverClock = new CoolClock({ - canvasId: "receiverclock", - skinId: "classic", - displayRadius: 40, - showSecondHand: true, - gmtOffset: null, - showDigital: false, - logClock: false, - logClockRev: false - }); - - // disable ticking on the receiver clock, we will update it ourselves - ReceiverClock.tick = (function(){}) - } + refreshClock(); $("#loader").removeClass("hidden"); @@ -254,8 +236,58 @@ function initialize() { } } }); + + // check if the altitude color values are default to enable the altitude filter + if (ColorByAlt.air.h.length === 3 && ColorByAlt.air.h[0].alt === 2000 && ColorByAlt.air.h[0].val === 20 && ColorByAlt.air.h[1].alt === 10000 && ColorByAlt.air.h[1].val === 140 && ColorByAlt.air.h[2].alt === 40000 && ColorByAlt.air.h[2].val === 300) { + customAltitudeColors = false; + } + + $("#altitude_filter_reset_button").click(onResetAltitudeFilter); + $('#settingsCog').on('click', function() { + $('#settings_infoblock').toggle(); + }); + + $('#settings_close').on('click', function() { + $('#settings_infoblock').hide(); + }); + + $('#groundvehicle_filter').on('click', function() { + filterGroundVehicles(true); + refreshSelected(); + refreshHighlighted(); + refreshTableInfo(); + }); + + $('#blockedmlat_filter').on('click', function() { + filterBlockedMLAT(true); + refreshSelected(); + refreshHighlighted(); + refreshTableInfo(); + }); + + $('#grouptype_checkbox').on('click', function() { + if ($('#grouptype_checkbox').hasClass('settingsCheckboxChecked')) { + sortByDistance(); + } else { + sortByDataSource(); + } + + }); + + $('#altitude_checkbox').on('click', function() { + toggleAltitudeChart(true); + }); + + $('#selectall_checkbox').on('click', function() { + if ($('#selectall_checkbox').hasClass('settingsCheckboxChecked')) { + deselectAllPlanes(); + } else { + selectAllPlanes(); + } + }) + // Force map to redraw if sidebar container is resized - use a timer to debounce var mapResizeTimeout; $("#sidebar_container").on("resize", function() { @@ -263,6 +295,10 @@ function initialize() { mapResizeTimeout = setTimeout(updateMapSize, 10); }); + filterGroundVehicles(false); + filterBlockedMLAT(false); + toggleAltitudeChart(false); + // Get receiver metadata, reconfigure using it, then continue // with initialization $.ajax({ url: 'data/receiver.json', @@ -371,6 +407,7 @@ function end_load_history() { refreshTableInfo(); refreshSelected(); + refreshHighlighted(); reaper(); // Setup our timer to poll from the server. @@ -434,7 +471,7 @@ function initialize_map() { // Initialize OL3 - var layers = createBaseLayers(); + layers = createBaseLayers(); var iconsLayer = new ol.layer.Vector({ name: 'ac_positions', @@ -471,12 +508,14 @@ function initialize_map() { })); var foundType = false; + var baseCount = 0; ol.control.LayerSwitcher.forEachRecursive(layers, function(lyr) { if (!lyr.get('name')) return; if (lyr.get('type') === 'base') { + baseCount++; if (MapType === lyr.get('name')) { foundType = true; lyr.setVisible(true); @@ -522,14 +561,17 @@ function initialize_map() { }), controls: [new ol.control.Zoom(), new ol.control.Rotate(), - new ol.control.Attribution({collapsed: false}), - new ol.control.ScaleLine({units: DisplayUnits}), - new ol.control.LayerSwitcher() + new ol.control.Attribution({collapsed: true}), + new ol.control.ScaleLine({units: DisplayUnits}) ], loadTilesWhileAnimating: true, loadTilesWhileInteracting: true }); + if (baseCount > 1) { + OLMap.addControl(new ol.control.LayerSwitcher()); + } + // Listeners for newly created Map OLMap.getView().on('change:center', function(event) { var center = ol.proj.toLonLat(OLMap.getView().getCenter(), OLMap.getView().getProjection()); @@ -542,6 +584,7 @@ function initialize_map() { Math.abs(center[1] - selected.position[1]) > 0.0001) { FollowSelected = false; refreshSelected(); + refreshHighlighted(); } } }); @@ -573,6 +616,36 @@ function initialize_map() { } }); + + // show the hover box + OLMap.on('pointermove', function(evt) { + var hex = evt.map.forEachFeatureAtPixel(evt.pixel, + function(feature, layer) { + return feature.hex; + }, + null, + function(layer) { + return (layer === iconsLayer); + }, + null + ); + + if (hex) { + highlightPlaneByHex(hex); + } else { + removeHighlight(); + } + + }) + + // handle the layer settings pane checkboxes + OLMap.once('postrender', function(e) { + toggleLayer('#nexrad_checkbox', 'nexrad'); + toggleLayer('#sitepos_checkbox', 'site_pos'); + toggleLayer('#actrail_checkbox', 'ac_trail'); + toggleLayer('#acpositions_checkbox', 'ac_positions'); + }); + // Add home marker if requested if (SitePosition) { var markerStyle = new ol.style.Style({ @@ -652,13 +725,22 @@ function createSiteCircleFeatures() { }); SiteCircleFeatures.clear(); - var circleStyle = new ol.style.Style({ + var circleStyle = function(distance) { + return new ol.style.Style({ fill: null, stroke: new ol.style.Stroke({ color: '#000000', width: 1 - }) - }); + }), + text: new ol.style.Text({ + font: '10px Helvetica Neue, sans-serif', + fill: new ol.style.Fill({ color: '#000' }), + offsetY: -8, + text: format_distance_long(distance, DisplayUnits, 0) + + }) + }); + }; var conversionFactor = 1000.0; if (DisplayUnits === "nautical") { @@ -672,7 +754,7 @@ function createSiteCircleFeatures() { var circle = make_geodesic_circle(SitePosition, distance, 360); circle.transform('EPSG:4326', 'EPSG:3857'); var feature = new ol.Feature(circle); - feature.setStyle(circleStyle); + feature.setStyle(circleStyle(distance)); StaticFeatures.push(feature); SiteCircleFeatures.push(feature); } @@ -701,12 +783,15 @@ function reaper() { PlanesOrdered = newPlanes; refreshTableInfo(); refreshSelected(); + refreshHighlighted(); } // Page Title update function function refreshPageTitle() { - if (!PlaneCountInTitle && !MessageRateInTitle) + if (!PlaneCountInTitle && !MessageRateInTitle) { + document.title = PageName; return; + } var subtitle = ""; @@ -763,7 +848,7 @@ function refreshSelected() { } else { $('#selected_callsign').text('n/a'); } - $('#selected_flightaware_link').html(getFlightAwareModeSLink(selected.icao, selected.flight, "[FlightAware]")); + $('#selected_flightaware_link').html(getFlightAwareModeSLink(selected.icao, selected.flight, "FlightAware.com")); if (selected.registration !== null) { $('#selected_registration').text(selected.registration); @@ -777,13 +862,14 @@ function refreshSelected() { $('#selected_icaotype').text(""); } - var emerg = document.getElementById('selected_emergency'); - if (selected.squawk in SpecialSquawks) { - emerg.className = SpecialSquawks[selected.squawk].cssClass; - emerg.textContent = NBSP + 'Squawking: ' + SpecialSquawks[selected.squawk].text + NBSP ; - } else { - emerg.className = 'hidden'; - } + // Not using this logic for the redesigned info panel at the time, but leaving it in if/when adding it back + // var emerg = document.getElementById('selected_emergency'); + // if (selected.squawk in SpecialSquawks) { + // emerg.className = SpecialSquawks[selected.squawk].cssClass; + // emerg.textContent = NBSP + 'Squawking: ' + SpecialSquawks[selected.squawk].text + NBSP ; + // } else { + // emerg.className = 'hidden'; + // } $("#selected_altitude").text(format_altitude_long(selected.altitude, selected.vert_rate, DisplayUnits)); @@ -818,12 +904,13 @@ function refreshSelected() { $('#selected_position').text('n/a'); $('#selected_follow').addClass('hidden'); } else { - var mlat_bit = (selected.position_from_mlat ? "MLAT: " : ""); + if (selected.seen_pos > 1) { - $('#selected_position').text(mlat_bit + format_latlng(selected.position) + " (" + selected.seen_pos.toFixed(1) + "s)"); + $('#selected_position').text(format_latlng(selected.position)); } else { - $('#selected_position').text(mlat_bit + format_latlng(selected.position)); + $('#selected_position').text(format_latlng(selected.position)); } + $('#selected_source').text( (selected.position_from_mlat ? "MLAT" : "ADS-B")); $('#selected_follow').removeClass('hidden'); if (FollowSelected) { $('#selected_follow').css('font-weight', 'bold'); @@ -839,77 +926,131 @@ function refreshSelected() { $('#selected_photo_link').html(getFlightAwarePhotoLink(selected.registration)); } -// Refreshes the larger table of all the planes -function refreshTableInfo() { - var show_squawk_warning = false; +function refreshHighlighted() { + // this is following nearly identical logic, etc, as the refreshSelected function, but doing less junk for the highlighted pane + var highlighted = false; - TrackedAircraft = 0 - TrackedAircraftPositions = 0 - TrackedHistorySize = 0 - - $(".altitudeUnit").text(get_unit_label("altitude", DisplayUnits)); - $(".speedUnit").text(get_unit_label("speed", DisplayUnits)); - $(".distanceUnit").text(get_unit_label("distance", DisplayUnits)); - $(".verticalRateUnit").text(get_unit_label("verticalRate", DisplayUnits)); - - for (var i = 0; i < PlanesOrdered.length; ++i) { - var tableplane = PlanesOrdered[i]; - TrackedHistorySize += tableplane.history_size; - if (tableplane.seen >= 58 || tableplane.isFiltered()) { - tableplane.tr.className = "plane_table_row hidden"; - } else { - TrackedAircraft++; - var classes = "plane_table_row"; - - if (tableplane.position !== null && tableplane.seen_pos < 60) { - ++TrackedAircraftPositions; - if (tableplane.position_from_mlat) - classes += " mlat"; - else - classes += " vPosition"; - } - if (tableplane.icao == SelectedPlane) - classes += " selected"; - - if (tableplane.squawk in SpecialSquawks) { - classes = classes + " " + SpecialSquawks[tableplane.squawk].cssClass; - show_squawk_warning = true; - } - - // ICAO doesn't change - if (tableplane.flight) { - tableplane.tr.cells[2].innerHTML = getFlightAwareModeSLink(tableplane.icao, tableplane.flight, tableplane.flight); - } else { - tableplane.tr.cells[2].innerHTML = ""; - } - tableplane.tr.cells[3].textContent = (tableplane.registration !== null ? tableplane.registration : ""); - tableplane.tr.cells[4].textContent = (tableplane.icaotype !== null ? tableplane.icaotype : ""); - tableplane.tr.cells[5].textContent = (tableplane.squawk !== null ? tableplane.squawk : ""); - tableplane.tr.cells[6].innerHTML = format_altitude_brief(tableplane.altitude, tableplane.vert_rate, DisplayUnits); - tableplane.tr.cells[7].textContent = format_speed_brief(tableplane.speed, DisplayUnits); - tableplane.tr.cells[8].textContent = format_vert_rate_brief(tableplane.vert_rate, DisplayUnits); - tableplane.tr.cells[9].textContent = format_distance_brief(tableplane.sitedist, DisplayUnits); - tableplane.tr.cells[10].textContent = format_track_brief(tableplane.track); - tableplane.tr.cells[11].textContent = tableplane.messages; - tableplane.tr.cells[12].textContent = tableplane.seen.toFixed(0); - tableplane.tr.cells[13].textContent = (tableplane.rssi !== null ? tableplane.rssi : ""); - tableplane.tr.cells[14].textContent = (tableplane.position !== null ? tableplane.position[1].toFixed(4) : ""); - tableplane.tr.cells[15].textContent = (tableplane.position !== null ? tableplane.position[0].toFixed(4) : ""); - tableplane.tr.cells[16].textContent = format_data_source(tableplane.getDataSource()); - tableplane.tr.cells[17].innerHTML = getAirframesModeSLink(tableplane.icao); - tableplane.tr.cells[18].innerHTML = getFlightAwareModeSLink(tableplane.icao, tableplane.flight); - tableplane.tr.cells[19].innerHTML = getFlightAwarePhotoLink(tableplane.registration); - tableplane.tr.className = classes; - } + if (typeof HighlightedPlane !== 'undefined' && HighlightedPlane !== null) { + highlighted = Planes[HighlightedPlane]; } - if (show_squawk_warning) { - $("#SpecialSquawkWarning").css('display','block'); + // no highlighted plane + if (!highlighted) { + $('#highlighted_infoblock').hide(); + return; + } + + $('#highlighted_infoblock').show(); + + if (highlighted.flight !== null && highlighted.flight !== "") { + $('#highlighted_callsign').text(highlighted.flight); + } else { + $('#highlighted_callsign').text('n/a'); + } + + if (highlighted.icaotype !== null) { + $('#higlighted_icaotype').text(highlighted.icaotype); + } else { + $('#higlighted_icaotype').text(""); + } + + + $('#highlighted_speed').text(format_speed_long(highlighted.speed, DisplayUnits)); + + $("#highlighted_altitude").text(format_altitude_long(highlighted.altitude, highlighted.vert_rate, DisplayUnits)); + + $('#highlighted_icao').text(highlighted.icao.toUpperCase()); + +} + +function refreshClock() { + $('#clock_div').text(new Date().toLocaleString()); + var c = setTimeout(refreshClock, 500); +} + +function removeHighlight() { + HighlightedPlane = null; + refreshHighlighted(); +} + +// Refreshes the larger table of all the planes +function refreshTableInfo() { + var show_squawk_warning = false; + + TrackedAircraft = 0 + TrackedAircraftPositions = 0 + TrackedHistorySize = 0 + + $(".altitudeUnit").text(get_unit_label("altitude", DisplayUnits)); + $(".speedUnit").text(get_unit_label("speed", DisplayUnits)); + $(".distanceUnit").text(get_unit_label("distance", DisplayUnits)); + $(".verticalRateUnit").text(get_unit_label("verticalRate", DisplayUnits)); + + for (var i = 0; i < PlanesOrdered.length; ++i) { + var tableplane = PlanesOrdered[i]; + TrackedHistorySize += tableplane.history_size; + if (tableplane.seen >= 58 || tableplane.isFiltered()) { + tableplane.tr.className = "plane_table_row hidden"; + } else { + TrackedAircraft++; + var classes = "plane_table_row"; + + if (tableplane.position !== null && tableplane.seen_pos < 60) { + ++TrackedAircraftPositions; + } + + if (tableplane.getDataSource() === "adsb_icao") { + classes += " vPosition"; + } else if (tableplane.getDataSource() === "tisb_trackfile") { + classes += " tisb"; + } else if (tableplane.getDataSource() === "mlat") { + classes += " mlat"; } else { - $("#SpecialSquawkWarning").css('display','none'); + classes += " other"; } - resortTable(); + if (tableplane.icao == SelectedPlane) + classes += " selected"; + + if (tableplane.squawk in SpecialSquawks) { + classes = classes + " " + SpecialSquawks[tableplane.squawk].cssClass; + show_squawk_warning = true; + } + + // ICAO doesn't change + if (tableplane.flight) { + tableplane.tr.cells[2].innerHTML = getFlightAwareModeSLink(tableplane.icao, tableplane.flight, tableplane.flight); + } else { + tableplane.tr.cells[2].innerHTML = ""; + } + tableplane.tr.cells[3].textContent = (tableplane.registration !== null ? tableplane.registration : ""); + tableplane.tr.cells[4].textContent = (tableplane.icaotype !== null ? tableplane.icaotype : ""); + tableplane.tr.cells[5].textContent = (tableplane.squawk !== null ? tableplane.squawk : ""); + tableplane.tr.cells[6].innerHTML = format_altitude_brief(tableplane.altitude, tableplane.vert_rate, DisplayUnits); + tableplane.tr.cells[7].textContent = format_speed_brief(tableplane.speed, DisplayUnits); + tableplane.tr.cells[8].textContent = format_vert_rate_brief(tableplane.vert_rate, DisplayUnits); + tableplane.tr.cells[9].textContent = format_distance_brief(tableplane.sitedist, DisplayUnits); + tableplane.tr.cells[10].textContent = format_track_brief(tableplane.track); + tableplane.tr.cells[11].textContent = tableplane.messages; + tableplane.tr.cells[12].textContent = tableplane.seen.toFixed(0); + tableplane.tr.cells[13].textContent = (tableplane.rssi !== null ? tableplane.rssi : ""); + tableplane.tr.cells[14].textContent = (tableplane.position !== null ? tableplane.position[1].toFixed(4) : ""); + tableplane.tr.cells[15].textContent = (tableplane.position !== null ? tableplane.position[0].toFixed(4) : ""); + tableplane.tr.cells[16].textContent = format_data_source(tableplane.getDataSource()); + tableplane.tr.cells[17].innerHTML = getAirframesModeSLink(tableplane.icao); + tableplane.tr.cells[18].innerHTML = getFlightAwareModeSLink(tableplane.icao, tableplane.flight); + tableplane.tr.cells[19].innerHTML = getFlightAwarePhotoLink(tableplane.registration); + tableplane.tr.className = classes; + } +} + +if (show_squawk_warning) { + $("#SpecialSquawkWarning").css('display','block'); + } else { + $("#SpecialSquawkWarning").css('display','none'); + } + + resortTable(); } // @@ -988,6 +1129,11 @@ function resortTable() { } function sortBy(id,sc,se) { + if (id !== 'data_source') { + $('#grouptype_checkbox').removeClass('settingsCheckboxChecked'); + } else { + $('#grouptype_checkbox').addClass('settingsCheckboxChecked'); + } if (id === sortId) { sortAscending = !sortAscending; PlanesOrdered.reverse(); // this correctly flips the order of rows that compare equal @@ -1005,7 +1151,7 @@ function sortBy(id,sc,se) { function selectPlaneByHex(hex,autofollow) { //console.log("select: " + hex); // If SelectedPlane has something in it, clear out the selected - + removeHighlight(); if (SelectedAllPlanes) { deselectAllPlanes(); } @@ -1043,10 +1189,23 @@ function selectPlaneByHex(hex,autofollow) { } refreshSelected(); + refreshHighlighted(); +} + +function highlightPlaneByHex(hex) { + // if we've selected a plane, don't show the highlighting box + if (SelectedPlane != null) { + return; + } + + if (hex != null) { + HighlightedPlane = hex; + } } // loop through the planes and mark them as selected to show the paths for all planes function selectAllPlanes() { + HighlightedPlane = null; // if all planes are already selected, deselect them all if (SelectedAllPlanes) { deselectAllPlanes(); @@ -1071,7 +1230,10 @@ function selectAllPlanes() { } } + $('#selectall_checkbox').addClass('settingsCheckboxChecked'); + refreshSelected(); + refreshHighlighted(); } // on refreshes, try to find new planes and mark them as selected @@ -1101,9 +1263,11 @@ function deselectAllPlanes() { Planes[key].updateMarker(); $(Planes[key].tr).removeClass("selected"); } + $('#selectall_checkbox').removeClass('settingsCheckboxChecked'); SelectedPlane = null; SelectedAllPlanes = false; refreshSelected(); + refreshHighlighted(); } function toggleFollowSelected() { @@ -1225,6 +1389,14 @@ function adjustSelectedInfoBlockPosition() { // Get info box position and size var infoBox = $('#selected_infoblock'); var infoBoxPosition = infoBox.position(); + if (typeof infoBoxOriginalPosition.top === 'undefined') { + infoBoxOriginalPosition.top = infoBoxPosition.top; + infoBoxOriginalPosition.left = infoBoxPosition.left; + } else { + infoBox.css("left", infoBoxOriginalPosition.left); + infoBox.css("top", infoBoxOriginalPosition.top); + infoBoxPosition = infoBox.position(); + } var infoBoxExtent = getExtent(infoBoxPosition.left, infoBoxPosition.top, infoBox.outerWidth(), infoBox.outerHeight()); // Get map size @@ -1235,8 +1407,8 @@ function adjustSelectedInfoBlockPosition() { if (isPointInsideExtent(markerPosition[0], markerPosition[1], infoBoxExtent)) { // Array of possible new positions for info box var candidatePositions = []; - candidatePositions.push( { x: 20, y: 20 } ); - candidatePositions.push( { x: 20, y: markerPosition[1] + 40 } ); + candidatePositions.push( { x: 40, y: 60 } ); + candidatePositions.push( { x: 40, y: markerPosition[1] + 80 } ); // Find new position for (var i = 0; i < candidatePositions.length; i++) { @@ -1276,6 +1448,8 @@ function initializeUnitsSelector() { var displayUnits = localStorage['displayUnits']; DisplayUnits = displayUnits; + setAltitudeLegend(displayUnits); + // Initialize drop-down var unitsSelector = $("#units_selector"); unitsSelector.val(displayUnits); @@ -1288,12 +1462,15 @@ function onDisplayUnitsChanged(e) { localStorage['displayUnits'] = displayUnits; DisplayUnits = displayUnits; + setAltitudeLegend(displayUnits); + // Update filters updatePlaneFilter(); // Refresh data refreshTableInfo(); refreshSelected(); + refreshHighlighted(); // Redraw range rings if (SitePosition !== null && SitePosition !== undefined && SiteCircles) { @@ -1308,6 +1485,14 @@ function onDisplayUnitsChanged(e) { }); } +function setAltitudeLegend(units) { + if (units === 'metric') { + $('#altitude_chart_button').addClass('altitudeMeters'); + } else { + $('#altitude_chart_button').removeClass('altitudeMeters'); + } +} + function onFilterByAltitude(e) { e.preventDefault(); updatePlaneFilter(); @@ -1320,9 +1505,68 @@ function onFilterByAltitude(e) { selectedPlane.clearLines(); selectedPlane.updateMarker(); refreshSelected(); + refreshHighlighted(); } } +function filterGroundVehicles(switchFilter) { + if (typeof localStorage['groundVehicleFilter'] === 'undefined') { + localStorage['groundVehicleFilter'] = 'not_filtered'; + } + var groundFilter = localStorage['groundVehicleFilter']; + if (switchFilter === true) { + groundFilter = (groundFilter === 'not_filtered') ? 'filtered' : 'not_filtered'; + } + if (groundFilter === 'not_filtered') { + $('#groundvehicle_filter').addClass('settingsCheckboxChecked'); + } else { + $('#groundvehicle_filter').removeClass('settingsCheckboxChecked'); + } + localStorage['groundVehicleFilter'] = groundFilter; + PlaneFilter.groundVehicles = groundFilter; +} + +function filterBlockedMLAT(switchFilter) { + if (typeof localStorage['blockedMLATFilter'] === 'undefined') { + localStorage['blockedMLATFilter'] = 'not_filtered'; + } + var blockedMLATFilter = localStorage['blockedMLATFilter']; + if (switchFilter === true) { + blockedMLATFilter = (blockedMLATFilter === 'not_filtered') ? 'filtered' : 'not_filtered'; + } + if (blockedMLATFilter === 'not_filtered') { + $('#blockedmlat_filter').addClass('settingsCheckboxChecked'); + } else { + $('#blockedmlat_filter').removeClass('settingsCheckboxChecked'); + } + localStorage['blockedMLATFilter'] = blockedMLATFilter; + PlaneFilter.blockedMLAT = blockedMLATFilter; +} + +function toggleAltitudeChart(switchToggle) { + if (typeof localStorage['altitudeChart'] === 'undefined') { + localStorage['altitudeChart'] = 'show'; + } + var altitudeChartDisplay = localStorage['altitudeChart']; + if (switchToggle === true) { + altitudeChartDisplay = (altitudeChartDisplay === 'show') ? 'hidden' : 'show'; + } + // if you're using custom colors always hide the chart + if (customAltitudeColors === true) { + altitudeChartDisplay = 'hidden'; + // also hide the control option + $('#altitude_chart_container').hide(); + } + if (altitudeChartDisplay === 'show') { + $('#altitude_checkbox').addClass('settingsCheckboxChecked'); + $('#altitude_chart').show(); + } else { + $('#altitude_checkbox').removeClass('settingsCheckboxChecked'); + $('#altitude_chart').hide(); + } + localStorage['altitudeChart'] = altitudeChartDisplay; +} + function onResetAltitudeFilter(e) { $("#altitude_filter_min").val(""); $("#altitude_filter_max").val(""); @@ -1378,7 +1622,7 @@ function getFlightAwareModeSLink(code, ident, linkText) { function getFlightAwarePhotoLink(registration) { if (registration !== null && registration !== "") { - return "See Photos"; + return "See Aircraft Photos"; } return ""; @@ -1391,3 +1635,57 @@ function getAirframesModeSLink(code) { return ""; } + + +// takes in an elemnt jQuery path and the OL3 layer name and toggles the visibility based on clicking it +function toggleLayer(element, layer) { + // set initial checked status + ol.control.LayerSwitcher.forEachRecursive(layers, function(lyr) { + if (lyr.get('name') === layer && lyr.getVisible()) { + $(element).addClass('settingsCheckboxChecked'); + } + }); + $(element).on('click', function() { + var visible = false; + if ($(element).hasClass('settingsCheckboxChecked')) { + visible = true; + } + ol.control.LayerSwitcher.forEachRecursive(layers, function(lyr) { + if (lyr.get('name') === layer) { + if (visible) { + lyr.setVisible(false); + $(element).removeClass('settingsCheckboxChecked'); + } else { + lyr.setVisible(true); + $(element).addClass('settingsCheckboxChecked'); + } + } + }); + }); +} + +// check status.json if it has a serial number for a flightfeeder +function flightFeederCheck() { + $.ajax('/status.json', { + success: function(data) { + if (data.type === "flightfeeder") { + isFlightFeeder = true; + updatePiAwareOrFlightFeeder(); + } + } + }) +} + +// updates the page to replace piaware with flightfeeder references +function updatePiAwareOrFlightFeeder() { + if (isFlightFeeder) { + $('.piAwareLogo').hide(); + $('.flightfeederLogo').show(); + PageName = 'FlightFeeder Skyview'; + } else { + $('.flightfeederLogo').hide(); + $('.piAwareLogo').show(); + PageName = 'PiAware Skyview'; + } + refreshPageTitle(); +} diff --git a/public_html/style.css b/public_html/style.css index 456f310..9121863 100644 --- a/public_html/style.css +++ b/public_html/style.css @@ -1,19 +1,19 @@ html, body { - margin: 0; padding: 0; background-color: #ffffff; font-family: Tahoma, Sans-Serif; + margin: 0; padding: 0; background-color: #ffffff; font-family: Helvetica Neue, Sans-Serif; font-size: 10pt; overflow: auto; height: 100%; } #layout_container { display: flex; - height: 100%; + height: calc(100% - 60px);; } #selected_infoblock { position: absolute; left: 40px; - top: 10px; - min-width: 360px; - padding: 20px; + top: 60px; + min-width: 394px; + padding: 10px; background: #ffffff; box-shadow: 4px 4px 10px #444444; cursor: pointer; @@ -35,15 +35,16 @@ html, body { #toggle_sidebar_control { display: block; position: absolute; - top: 10px; - right: 10px; + top: 16px; + right: -3px; } #toggle_sidebar_button { + cursor: pointer; float: right; - width: 32px; - height: 28px; - background-size: 32px 28px; + width: 24px; + height: 25px; + background-size: 24px 25px; background-repeat: no-repeat; background-position: 0px; background-color: transparent; @@ -51,33 +52,26 @@ html, body { } #toggle_sidebar_button.show_sidebar { - background-image: url("images/show_sidebar_inactive_48x40.png"); -} - -#toggle_sidebar_button.show_sidebar:hover { - background-image: url("images/show_sidebar_active_48x40.png"); + background-image: url("images/table-icon.png"); } #toggle_sidebar_button.hide_sidebar { - background-image: url("images/hide_sidebar_inactive_48x40.png"); -} - -#toggle_sidebar_button.hide_sidebar:hover { - background-image: url("images/hide_sidebar_active_48x40.png"); + background-image: url("images/map-icon.png"); } #expand_sidebar_control { display: block; position: absolute; top: 48px; - right: 10px; + right: -3px; } #expand_sidebar_button { + cursor: pointer; float: right; - width: 32px; - height: 28px; - background-size: 32px 28px; + width: 24px; + height: 25px; + background-size: 24px 25px; background-repeat: no-repeat; background-position: 0px; background-color: transparent; @@ -85,24 +79,53 @@ html, body { } #expand_sidebar_button { - background-image: url("images/show_sidebar_inactive_48x40.png"); -} - -#expand_sidebar_button:hover { - background-image: url("images/show_sidebar_active_48x40.png"); + background-image: url("images/table-icon.png"); } #sidebar_container { display: flex; - width: 470px; + width: 500px; left: 0 !important; } + #splitter { - flex: 0 0 6px; cursor: col-resize; - background-color: #bbbbbb; - left: 0 !important; + display: block; + position: absolute; + top: 125px; + left: -24px; + float: right; + width: 24px; + height: 25px; + background-size: 24px 25px; + background-repeat: no-repeat; + background-position: 0px; + background-color: transparent; + border: none; + background-image: url("images/column-adjust.png"); +} + +.ol-zoom-in { + background-image: url("images/zoom-in.png"); + color:transparent !important; + width: 19px !important; + height: 19px !important; + background-color: transparent !important; + margin-bottom: 5px !important; +} + +.ol-zoom-out { + background-image: url("images/zoom-out.png"); + color:transparent !important; + width: 19px !important; + height: 19px !important; + background-color: transparent !important; +} + +.ol-zoom { + background-color: transparent !important; + left: 10px !important; } #sidebar_canvas { @@ -138,7 +161,7 @@ div#loader { z-index: 99; position: absolute; left: 0; top: 0; bottom: 0; right: } .aircraft_table_header { - background-color: #409EDF; + background-color: #002F5D; color: #FFFFFF; cursor: pointer; } @@ -157,22 +180,22 @@ div#loader { z-index: 99; position: absolute; left: 0; top: 0; bottom: 0; right: text-transform: uppercase; } -.vPosition { background-color: #C3FFDF; } -.mlat { background-color: #C7EAFC; } +.vPosition { background-color: #E5F6FC; } +.mlat { background-color: #FDF2E5; } +.other { background-color: #CCD5F8; } +.tisb { background-color: #FFF3B8; } .squawk7500 { font-weight: bold; background-color: #ff5555; } .squawk7600 { font-weight: bold; background-color: #00ffff; } .squawk7700 { font-weight: bold; background-color: #ffff00; } .selected { background-color: #dddddd; } -.plane_table_row { cursor: pointer; } +.plane_table_row { + cursor: pointer; + font-family: Helvetica Neue; +} .hidden { display: none; } .infoblock_heading { font-size: larger; } .infoblock_heading a { text-decoration: none; color: blue; font-size: x-small;} -.infoblock_body { font-size: small; } - -#selected_icao { font-size: x-small; } -#selected_registration { font-size: x-small; } -#selected_icaotype { font-size: x-small; } .dim { opacity: 0.3; filter:alpha(opacity=30); /* For IE8 and earlier */ } @@ -199,6 +222,490 @@ select.error, textarea.error, input.error { } .layer-switcher { - top: 86px !important; + bottom: 80px !important; + top: auto !important; right: 10px !important; } + +/* new css */ +.rangeRingText +{ + font-family: Helvetica Neue; + font-weight: bold; + font-size: 8px; + color: #333333; + color: rgb(51, 51, 51); +} + +.dateTime +{ + font-family: Helvetica Neue; + font-weight: bold; + font-size: 14px; + line-height: 18px; + color: #FFFFFF; + color: rgb(255, 255, 255); + line-height: 60px; + text-align: right; + display: inline-block; + padding-right: 20px; +} + +.infoHeading +{ + font-family: Helvetica Neue; + font-size: 14px; + line-height: 18px; + color: #002F5D; + color: rgb(0, 47, 93); +} + +.infoData +{ + font-family: Helvetica Neue; + font-size: 14px; + line-height: 18px; + color: #000000; + color: rgb(0, 0, 0); +} + +.legend +{ + font-family: Helvetica Neue; + width: 100%; + font-size: 12px; + color: #000000; + color: rgb(0, 0, 0); + display: inline-flex; + justify-content: flex-end; + padding-top: 10px; +} + +.settingsHeading +{ + font-family: Helvetica Neue; + font-size: 14px; + line-height: 20px; + color: #002F5D; + color: rgb(0, 47, 93); +} + +.settingsText +{ + font-family: Helvetica Neue; + font-size: 14px; + line-height: 20px; + text-indent: 16px + color: #000000; + color: rgb(0, 0, 0); +} + +.link +{ + font-family: Helvetica Neue; + font-size: 10px; + line-height: 20px; + color: #0000C8; + color: rgb(0, 0, 200); + text-decoration: underline; +} + +.infoHeading +{ + font-family: Helvetica Neue; + font-size: 12px; + line-height: 16px; + color: #666666; + color: rgb(102, 102, 102); +} + +.infoData +{ + font-family: Helvetica Neue; + font-size: 12px; + line-height: 16px; + color: #000000; + color: rgb(0, 0, 0); +} + +#header { + width: 100%; + height: 60px; + background: #002F5D; + background: -webkit-linear-gradient(#002F5D, #002F5D 60%, #021624); + background: -moz-linear-gradient(#002F5D, #002F5D 60%, #021624); + background: -ms-linear-gradient(#002F5D, #002F5D 60%, #021624); + background: linear-gradient(#002F5D, #002F5D 60%, #021624); + display: flex; + box-shadow: -6px 0px 8px #999999; + z-index: 99999; +} + +.flightawareLogo { + background-color: #FFF; + padding-top: 7px; + padding-bottom: 6px; + padding-left: 20px; + padding-right: 20px; + width: 121px; + height: 46px; + box-shadow:inset -12px 0 12px -12px #000000; +} + +.adsbLogo { + padding-left: 20px; + padding-top: 30px; + padding-bottom: 5px; +} + +.piAwareLogo { + width: 186px; + height: 24px; +} +.flightfeederLogo { + width: 229px; + height: 24px; +} + +.logoContainer { + flex: 1; +} + +.buttonContainer { + margin-left: auto; +} + +.buttonText +{ + font-family: Helvetica Neue; + font-weight: bold; + font-size: 12px; + color: #FFFFFF; + color: rgb(255, 255, 255); + line-height: 28px; + padding-left: 10px; + padding-right: 10px; +} + +.button { + background: #00A0E2; + background: rgba(0, 160, 226, 1); + min-width: 80px; + height: 28px; + border-radius: 4px; + -moz-border-radius: 4px; + -webkit-border-radius: 4px; + display: inline-block; + margin-right: 10px; + cursor: pointer; + text-align: center; +} + +.buttonHeader { + margin-top: 15px; +} + +.buttonTable { + margin-bottom: 5px; +} + +.settingsContainer { + padding-right: 60px; + padding-left: 2px; + margin-top: 18px; + margin-left: auto; + cursor: pointer; +} + +#highlighted_infoblock { + position: absolute; + left: 40px; + top: 60px; + min-width: 168px; + padding-right: 5px; + background: #ffffff; + box-shadow: 4px 4px 10px #444444; + cursor: pointer; + z-index: 9999; + display: none; +} + +.highlightedTitle { + height: 36px; + border-bottom: 1px solid #00A0E2; + padding-left: 18px; + padding-top: 14px; +} + +.highlightedInfo { + padding-left: 10px; +} + +.identLarge { + font-family: Helvetica Neue; + font-size: 24px; + line-height: 20px; + color: #002F5D; + color: rgb(0, 47, 93); + font-weight: lighter; +} + +.identSmall { + font-family: Helvetica Neue; + font-size: 12px; + font-weight: bold; + line-height: 20px; + color: #00A0E2; + color: rgb(0, 160, 226); +} + +.highlightedInfo { + padding-bottom: 12px; +} + +.infoRowTitle { + display: inline-block; + width: 50%; +} + +.infoRowContent { + display: inline-block; + width: 40%; +} + +.infoRowFluid { + display: inline-block; +} + +.infoRow { + padding-top: 10px; +} + +.removePadding { + padding: 0; +} + +.rightLink { + float: right; + padding-right: 5px; +} + +.infoBlockTopSection { + padding-top: 14px; + padding-bottom: 14px; + padding-left: 8px; +} + +.infoBlock45pxSection { + height: 45px; + line-height: 45px; + padding-left: 10px; +} + +.infoBlockSection { + padding-top: 14px; + padding-bottom: 14px; + padding-left: 10px; +} + +.lightGreyBackground { + background-color: #efefef; +} + +.fourColumnSection1 { + width: 20%; +} + +.fourColumnSection2 { + width: 20%; +} + +.fourColumnSection3 { + width: 20%; +} + +.fourColumnSection4 { + width: 20%; +} + +#dump1090_infoblock { + font-family: Helvetica Neue; +} + +.infoBlockTitleText { + font-weight: bold; + color: #002F5D; +} + +.legendBox { + width: 15px; + height: 15px; + border: 1px solid #efefef; + border-radius: 4px; + -moz-border-radius: 4px; + -webkit-border-radius: 4px; +} + +#adsbLegendBox { + background-color: #E5F6FC; +} + +#mlatLegendBox { + background-color: #FDF2E5; +} + +#otherLegendBox { + background-color: #E6E6E6; +} + +#tisbLegendBox { + background-color: #CCD5DF; +} + +.legendTitle { + /*margin-left: auto;*/ + line-height: 19px; + display: inline-block; + padding-right: 20px; + padding-left: 5px; +} + +#settings_infoblock { + position: absolute; + right: 1px; + top: 60px; + width: 398px; + min-height: 180px; + background: #ffffff; + box-shadow: 4px 4px 10px #444444; + padding: 20px; + z-index: 9999; + display: none; +} + +.settingsColumn { + display: table-cell; + width: 199px; +} +.settingsOptionContainer { + display: table; + padding-bottom: 10px; +} + +.settingsCheckbox { + width: 20px; + height: 11px; + background-image: url('images/box-empty.png'); + background-repeat: no-repeat; + background-position: center; + cursor: pointer; +} + +.settingsCheckboxChecked { + background-image: url('images/box-checked.png') !important; +} + +.settingsCloseBox { + position: absolute; + right: 8px; + top: 8px; + background-image: url('images/close-settings.png'); + width: 20px; + height: 20px; + cursor: pointer; +} + +.settingsText { + line-height: 20px; + display: table-cell; +} + +#altitude_chart { + float: right; + width: calc(100% - 5px); + max-width: 800px; + right: 5px; + bottom: 35px; + background-color: transparent !important; +} + +#altitude_chart_button { + background-image: url('images/alt_legend_feet.svg'); + background-size: cover; + background-color: transparent; + width: 100%; + height: 0; + padding: 0; + padding-bottom: calc(100% * 56 / 1815); +} + +.altitudeMeters { + background-image: url('images/alt_legend_meters.svg') !important; +} + +/* remove the blue highlighting around the map buttons */ +.ol-control button { + outline: none; +} + +/* Retina 2x images */ +@media (-webkit-min-device-pixel-ratio: 2), (min-resolution: 192dpi) { + .settingsCloseBox { + background-image: url('images/close-settings@2x.png'); + } + .settingsCheckboxChecked { + background-image: url('images/box-checked@2x.png') !important; + } + .settingsCheckbox { + background-image: url('images/box-empty@2x.png'); + } + .ol-zoom-out { + background-image: url("images/zoom-out@2x.png"); + } + .ol-zoom-in { + background-image: url("images/zoom-in@2x.png"); + } + #splitter { + background-image: url("images/column-adjust@2x.png"); + } + #toggle_sidebar_button.show_sidebar { + background-image: url("images/table-icon@2x.png"); + } + #expand_sidebar_button { + background-image: url("images/table-icon@2x.png"); + } + #toggle_sidebar_button.hide_sidebar { + background-image: url("images/map-icon@2x.png"); + } +} + +/* Retina 3x images */ +@media (-webkit-min-device-pixel-ratio: 3), (min-resolution: 192dpi) { + .settingsCloseBox { + background-image: url('images/close-settings@3x.png'); + } + .settingsCheckboxChecked { + background-image: url('images/box-checked@3x.png') !important; + } + .settingsCheckbox { + background-image: url('images/box-empty@3x.png'); + } + .ol-zoom-out { + background-image: url("images/zoom-out@3x.png"); + } + .ol-zoom-in { + background-image: url("images/zoom-in@3x.png"); + } + #splitter { + background-image: url("images/column-adjust@3x.png"); + } + #toggle_sidebar_button.show_sidebar { + background-image: url("images/table-icon@3x.png"); + } + #expand_sidebar_button { + background-image: url("images/table-icon@3x.png"); + } + #toggle_sidebar_button.hide_sidebar { + background-image: url("images/map-icon@3x.png"); + } +} \ No newline at end of file