mirror of
https://github.com/Pax1601/DCSOlympus.git
synced 2025-10-29 16:56:34 +00:00
Added logs on client
Airplanes are now shown with silhouettes
This commit is contained in:
@@ -5,5 +5,3 @@ explosion
|
||||
wrong name for ground units
|
||||
improve map zIndex
|
||||
human symbol if user
|
||||
|
||||
IF YOU DISCONNECT IT FLAGS YOU DEAD AND YOU DISAPPEAR!
|
||||
5
client/public/images/units/listNames.py
Normal file
5
client/public/images/units/listNames.py
Normal file
@@ -0,0 +1,5 @@
|
||||
from os import listdir
|
||||
from os.path import isfile, join
|
||||
onlyfiles = [f for f in listdir(".") if isfile(join(".", f))]
|
||||
|
||||
print(onlyfiles)
|
||||
@@ -77,7 +77,7 @@ body {
|
||||
position: absolute;
|
||||
height: 30px;
|
||||
width: 160px;
|
||||
bottom: 10px;
|
||||
bottom: 20px;
|
||||
right: 10px;
|
||||
z-index: 1000;
|
||||
}
|
||||
@@ -86,11 +86,20 @@ body {
|
||||
position: absolute;
|
||||
height: fit-content;
|
||||
width: 160px;
|
||||
bottom: 50px;
|
||||
bottom: 60px;
|
||||
right: 10px;
|
||||
z-index: 1000;
|
||||
}
|
||||
|
||||
#log-panel {
|
||||
position: absolute;
|
||||
height: 200px;
|
||||
width: 400px;
|
||||
top: 60px;
|
||||
left: 10px;
|
||||
z-index: 1000;
|
||||
}
|
||||
|
||||
@media only screen and (max-width: 1000px) {
|
||||
#unit-control-buttons {
|
||||
top: 50px;
|
||||
|
||||
23
client/public/stylesheets/logpanel.css
Normal file
23
client/public/stylesheets/logpanel.css
Normal file
@@ -0,0 +1,23 @@
|
||||
#log-panel {
|
||||
overflow-y: scroll;
|
||||
padding: 10px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
row-gap: 2px;
|
||||
}
|
||||
|
||||
.ol-log-element {
|
||||
font-size: 12px;
|
||||
color: white;
|
||||
text-shadow: 1px 1px 0px black, 1px -1px 0px black, -1px 1px 0px black, -1px -1px 0px black;
|
||||
font-weight: 600;
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
#log-panel {
|
||||
-ms-overflow-style: none; /* Internet Explorer 10+ */
|
||||
scrollbar-width: none; /* Firefox */
|
||||
}
|
||||
#log-panel::-webkit-scrollbar {
|
||||
display: none; /* Safari and Chrome */
|
||||
}
|
||||
@@ -5,7 +5,7 @@
|
||||
row-gap: 5px;
|
||||
}
|
||||
|
||||
#mouse-info-panel .rectangular-container{
|
||||
#mouse-info-panel .ol-rectangular-container{
|
||||
width: 100%;
|
||||
font-weight: 600;
|
||||
font-size: 12px;
|
||||
|
||||
@@ -2,7 +2,13 @@
|
||||
.ol-panel {
|
||||
background-color: var(--background-color-dark);
|
||||
font-size: 12px;
|
||||
transition: bottom 0.2s;
|
||||
border-radius: 15px;
|
||||
box-shadow: 0px 2px 5px #000A;
|
||||
}
|
||||
|
||||
.ol-panel-transparent {
|
||||
background-color: transparent;
|
||||
font-size: 12px;
|
||||
box-shadow: 0px 0px 0px transparent;
|
||||
border-radius: 0px;
|
||||
}
|
||||
|
||||
@@ -5,7 +5,6 @@
|
||||
width: 220px;
|
||||
height: fit-content;
|
||||
z-index: 2000;
|
||||
max-height: 400px;
|
||||
padding: 8px;
|
||||
display: flex;
|
||||
flex-direction: column;
|
||||
@@ -35,6 +34,7 @@
|
||||
overflow-y: auto;
|
||||
height: 100%;
|
||||
width: 100%;
|
||||
max-height: 400px;
|
||||
}
|
||||
|
||||
.ol-selection-scroll::-webkit-scrollbar {
|
||||
|
||||
@@ -14,6 +14,7 @@
|
||||
@import url("visibilitycontrolpanel.css");
|
||||
@import url("unitinfopanel.css");
|
||||
@import url("mouseinfopanel.css");
|
||||
@import url("logpanel.css");
|
||||
|
||||
@import url("layout.css");
|
||||
|
||||
@@ -45,7 +46,7 @@ html {
|
||||
cursor:crosshair;
|
||||
}
|
||||
|
||||
.rectangular-container {
|
||||
.ol-rectangular-container {
|
||||
padding: 0.5em;
|
||||
background-color: gray;
|
||||
border-radius: 5px;
|
||||
@@ -56,7 +57,7 @@ html {
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.rectangular-container-dark {
|
||||
.ol-rectangular-container-dark {
|
||||
padding-left: 0.5em;
|
||||
padding-right: 0.5em;
|
||||
padding-top: 0.2em;
|
||||
@@ -70,7 +71,7 @@ html {
|
||||
font-size: 12px;
|
||||
}
|
||||
|
||||
.rounded-container {
|
||||
.ol-rounded-container {
|
||||
position: relative;
|
||||
padding: 0.5em;
|
||||
width: fit-content;
|
||||
@@ -82,21 +83,21 @@ html {
|
||||
background-color: gray;
|
||||
}
|
||||
|
||||
.rounded-container.blue {
|
||||
.ol-rounded-container.blue {
|
||||
background-color: var(--blue-coalition-color);
|
||||
border: 1px solid var(--blue-coalition-color);
|
||||
}
|
||||
|
||||
.rounded-container.red {
|
||||
.ol-rounded-container.red {
|
||||
background-color: var(--red-coalition-color);
|
||||
border: 1px solid var(--red-coalition-color);
|
||||
}
|
||||
|
||||
.rounded-container.neutral {
|
||||
.ol-rounded-container.neutral {
|
||||
background-color: var(--neutral-coalition-color);
|
||||
}
|
||||
|
||||
.rounded-container-small {
|
||||
.ol-rounded-container-small {
|
||||
padding: 0.2em;
|
||||
width: fit-content;
|
||||
height: fit-content;
|
||||
@@ -110,7 +111,7 @@ html {
|
||||
padding-right: 5px;
|
||||
}
|
||||
|
||||
.rectangular-button {
|
||||
.ol-rectangular-button {
|
||||
position: relative;
|
||||
padding: 0.5em;
|
||||
width: fit-content;
|
||||
@@ -128,48 +129,48 @@ html {
|
||||
column-gap: 5px;
|
||||
}
|
||||
|
||||
.rectangular-button.blue {
|
||||
.ol-rectangular-button.blue {
|
||||
border: 1px solid var(--blue-coalition-color);
|
||||
color: var(--blue-coalition-color);
|
||||
}
|
||||
|
||||
.rectangular-button.red {
|
||||
.ol-rectangular-button.red {
|
||||
border: 1px solid var(--red-coalition-color);
|
||||
color: var(--red-coalition-color);
|
||||
}
|
||||
|
||||
.rectangular-button.white {
|
||||
.ol-rectangular-button.white {
|
||||
border: 1px solid white;
|
||||
color: white;
|
||||
}
|
||||
|
||||
.rectangular-button.white>img {
|
||||
.ol-rectangular-button.white>img {
|
||||
filter: invert(100%);
|
||||
}
|
||||
|
||||
.rectangular-button>img {
|
||||
.ol-rectangular-button>img {
|
||||
display: inline-block;
|
||||
height: 18px;
|
||||
width: 18px;
|
||||
}
|
||||
|
||||
.rectangular-button.red {
|
||||
.ol-rectangular-button.red {
|
||||
border: 1px solid var(--red-coalition-color);
|
||||
}
|
||||
|
||||
.vl {
|
||||
.ol-vl {
|
||||
border-left: 1px solid #555;
|
||||
width: 1px !important;
|
||||
display: inline-block;
|
||||
}
|
||||
|
||||
.hl {
|
||||
.ol-hl {
|
||||
border-top: 1px solid #555;
|
||||
height: 1px !important;
|
||||
display: inline-block;
|
||||
}
|
||||
|
||||
.measure-box {
|
||||
.ol-measure-box {
|
||||
position: absolute;
|
||||
padding-left: 0.5em;
|
||||
padding-right: 0.5em;
|
||||
|
||||
@@ -65,17 +65,17 @@
|
||||
height: 100%;
|
||||
}
|
||||
|
||||
#selected-units-container .rounded-container {
|
||||
#selected-units-container .ol-rounded-container {
|
||||
width: calc(100% - 25px);
|
||||
cursor: pointer;
|
||||
margin-left: 25px;
|
||||
}
|
||||
|
||||
#selected-units-container .rounded-container.not-selected {
|
||||
#selected-units-container .ol-rounded-container.not-selected {
|
||||
background-color: transparent;
|
||||
}
|
||||
|
||||
#selected-units-container .rounded-container .rounded-container-small {
|
||||
#selected-units-container .ol-rounded-container .ol-rounded-container-small {
|
||||
display: inline-block;
|
||||
position: absolute;
|
||||
left: 5px;
|
||||
@@ -98,7 +98,7 @@
|
||||
filter: invert(93%) sepia(97%) saturate(1174%) hue-rotate(291deg) brightness(105%) contrast(97%);
|
||||
}
|
||||
|
||||
#unit-control-panel #title-label {
|
||||
#unit-control-panel .ol-title-label {
|
||||
color: white;
|
||||
font-size: 14px;
|
||||
width: 100%;
|
||||
|
||||
@@ -15,7 +15,7 @@
|
||||
width: 100%;
|
||||
}
|
||||
|
||||
#unit-info-panel>.vl {
|
||||
#unit-info-panel>.ol-vl {
|
||||
margin-left: 30px;
|
||||
margin-right: 30px;
|
||||
}
|
||||
|
||||
@@ -1,8 +1,8 @@
|
||||
.unit-marker-container {
|
||||
.ol-unit-marker-container {
|
||||
height: 60px;
|
||||
width: 60px;
|
||||
left: -30px;
|
||||
top: -30px;
|
||||
left: 0px;
|
||||
top: 0px;
|
||||
border: 0px black solid;
|
||||
position: absolute;
|
||||
padding: 0;
|
||||
@@ -10,7 +10,7 @@
|
||||
border-collapse: collapse;
|
||||
}
|
||||
|
||||
.unit-marker-icon {
|
||||
.ol-unit-marker-icon {
|
||||
height: 60px;
|
||||
width: 60px;
|
||||
left: 0px;
|
||||
@@ -21,24 +21,24 @@
|
||||
align-items: center;
|
||||
}
|
||||
|
||||
.unit-marker-image {
|
||||
.ol-unit-marker-image {
|
||||
height: 60px;
|
||||
width: 60px;
|
||||
}
|
||||
|
||||
.blue.unit-marker-image {
|
||||
filter: invert(40%) sepia(94%) saturate(2477%) hue-rotate(197deg) brightness(92%) contrast(91%) drop-shadow(1px 1px #FFFA) drop-shadow(1px -1px #FFFA) drop-shadow(-1px 1px 0px #FFFA) drop-shadow(-1px -1px #FFFA);
|
||||
.blue.ol-unit-marker-image {
|
||||
filter: invert(40%) sepia(94%) saturate(2477%) hue-rotate(197deg) brightness(92%) contrast(91%) drop-shadow(1px 1px #0005) drop-shadow(1px -1px #0005) drop-shadow(-1px 1px 0px #0005) drop-shadow(-1px -1px #0005);
|
||||
}
|
||||
|
||||
.red.unit-marker-image {
|
||||
filter:invert(32%) sepia(91%) saturate(5128%) hue-rotate(349deg) brightness(97%) contrast(97%) drop-shadow(1px 1px #FFFA) drop-shadow(1px -1px #FFFA) drop-shadow(-1px 1px 0px #FFFA) drop-shadow(-1px -1px #FFFA);
|
||||
.red.ol-unit-marker-image {
|
||||
filter:invert(32%) sepia(91%) saturate(5128%) hue-rotate(349deg) brightness(97%) contrast(97%) drop-shadow(1px 1px #0005) drop-shadow(1px -1px #0005) drop-shadow(-1px 1px 0px #0005) drop-shadow(-1px -1px #0005);
|
||||
}
|
||||
|
||||
.neutral.unit-marker-image {
|
||||
filter: invert(71%) sepia(12%) saturate(9%) hue-rotate(319deg) brightness(92%) contrast(96%) drop-shadow(1px 1px #FFFA) drop-shadow(1px -1px #FFFA) drop-shadow(-1px 1px 0px #FFFA) drop-shadow(-1px -1px #FFFA);
|
||||
.neutral.ol-unit-marker-image {
|
||||
filter: invert(71%) sepia(12%) saturate(9%) hue-rotate(319deg) brightness(92%) contrast(96%) drop-shadow(1px 1px #0005) drop-shadow(1px -1px #0005) drop-shadow(-1px 1px 0px #0005) drop-shadow(-1px -1px #0005);
|
||||
}
|
||||
|
||||
.unit-marker-selected {
|
||||
.ol-unit-marker-selected {
|
||||
width: 100%;
|
||||
height: 100%;
|
||||
border-radius: 50%;
|
||||
@@ -59,23 +59,23 @@
|
||||
opacity: 0.2;
|
||||
}
|
||||
|
||||
.blue.unit-marker-selected {
|
||||
.blue.ol-unit-marker-selected {
|
||||
background-color: var(--blue-coalition-color);
|
||||
}
|
||||
|
||||
.red.unit-marker-selected {
|
||||
.red.ol-unit-marker-selected {
|
||||
background-color: var(--red-coalition-color);
|
||||
}
|
||||
|
||||
.unit-marker-hovered {
|
||||
.ol-unit-marker-hovered {
|
||||
filter: brightness(130%);
|
||||
}
|
||||
|
||||
.unit-marker-dead {
|
||||
.ol-unit-marker-dead {
|
||||
filter: brightness(50%);
|
||||
}
|
||||
|
||||
.unit-marker-unitName {
|
||||
.ol-unit-marker-unitName {
|
||||
top: -20px;
|
||||
position: absolute;
|
||||
text-align: center;
|
||||
@@ -85,8 +85,8 @@
|
||||
-webkit-text-stroke: 1px;
|
||||
}
|
||||
|
||||
.unit-marker-name {
|
||||
bottom: -20px;
|
||||
.ol-unit-marker-name {
|
||||
bottom: -12px;
|
||||
position: absolute;
|
||||
text-align: center;
|
||||
font: 800 12px Arial;
|
||||
@@ -95,7 +95,7 @@
|
||||
-webkit-text-stroke: 1px;
|
||||
}
|
||||
|
||||
.unit-marker-altitude {
|
||||
.ol-unit-marker-altitude {
|
||||
width: 100%;
|
||||
left: 0px;
|
||||
top: 0px;
|
||||
@@ -107,7 +107,7 @@
|
||||
-webkit-text-stroke: 1px;
|
||||
}
|
||||
|
||||
.unit-marker-speed {
|
||||
.ol-unit-marker-speed {
|
||||
width: 100%;
|
||||
left: 0px;
|
||||
top: 0px;
|
||||
@@ -119,6 +119,6 @@
|
||||
-webkit-text-stroke: 1px;
|
||||
}
|
||||
|
||||
.unit-marker-container-table-dead .unit-marker-name {
|
||||
.ol-unit-marker-container-table-dead .ol-unit-marker-name {
|
||||
opacity: 0;
|
||||
}
|
||||
@@ -10,7 +10,7 @@
|
||||
font-weight: 600;
|
||||
}
|
||||
|
||||
#visibility-control-panel .vl {
|
||||
#visibility-control-panel .ol-vl {
|
||||
height: 60%;
|
||||
}
|
||||
|
||||
|
||||
@@ -6,12 +6,11 @@ import { UnitInfoPanel } from "./panels/unitinfopanel";
|
||||
import { SelectionScroll } from "./controls/selectionscroll";
|
||||
import { Dropdown } from "./controls/dropdown";
|
||||
import { ConnectionStatusPanel } from "./panels/connectionstatuspanel";
|
||||
import { Button } from "./controls/button";
|
||||
import { MissionData } from "./missiondata/missiondata";
|
||||
import { UnitControlPanel } from "./panels/unitcontrolpanel";
|
||||
import { MouseInfoPanel } from "./panels/mouseInfoPanel";
|
||||
import { Slider } from "./controls/slider";
|
||||
import { VisibilityControlPanel } from "./panels/visibilitycontrolpanel";
|
||||
import { LogPanel } from "./panels/logpanel";
|
||||
|
||||
/* TODO: should this be a class? */
|
||||
var map: Map;
|
||||
@@ -26,18 +25,10 @@ var connectionStatusPanel: ConnectionStatusPanel;
|
||||
var unitControlPanel: UnitControlPanel;
|
||||
var mouseInfoPanel: MouseInfoPanel;
|
||||
var visibilityControlPanel: VisibilityControlPanel;
|
||||
var logPanel: LogPanel;
|
||||
|
||||
var scenarioDropdown: Dropdown;
|
||||
var mapSourceDropdown: Dropdown;
|
||||
|
||||
var slowButton: Button;
|
||||
var fastButton: Button;
|
||||
var climbButton: Button;
|
||||
var descendButton: Button;
|
||||
|
||||
var altitudeSlider: Slider;
|
||||
var airspeedSlider: Slider;
|
||||
|
||||
var connected: boolean;
|
||||
var activeCoalition: string;
|
||||
|
||||
@@ -45,6 +36,7 @@ function setup() {
|
||||
/* Initialize */
|
||||
map = new Map('map-container');
|
||||
unitsManager = new UnitsManager();
|
||||
missionData = new MissionData();
|
||||
|
||||
selectionWheel = new SelectionWheel("selection-wheel");
|
||||
selectionScroll = new SelectionScroll("selection-scroll");
|
||||
@@ -54,22 +46,10 @@ function setup() {
|
||||
connectionStatusPanel = new ConnectionStatusPanel("connection-status-panel");
|
||||
mouseInfoPanel = new MouseInfoPanel("mouse-info-panel");
|
||||
visibilityControlPanel = new VisibilityControlPanel("visibility-control-panel");
|
||||
logPanel = new LogPanel("log-panel");
|
||||
|
||||
scenarioDropdown = new Dropdown("scenario-dropdown", ["Caucasus", "Syria", "Marianas", "Nevada", "South Atlantic", "The channel"], () => { });
|
||||
mapSourceDropdown = new Dropdown("map-source-dropdown", map.getLayers(), (option: string) => map.setLayer(option));
|
||||
|
||||
missionData = new MissionData();
|
||||
|
||||
/* Unit control buttons */
|
||||
slowButton = new Button("slow-button", ["images/buttons/slow.svg"], () => { getUnitsManager().selectedUnitsChangeSpeed("slow"); });
|
||||
fastButton = new Button("fast-button", ["images/buttons/fast.svg"], () => { getUnitsManager().selectedUnitsChangeSpeed("fast"); });
|
||||
climbButton = new Button("climb-button", ["images/buttons/climb.svg"], () => { getUnitsManager().selectedUnitsChangeAltitude("climb"); });
|
||||
descendButton = new Button("descend-button", ["images/buttons/descend.svg"], () => { getUnitsManager().selectedUnitsChangeAltitude("descend"); });
|
||||
|
||||
/* Unit control sliders */
|
||||
altitudeSlider = new Slider("altitude-slider", 0, 100, "ft", (value: number) => getUnitsManager().selectedUnitsSetAltitude(value * 0.3048));
|
||||
airspeedSlider = new Slider("airspeed-slider", 0, 100, "kts", (value: number) => getUnitsManager().selectedUnitsSetSpeed(value / 1.94384));
|
||||
|
||||
/* Default values */
|
||||
activeCoalition = "blue";
|
||||
connected = false;
|
||||
@@ -87,6 +67,7 @@ function requestUpdate() {
|
||||
export function update(data: JSON) {
|
||||
unitsManager.update(data);
|
||||
missionData.update(data);
|
||||
logPanel.update(data);
|
||||
}
|
||||
|
||||
export function getMap() {
|
||||
@@ -137,8 +118,4 @@ export function getConnected() {
|
||||
return connected;
|
||||
}
|
||||
|
||||
export function getUnitControlSliders() {
|
||||
return {altitude: altitudeSlider, airspeed: airspeedSlider}
|
||||
}
|
||||
|
||||
window.onload = setup;
|
||||
@@ -2,7 +2,7 @@ import * as L from "leaflet"
|
||||
import { getSelectionWheel, getSelectionScroll, getUnitsManager, getActiveCoalition, getMouseInfoPanel } from "..";
|
||||
import { spawnAircraft, spawnGroundUnit, spawnSmoke } from "../dcs/dcs";
|
||||
import { bearing, distance, zeroAppend } from "../other/utils";
|
||||
import { aircraftDatabase, getAircraftLabelsByRole, getLoadoutsByName, getLoadoutNamesByRole } from "../units/aircraftDatabase";
|
||||
import { aircraftDatabase, getAircraftLabelsByRole, getLoadoutsByName, getLoadoutNamesByRole, getAircraftNameByLabel } from "../units/aircraftDatabase";
|
||||
import { unitTypes } from "../units/unitTypes";
|
||||
import { BoxSelect } from "./boxselect";
|
||||
|
||||
@@ -46,7 +46,7 @@ export class Map extends L.Map {
|
||||
this.#measureIcon = new L.Icon({ iconUrl: 'images/pin.png', iconAnchor: [16, 32]});
|
||||
this.#measureMarker = new L.Marker([0, 0], {icon: this.#measureIcon, interactive: false});
|
||||
this.#measureLineDiv = document.createElement("div");
|
||||
this.#measureLineDiv.classList.add("measure-box");
|
||||
this.#measureLineDiv.classList.add("ol-measure-box");
|
||||
this.#measureLineDiv.style.display = 'none';
|
||||
|
||||
document.body.appendChild(this.#measureLineDiv);
|
||||
@@ -324,10 +324,12 @@ export class Map extends L.Map {
|
||||
this.hideSelectionWheel();
|
||||
this.hideSelectionScroll();
|
||||
var options = getAircraftLabelsByRole(role);
|
||||
this.showSelectionScroll(e, "Select aircraft", options, (unitType: string) => {
|
||||
this.showSelectionScroll(e, "Select aircraft", options, (label: string) => {
|
||||
this.hideSelectionWheel();
|
||||
this.hideSelectionScroll();
|
||||
this.#unitSelectPayload(e, unitType, role);
|
||||
var name = getAircraftNameByLabel(label);
|
||||
if (name != null)
|
||||
this.#unitSelectPayload(e, name, role);
|
||||
}, true);
|
||||
}
|
||||
|
||||
|
||||
@@ -1,24 +1,22 @@
|
||||
export class ConnectionStatusPanel {
|
||||
#element: HTMLElement
|
||||
import { Panel } from "./panel";
|
||||
|
||||
export class ConnectionStatusPanel extends Panel {
|
||||
constructor(ID: string) {
|
||||
this.#element = <HTMLElement>document.getElementById(ID);
|
||||
super(ID);
|
||||
}
|
||||
|
||||
update(connected: boolean) {
|
||||
if (this.#element != null) {
|
||||
var div = this.#element.querySelector("#status-string");
|
||||
if (div != null) {
|
||||
if (connected) {
|
||||
div.innerHTML = "Connected";
|
||||
div.classList.add("ol-status-connected");
|
||||
div.classList.remove("ol-status-disconnected");
|
||||
}
|
||||
else {
|
||||
div.innerHTML = "Disconnected";
|
||||
div.classList.add("ol-status-disconnected");
|
||||
div.classList.remove("ol-status-connected");
|
||||
}
|
||||
var div = this.getElement().querySelector("#status-string");
|
||||
if (div != null) {
|
||||
if (connected) {
|
||||
div.innerHTML = "Connected";
|
||||
div.classList.add("ol-status-connected");
|
||||
div.classList.remove("ol-status-disconnected");
|
||||
}
|
||||
else {
|
||||
div.innerHTML = "Disconnected";
|
||||
div.classList.add("ol-status-disconnected");
|
||||
div.classList.remove("ol-status-connected");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
28
client/src/panels/logpanel.ts
Normal file
28
client/src/panels/logpanel.ts
Normal file
@@ -0,0 +1,28 @@
|
||||
import { Panel } from "./panel";
|
||||
|
||||
export class LogPanel extends Panel
|
||||
{
|
||||
#logs: String[];
|
||||
|
||||
constructor(ID: string)
|
||||
{
|
||||
super(ID);
|
||||
this.#logs = [];
|
||||
}
|
||||
|
||||
update(data: any)
|
||||
{
|
||||
var logs = data["logs"];
|
||||
for (let idx in logs)
|
||||
{
|
||||
if (parseInt(idx) >= this.#logs.length) {
|
||||
this.#logs.push(logs[idx]);
|
||||
var el = document.createElement("div");
|
||||
el.innerHTML = logs[idx];
|
||||
el.classList.add("js-log-element", "ol-log-element");
|
||||
this.getElement().appendChild(el);
|
||||
this.getElement().scrollTop = this.getElement().scrollHeight;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
@@ -1,28 +1,11 @@
|
||||
import { LatLng } from "leaflet";
|
||||
import { getMissionData } from "..";
|
||||
import { distance, bearing, zeroPad, zeroAppend } from "../other/utils";
|
||||
import { Unit } from "../units/unit";
|
||||
|
||||
export class MouseInfoPanel {
|
||||
#element: HTMLElement
|
||||
#display: string;
|
||||
import { Panel } from "./panel";
|
||||
|
||||
export class MouseInfoPanel extends Panel {
|
||||
constructor(ID: string) {
|
||||
this.#element = <HTMLElement>document.getElementById(ID);
|
||||
this.#display = '';
|
||||
if (this.#element != null) {
|
||||
this.#display = this.#element.style.display;
|
||||
var el = <HTMLElement>this.#element.querySelector(`#measure-position`);
|
||||
this.show();
|
||||
}
|
||||
}
|
||||
|
||||
show() {
|
||||
this.#element.style.display = this.#display;
|
||||
}
|
||||
|
||||
hide() {
|
||||
this.#element.style.display = "none";
|
||||
super(ID);
|
||||
}
|
||||
|
||||
update(mousePosition: LatLng, measurePosition: LatLng | null, unitPosition: LatLng | null) {
|
||||
@@ -31,7 +14,7 @@ export class MouseInfoPanel {
|
||||
{
|
||||
var dist = distance(bullseyes[idx].lat, bullseyes[idx].lng, mousePosition.lat, mousePosition.lng);
|
||||
var bear = bearing(bullseyes[idx].lat, bullseyes[idx].lng, mousePosition.lat, mousePosition.lng);
|
||||
var el = <HTMLElement>this.#element.querySelector(`#bullseye-${idx}`);
|
||||
var el = <HTMLElement>this.getElement().querySelector(`#bullseye-${idx}`);
|
||||
if (el != null)
|
||||
el.innerHTML = `${zeroAppend(Math.floor(bear), 3)}° / ${zeroAppend(Math.floor(dist*0.000539957), 3)} NM`
|
||||
}
|
||||
@@ -39,16 +22,16 @@ export class MouseInfoPanel {
|
||||
if (measurePosition) {
|
||||
var dist = distance(measurePosition.lat, measurePosition.lng, mousePosition.lat, mousePosition.lng);
|
||||
var bear = bearing(measurePosition.lat, measurePosition.lng, mousePosition.lat, mousePosition.lng);
|
||||
var el = <HTMLElement>this.#element.querySelector(`#measure-position`);
|
||||
var el = <HTMLElement>this.getElement().querySelector(`#measure-position`);
|
||||
if (el != null)
|
||||
{
|
||||
el.innerHTML = `${zeroAppend(Math.floor(bear), 3)}° / ${zeroAppend(Math.floor(dist*0.000539957), 3)} NM`
|
||||
if (el.parentElement != null)
|
||||
el.parentElement.style.display = 'flex'; //TODO: don't like that its hardcoded
|
||||
el.parentElement.style.display = 'flex'; //TODO: don't like that it's hardcoded
|
||||
}
|
||||
}
|
||||
else {
|
||||
var el = <HTMLElement>this.#element.querySelector(`#measure-position`);
|
||||
var el = <HTMLElement>this.getElement().querySelector(`#measure-position`);
|
||||
if (el != null && el.parentElement != null)
|
||||
el.parentElement.style.display = 'none';
|
||||
}
|
||||
@@ -56,7 +39,7 @@ export class MouseInfoPanel {
|
||||
if (unitPosition) {
|
||||
var dist = distance(unitPosition.lat, unitPosition.lng, mousePosition.lat, mousePosition.lng);
|
||||
var bear = bearing(unitPosition.lat, unitPosition.lng, mousePosition.lat, mousePosition.lng);
|
||||
var el = <HTMLElement>this.#element.querySelector(`#unit-position`);
|
||||
var el = <HTMLElement>this.getElement().querySelector(`#unit-position`);
|
||||
if (el != null)
|
||||
{
|
||||
el.innerHTML = `${zeroAppend(Math.floor(bear), 3)}° / ${zeroAppend(Math.floor(dist*0.000539957), 3)} NM`
|
||||
@@ -65,7 +48,7 @@ export class MouseInfoPanel {
|
||||
}
|
||||
}
|
||||
else {
|
||||
var el = <HTMLElement>this.#element.querySelector(`#unit-position`);
|
||||
var el = <HTMLElement>this.getElement().querySelector(`#unit-position`);
|
||||
if (el != null && el.parentElement != null)
|
||||
el.parentElement.style.display = 'none';
|
||||
}
|
||||
|
||||
22
client/src/panels/panel.ts
Normal file
22
client/src/panels/panel.ts
Normal file
@@ -0,0 +1,22 @@
|
||||
export class Panel {
|
||||
#element: HTMLElement
|
||||
#display: string;
|
||||
|
||||
constructor(ID: string) {
|
||||
this.#element = <HTMLElement>document.getElementById(ID);
|
||||
this.#display = '';
|
||||
this.#display = this.#element.style.display;
|
||||
}
|
||||
|
||||
show() {
|
||||
this.#element.style.display = this.#display;
|
||||
}
|
||||
|
||||
hide() {
|
||||
this.#element.style.display = "none";
|
||||
}
|
||||
|
||||
getElement() {
|
||||
return this.#element;
|
||||
}
|
||||
}
|
||||
@@ -1,159 +1,155 @@
|
||||
import { imageOverlay } from "leaflet";
|
||||
import { getUnitControlSliders, getUnitsManager } from "..";
|
||||
import { ConvertDDToDMS, rad2deg } from "../other/utils";
|
||||
import { getUnitsManager } from "..";
|
||||
import { Slider } from "../controls/slider";
|
||||
import { Aircraft, AirUnit, GroundUnit, Helicopter, NavyUnit, Unit } from "../units/unit";
|
||||
import { Panel } from "./panel";
|
||||
|
||||
export class UnitControlPanel {
|
||||
#element: HTMLElement
|
||||
#display: string;
|
||||
interface Button {
|
||||
id: string,
|
||||
value: string,
|
||||
element: null | HTMLElement
|
||||
}
|
||||
|
||||
export class UnitControlPanel extends Panel {
|
||||
#altitudeSlider: Slider;
|
||||
#airspeedSlider: Slider;
|
||||
#formationCreationContainer: HTMLElement;
|
||||
#ROEButtonsContainer: HTMLElement;
|
||||
#reactionToThreatButtonsContainer: HTMLElement;
|
||||
#selectedUnitsContainer: HTMLElement;
|
||||
#ROEButtons: Button[] = [
|
||||
{id: "#free", value: "Free", element: null},
|
||||
{id: "#designated-free", value: "Designated free", element: null},
|
||||
{id: "#designated", value: "Designated", element: null},
|
||||
{id: "#return", value: "Return", element: null},
|
||||
{id: "#hold", value: "Hold", element: null}
|
||||
]
|
||||
#reactionToThreatButtons: Button[] = [
|
||||
{id: "#none", value: "None", element: null},
|
||||
{id: "#passive", value: "Passive", element: null},
|
||||
{id: "#evade", value: "Evade", element: null},
|
||||
{id: "#escape", value: "Escape", element: null},
|
||||
{id: "#abort", value: "Abort", element: null}
|
||||
]
|
||||
|
||||
constructor(ID: string) {
|
||||
this.#element = <HTMLElement>document.getElementById(ID);
|
||||
this.#display = '';
|
||||
if (this.#element != null) {
|
||||
this.#display = this.#element.style.display;
|
||||
var formationCreationContainer = <HTMLElement>(this.#element.querySelector("#formation-creation-container"));
|
||||
if (formationCreationContainer != null)
|
||||
{
|
||||
var createButton = <HTMLElement>formationCreationContainer.querySelector("#create-formation");
|
||||
createButton?.addEventListener("click", () => getUnitsManager().selectedUnitsCreateFormation());
|
||||
super(ID);
|
||||
|
||||
var undoButton = <HTMLElement>formationCreationContainer.querySelector("#undo-formation");
|
||||
undoButton?.addEventListener("click", () => getUnitsManager().selectedUnitsUndoFormation());
|
||||
}
|
||||
var ROEButtonsContainer = <HTMLElement>(this.#element.querySelector("#roe-buttons-container"));
|
||||
if (ROEButtonsContainer != null)
|
||||
{
|
||||
(<HTMLElement>ROEButtonsContainer.querySelector("#free"))?.addEventListener("click", () => getUnitsManager().selectedUnitsSetROE("Free"));
|
||||
(<HTMLElement>ROEButtonsContainer.querySelector("#designated-free"))?.addEventListener("click", () => getUnitsManager().selectedUnitsSetROE("Designated free"));
|
||||
(<HTMLElement>ROEButtonsContainer.querySelector("#designated"))?.addEventListener("click", () => getUnitsManager().selectedUnitsSetROE("Designated"));
|
||||
(<HTMLElement>ROEButtonsContainer.querySelector("#return"))?.addEventListener("click", () => getUnitsManager().selectedUnitsSetROE("Return"));
|
||||
(<HTMLElement>ROEButtonsContainer.querySelector("#hold"))?.addEventListener("click", () => getUnitsManager().selectedUnitsSetROE("Hold"));
|
||||
}
|
||||
/* Selected units container */
|
||||
this.#selectedUnitsContainer = <HTMLElement>(this.getElement().querySelector("#selected-units-container"));
|
||||
|
||||
var reactionToThreatButtonsContainer = <HTMLElement>(this.#element.querySelector("#reaction-to-threat-buttons-container"));
|
||||
if (reactionToThreatButtonsContainer != null)
|
||||
{
|
||||
(<HTMLElement>reactionToThreatButtonsContainer.querySelector("#none"))?.addEventListener("click", () => getUnitsManager().selectedUnitsSetReactionToThreat("None"));
|
||||
(<HTMLElement>reactionToThreatButtonsContainer.querySelector("#passive"))?.addEventListener("click", () => getUnitsManager().selectedUnitsSetReactionToThreat("Passive"));
|
||||
(<HTMLElement>reactionToThreatButtonsContainer.querySelector("#evade"))?.addEventListener("click", () => getUnitsManager().selectedUnitsSetReactionToThreat("Evade"));
|
||||
(<HTMLElement>reactionToThreatButtonsContainer.querySelector("#escape"))?.addEventListener("click", () => getUnitsManager().selectedUnitsSetReactionToThreat("Escape"));
|
||||
(<HTMLElement>reactionToThreatButtonsContainer.querySelector("#abort"))?.addEventListener("click", () => getUnitsManager().selectedUnitsSetReactionToThreat("Abort"));
|
||||
}
|
||||
this.hide();
|
||||
/* Unit control sliders */
|
||||
this.#altitudeSlider = new Slider("altitude-slider", 0, 100, "ft", (value: number) => getUnitsManager().selectedUnitsSetAltitude(value * 0.3048));
|
||||
this.#airspeedSlider = new Slider("airspeed-slider", 0, 100, "kts", (value: number) => getUnitsManager().selectedUnitsSetSpeed(value / 1.94384));
|
||||
|
||||
/* Formation control buttons */
|
||||
this.#formationCreationContainer = <HTMLElement>(this.getElement().querySelector("#formation-creation-container"));
|
||||
//var createButton = <HTMLElement>this.#formationCreationContainer.querySelector("#create-formation");
|
||||
//createButton?.addEventListener("click", () => getUnitsManager().selectedUnitsCreateFormation());
|
||||
//var undoButton = <HTMLElement>this.#formationCreationContainer.querySelector("#undo-formation");
|
||||
//undoButton?.addEventListener("click", () => getUnitsManager().selectedUnitsUndoFormation());
|
||||
|
||||
/* ROE buttons */
|
||||
this.#ROEButtonsContainer = <HTMLElement>(this.getElement().querySelector("#roe-buttons-container"));
|
||||
for (let button of this.#ROEButtons)
|
||||
{
|
||||
button.element = <HTMLElement>(this.#ROEButtonsContainer.querySelector(button.id));
|
||||
button.element?.addEventListener("click", () => getUnitsManager().selectedUnitsSetROE(button.value));
|
||||
}
|
||||
|
||||
/* Reaction to threat buttons */
|
||||
this.#reactionToThreatButtonsContainer = <HTMLElement>(this.getElement().querySelector("#reaction-to-threat-buttons-container"));
|
||||
for (let button of this.#reactionToThreatButtons)
|
||||
{
|
||||
button.element = <HTMLElement>(this.#reactionToThreatButtonsContainer.querySelector(button.id));
|
||||
button.element?.addEventListener("click", () => getUnitsManager().selectedUnitsSetReactionToThreat(button.value));
|
||||
}
|
||||
}
|
||||
|
||||
show() {
|
||||
this.#element.style.display = this.#display;
|
||||
}
|
||||
|
||||
hide() {
|
||||
this.#element.style.display = "none";
|
||||
this.hide();
|
||||
}
|
||||
|
||||
update(units: Unit[]) {
|
||||
if (this.#element != null)
|
||||
if (this.getElement() != null)
|
||||
{
|
||||
var selectedUnitsContainer = <HTMLElement>(this.#element.querySelector("#selected-units-container"));
|
||||
var formationCreationContainer = <HTMLElement>(this.#element.querySelector("#formation-creation-container"));
|
||||
if (selectedUnitsContainer != null && formationCreationContainer != null)
|
||||
{
|
||||
this.#addUnitsButtons(units, selectedUnitsContainer);
|
||||
this.#showFlightControlSliders(units);
|
||||
this.#showFormationButtons(units, formationCreationContainer);
|
||||
}
|
||||
//this.#addUnitsButtons(units);
|
||||
//this.#showFormationButtons(units);
|
||||
|
||||
this.#showFlightControlSliders(units);
|
||||
|
||||
var ROEButtonsContainer = <HTMLElement>(this.#element.querySelector("#roe-buttons-container"));
|
||||
if (ROEButtonsContainer != null)
|
||||
{
|
||||
(<HTMLElement>ROEButtonsContainer.querySelector("#free"))?.classList.toggle("white", this.#getROE(units) === "Free");
|
||||
(<HTMLElement>ROEButtonsContainer.querySelector("#designated-free"))?.classList.toggle("white", this.#getROE(units) === "Designated free");
|
||||
(<HTMLElement>ROEButtonsContainer.querySelector("#designated"))?.classList.toggle("white", this.#getROE(units) === "Designated");
|
||||
(<HTMLElement>ROEButtonsContainer.querySelector("#return"))?.classList.toggle("white", this.#getROE(units) === "Return");
|
||||
(<HTMLElement>ROEButtonsContainer.querySelector("#hold"))?.classList.toggle("white", this.#getROE(units) === "Hold");
|
||||
}
|
||||
|
||||
var reactionToThreatButtonsContainer = <HTMLElement>(this.#element.querySelector("#reaction-to-threat-buttons-container"));
|
||||
if (reactionToThreatButtonsContainer != null)
|
||||
{
|
||||
(<HTMLElement>reactionToThreatButtonsContainer.querySelector("#none"))?.classList.toggle("white", this.#getReactionToThreat(units) === "None");
|
||||
(<HTMLElement>reactionToThreatButtonsContainer.querySelector("#passive"))?.classList.toggle("white", this.#getReactionToThreat(units) === "Passive");
|
||||
(<HTMLElement>reactionToThreatButtonsContainer.querySelector("#evade"))?.classList.toggle("white", this.#getReactionToThreat(units) === "Evade");
|
||||
(<HTMLElement>reactionToThreatButtonsContainer.querySelector("#escape"))?.classList.toggle("white", this.#getReactionToThreat(units) === "Escape");
|
||||
(<HTMLElement>reactionToThreatButtonsContainer.querySelector("#abort"))?.classList.toggle("white", this.#getReactionToThreat(units) === "Abort");
|
||||
}
|
||||
for (let button of this.#ROEButtons)
|
||||
button.element?.classList.toggle("white", this.#getROE(units) === button.value);
|
||||
|
||||
for (let button of this.#reactionToThreatButtons)
|
||||
button.element?.classList.toggle("white", this.#getReactionToThreat(units) === button.value);
|
||||
}
|
||||
}
|
||||
|
||||
#showFlightControlSliders(units: Unit[])
|
||||
{
|
||||
var sliders = getUnitControlSliders();
|
||||
sliders.airspeed.show();
|
||||
sliders.altitude.show();
|
||||
this.#airspeedSlider.show();
|
||||
this.#altitudeSlider.show();
|
||||
|
||||
if (this.#checkAllUnitsAircraft(units))
|
||||
{
|
||||
sliders.airspeed.setMinMax(100, 600);
|
||||
sliders.altitude.setMinMax(0, 50000);
|
||||
this.#airspeedSlider.setMinMax(100, 600);
|
||||
this.#altitudeSlider.setMinMax(0, 50000);
|
||||
}
|
||||
else if (this.#checkAllUnitsHelicopter(units))
|
||||
{
|
||||
sliders.airspeed.setMinMax(0, 200);
|
||||
sliders.altitude.setMinMax(0, 10000);
|
||||
this.#airspeedSlider.setMinMax(0, 200);
|
||||
this.#altitudeSlider.setMinMax(0, 10000);
|
||||
}
|
||||
else if (this.#checkAllUnitsGroundUnit(units))
|
||||
{
|
||||
sliders.airspeed.setMinMax(0, 60);
|
||||
sliders.altitude.hide();
|
||||
this.#airspeedSlider.setMinMax(0, 60);
|
||||
this.#altitudeSlider.hide();
|
||||
}
|
||||
else if (this.#checkAllUnitsNavyUnit(units))
|
||||
{
|
||||
sliders.airspeed.setMinMax(0, 60);
|
||||
sliders.altitude.hide();
|
||||
this.#airspeedSlider.setMinMax(0, 60);
|
||||
this.#altitudeSlider.hide();
|
||||
}
|
||||
else {
|
||||
sliders.airspeed.hide();
|
||||
sliders.altitude.hide();
|
||||
this.#airspeedSlider.hide();
|
||||
this.#altitudeSlider.hide();
|
||||
}
|
||||
|
||||
var targetSpeed = this.#getTargetAirspeed(units);
|
||||
if (targetSpeed != null)
|
||||
{
|
||||
sliders.airspeed.setActive(true);
|
||||
sliders.airspeed.setValue(targetSpeed * 1.94384);
|
||||
this.#airspeedSlider.setActive(true);
|
||||
this.#airspeedSlider.setValue(targetSpeed * 1.94384);
|
||||
}
|
||||
else
|
||||
{
|
||||
sliders.airspeed.setActive(false);
|
||||
this.#airspeedSlider.setActive(false);
|
||||
}
|
||||
|
||||
var targetAltitude = this.#getTargetAltitude(units);
|
||||
if (targetAltitude != null)
|
||||
{
|
||||
sliders.altitude.setActive(true);
|
||||
sliders.altitude.setValue(targetAltitude / 0.3048);
|
||||
this.#altitudeSlider.setActive(true);
|
||||
this.#altitudeSlider.setValue(targetAltitude / 0.3048);
|
||||
}
|
||||
else
|
||||
{
|
||||
sliders.altitude.setActive(false);
|
||||
this.#altitudeSlider.setActive(false);
|
||||
}
|
||||
}
|
||||
|
||||
#addUnitsButtons(units: Unit[], selectedUnitsContainer: HTMLElement)
|
||||
#addUnitsButtons(units: Unit[])
|
||||
{
|
||||
/* Remove any pre-existing unit button */
|
||||
var elements = selectedUnitsContainer.getElementsByClassName("js-unit-container");
|
||||
var elements = this.#selectedUnitsContainer.getElementsByClassName("js-unit-container");
|
||||
while (elements.length > 0)
|
||||
selectedUnitsContainer.removeChild(elements[0])
|
||||
this.#selectedUnitsContainer.removeChild(elements[0])
|
||||
|
||||
/* Create all the units buttons */
|
||||
for (let unit of units)
|
||||
{
|
||||
this.#addUnitButton(unit, selectedUnitsContainer);
|
||||
this.#addUnitButton(unit, this.#selectedUnitsContainer);
|
||||
if (unit.isLeader)
|
||||
for (let wingman of unit.getWingmen())
|
||||
this.#addUnitButton(wingman, selectedUnitsContainer);
|
||||
this.#addUnitButton(wingman, this.#selectedUnitsContainer);
|
||||
}
|
||||
}
|
||||
|
||||
@@ -163,7 +159,7 @@ export class UnitControlPanel {
|
||||
|
||||
/* Unit name (actually type, but DCS calls it name for some reason) */
|
||||
var nameDiv = document.createElement("div");
|
||||
nameDiv.classList.add("rounded-container-small");
|
||||
nameDiv.classList.add("ol-rounded-container-small");
|
||||
if (unit.name.length >= 7)
|
||||
nameDiv.innerHTML = `${unit.name.substring(0, 4)} ...`;
|
||||
else
|
||||
@@ -193,36 +189,27 @@ export class UnitControlPanel {
|
||||
if ((unit instanceof AirUnit))
|
||||
el.append(icon);
|
||||
|
||||
el.classList.add("rounded-container", "js-unit-container");
|
||||
el.classList.add("ol-rounded-container", "js-unit-container");
|
||||
|
||||
if (!unit.getSelected())
|
||||
el.classList.add("not-selected")
|
||||
|
||||
/* Set background color */
|
||||
if (unit.coalitionID == 1)
|
||||
{
|
||||
el.classList.add("red");
|
||||
icon.classList.add("red");
|
||||
}
|
||||
else if (unit.coalitionID == 2)
|
||||
{
|
||||
el.classList.add("blue");
|
||||
icon.classList.add("blue");
|
||||
}
|
||||
else
|
||||
{
|
||||
el.classList.add("neutral");
|
||||
icon.classList.add("neutral");
|
||||
}
|
||||
|
||||
el.classList.toggle("red", unit.coalitionID == 1);
|
||||
icon.classList.toggle("red", unit.coalitionID == 1);
|
||||
el.classList.toggle("blue", unit.coalitionID == 2);
|
||||
icon.classList.toggle("blue", unit.coalitionID == 2);
|
||||
el.classList.toggle("neutral", unit.coalitionID == 0);
|
||||
icon.classList.toggle("neutral", unit.coalitionID == 0);
|
||||
|
||||
el.addEventListener("click", () => getUnitsManager().selectUnit(unit.ID));
|
||||
container.appendChild(el);
|
||||
}
|
||||
|
||||
#showFormationButtons(units: Unit[], formationCreationContainer: HTMLElement)
|
||||
#showFormationButtons(units: Unit[])
|
||||
{
|
||||
var createButton = <HTMLElement>formationCreationContainer.querySelector("#create-formation");
|
||||
var undoButton = <HTMLElement>formationCreationContainer.querySelector("#undo-formation");
|
||||
var createButton = <HTMLElement>this.#formationCreationContainer.querySelector("#create-formation");
|
||||
var undoButton = <HTMLElement>this.#formationCreationContainer.querySelector("#undo-formation");
|
||||
if (createButton && undoButton && this.#checkAllUnitsAir(units))
|
||||
{
|
||||
if (!this.#checkUnitsAlreadyInFormation(units))
|
||||
|
||||
@@ -1,62 +1,75 @@
|
||||
import { ConvertDDToDMS, rad2deg } from "../other/utils";
|
||||
import { Unit } from "../units/unit";
|
||||
import { Panel } from "./panel";
|
||||
|
||||
export class UnitInfoPanel {
|
||||
#element: HTMLElement
|
||||
#display: string;
|
||||
export class UnitInfoPanel extends Panel {
|
||||
#unitName: HTMLElement;
|
||||
#groupName: HTMLElement;
|
||||
#name: HTMLElement;
|
||||
#heading: HTMLElement;
|
||||
#altitude: HTMLElement;
|
||||
#groundSpeed: HTMLElement;
|
||||
#fuel: HTMLElement;
|
||||
#latitude: HTMLElement;
|
||||
#longitude: HTMLElement;
|
||||
#task: HTMLElement;
|
||||
#loadoutContainer: HTMLElement;
|
||||
|
||||
constructor(ID: string) {
|
||||
this.#element = <HTMLElement>document.getElementById(ID);
|
||||
this.#display = '';
|
||||
if (this.#element != null) {
|
||||
this.#display = this.#element.style.display;
|
||||
this.hide();
|
||||
}
|
||||
}
|
||||
super(ID);
|
||||
|
||||
show() {
|
||||
this.#element.style.display = this.#display;
|
||||
}
|
||||
this.#unitName = <HTMLElement>(this.getElement().querySelector("#unit-name"));
|
||||
this.#groupName= <HTMLElement>(this.getElement().querySelector("#group-name"));
|
||||
this.#name = <HTMLElement>(this.getElement().querySelector("#name"));
|
||||
this.#heading = <HTMLElement>(this.getElement().querySelector("#heading"));
|
||||
this.#altitude = <HTMLElement>(this.getElement().querySelector("#altitude"));
|
||||
this.#groundSpeed = <HTMLElement>(this.getElement().querySelector("#ground-speed"));
|
||||
this.#fuel = <HTMLElement>(this.getElement().querySelector("#fuel"));
|
||||
this.#latitude = <HTMLElement>(this.getElement().querySelector("#latitude"));
|
||||
this.#longitude = <HTMLElement>(this.getElement().querySelector("#longitude"));
|
||||
this.#task = <HTMLElement>(this.getElement().querySelector("#task"));
|
||||
this.#loadoutContainer = <HTMLElement>(this.getElement().querySelector("#loadout-container"));
|
||||
|
||||
hide() {
|
||||
this.#element.style.display = "none";
|
||||
this.hide();
|
||||
}
|
||||
|
||||
|
||||
update(unit: Unit) {
|
||||
if (this.#element != null) {
|
||||
var els = this.#element.getElementsByClassName("js-loadout-element");
|
||||
while (els.length > 0)
|
||||
this.#element.querySelector("#loadout-container")?.removeChild(els[0]);
|
||||
|
||||
for (let index in unit.ammo) {
|
||||
var ammo = unit.ammo[index];
|
||||
var displayName = ammo.desc.displayName;
|
||||
var amount = ammo.count;
|
||||
var el = document.createElement("div")
|
||||
el.classList.add("js-loadout-element", "rectangular-container-dark")
|
||||
el.innerHTML = amount + "x" + displayName;
|
||||
this.#element.querySelector("#loadout-container")?.appendChild(el);
|
||||
}
|
||||
if (this.getElement() != null) {
|
||||
/* Set the unit info */
|
||||
this.#unitName.innerHTML = unit.unitName;
|
||||
this.#groupName.innerHTML = unit.groupName;
|
||||
this.#name.innerHTML = unit.name;
|
||||
this.#heading.innerHTML = String(Math.floor(rad2deg(unit.heading)) + " °");
|
||||
this.#altitude.innerHTML = String(Math.floor(unit.altitude / 0.3048) + " ft");
|
||||
this.#groundSpeed.innerHTML = String(Math.floor(unit.speed * 1.94384) + " kts");
|
||||
this.#fuel.innerHTML = String(unit.fuel + "%");
|
||||
this.#latitude.innerHTML = ConvertDDToDMS(unit.latitude, false);
|
||||
this.#longitude.innerHTML = ConvertDDToDMS(unit.longitude, true);
|
||||
this.#task.innerHTML = unit.currentTask !== ""? unit.currentTask: "No task";
|
||||
|
||||
this.#element.querySelector("#unit-name")!.innerHTML = unit.unitName;
|
||||
this.#element.querySelector("#group-name")!.innerHTML = unit.groupName;
|
||||
this.#element.querySelector("#name")!.innerHTML = unit.name;
|
||||
this.#element.querySelector("#heading")!.innerHTML = String(Math.floor(rad2deg(unit.heading)) + " °");
|
||||
this.#element.querySelector("#altitude")!.innerHTML = String(Math.floor(unit.altitude / 0.3048) + " ft");
|
||||
this.#element.querySelector("#ground-speed")!.innerHTML = String(Math.floor(unit.speed * 1.94384) + " kts");
|
||||
this.#element.querySelector("#fuel")!.innerHTML = String(unit.fuel + "%");
|
||||
this.#element.querySelector("#latitude")!.innerHTML = ConvertDDToDMS(unit.latitude, false);
|
||||
this.#element.querySelector("#longitude")!.innerHTML = ConvertDDToDMS(unit.longitude, true);
|
||||
this.#element.querySelector("#task")!.innerHTML = unit.currentTask !== ""? unit.currentTask: "Not controlled";
|
||||
|
||||
this.#element.querySelector("#task")!.classList.remove("red", "blue", "neutral");
|
||||
if (unit.coalitionID == 1)
|
||||
this.#element.querySelector("#task")!.classList.add("red");
|
||||
else if (unit.coalitionID == 2)
|
||||
this.#element.querySelector("#task")!.classList.add("blue");
|
||||
else
|
||||
this.#element.querySelector("#task")!.classList.add("neutral");
|
||||
/* Set the class of the task container */
|
||||
this.#task.classList.toggle("red", unit.coalitionID == 1);
|
||||
this.#task.classList.toggle("blue", unit.coalitionID == 2);
|
||||
this.#task.classList.toggle("neutral", unit.coalitionID == 0);
|
||||
|
||||
/* Add the loadout elements */
|
||||
var els = this.getElement().getElementsByClassName("js-loadout-element");
|
||||
while (els.length > 0)
|
||||
this.#loadoutContainer.removeChild(els[0]);
|
||||
|
||||
for (let index in unit.ammo)
|
||||
this.#addLoadoutElement(unit, index);
|
||||
}
|
||||
}
|
||||
|
||||
#addLoadoutElement(unit: Unit, index: string)
|
||||
{
|
||||
var ammo = unit.ammo[index];
|
||||
var displayName = ammo.desc.displayName;
|
||||
var amount = ammo.count;
|
||||
var el = document.createElement("div")
|
||||
el.classList.add("js-loadout-element", "ol-rectangular-container-dark")
|
||||
el.innerHTML = amount + "x" + displayName;
|
||||
this.#loadoutContainer.appendChild(el);
|
||||
}
|
||||
}
|
||||
@@ -33,7 +33,7 @@ export function getLoadoutNamesByRole(aircraft: string, role: string)
|
||||
|
||||
export function getLoadoutsByName(aircraft: string, loadoutName: string)
|
||||
{
|
||||
//@ts-ignore
|
||||
//@ts-ignore TODO
|
||||
for (let loadout of aircraftDatabase[aircraft]["loadouts"])
|
||||
{
|
||||
if (loadout["name"] === loadoutName)
|
||||
@@ -44,7 +44,21 @@ export function getLoadoutsByName(aircraft: string, loadoutName: string)
|
||||
return null;
|
||||
}
|
||||
|
||||
export function getUnitLabel(name: string)
|
||||
export function getAircraftNameByLabel(label: string)
|
||||
{
|
||||
for (let name in aircraftDatabase)
|
||||
{
|
||||
//@ts-ignore TODO
|
||||
if (aircraftDatabase[name]["label"] === label)
|
||||
{
|
||||
return name;
|
||||
}
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
|
||||
export function getAircraftLabelByName(name: string)
|
||||
{
|
||||
//@ts-ignore TODO
|
||||
return aircraftDatabase[name] === undefined? name: aircraftDatabase[name].label;
|
||||
@@ -1239,4 +1253,165 @@ export var aircraftDatabase = {
|
||||
}
|
||||
]
|
||||
},
|
||||
}
|
||||
}
|
||||
|
||||
export function getAircrafImage(name: string)
|
||||
{
|
||||
var results = []
|
||||
for (let imageName of imageNames) {
|
||||
var score = similarity(imageName, name);
|
||||
results.push({score: score, imageName: imageName});
|
||||
}
|
||||
|
||||
var bestResult = null;
|
||||
for (let result of results)
|
||||
{
|
||||
if (bestResult == null)
|
||||
bestResult = result;
|
||||
else {
|
||||
if (result.score > bestResult.score)
|
||||
bestResult = result;
|
||||
}
|
||||
}
|
||||
return bestResult?.imageName + ".png";
|
||||
}
|
||||
|
||||
function similarity(s1: string, s2: string) {
|
||||
var longer = s1;
|
||||
var shorter = s2;
|
||||
if (s1.length < s2.length) {
|
||||
longer = s2;
|
||||
shorter = s1;
|
||||
}
|
||||
var longerLength = longer.length;
|
||||
if (longerLength == 0) {
|
||||
return 1.0;
|
||||
}
|
||||
return (longerLength - editDistance(longer, shorter)) / longerLength;
|
||||
}
|
||||
|
||||
function editDistance(s1: string, s2: string) {
|
||||
s1 = s1.toLowerCase();
|
||||
s2 = s2.toLowerCase();
|
||||
|
||||
var costs = new Array();
|
||||
for (var i = 0; i <= s1.length; i++) {
|
||||
var lastValue = i;
|
||||
for (var j = 0; j <= s2.length; j++) {
|
||||
if (i == 0)
|
||||
costs[j] = j;
|
||||
else {
|
||||
if (j > 0) {
|
||||
var newValue = costs[j - 1];
|
||||
if (s1.charAt(i - 1) != s2.charAt(j - 1))
|
||||
newValue = Math.min(Math.min(newValue, lastValue),
|
||||
costs[j]) + 1;
|
||||
costs[j - 1] = lastValue;
|
||||
lastValue = newValue;
|
||||
}
|
||||
}
|
||||
}
|
||||
if (i > 0)
|
||||
costs[s2.length] = lastValue;
|
||||
}
|
||||
return costs[s2.length];
|
||||
}
|
||||
|
||||
var imageNames = [
|
||||
'a-10',
|
||||
'a-20',
|
||||
'a-29',
|
||||
'a-4',
|
||||
'a-400',
|
||||
'a-50',
|
||||
'a-6',
|
||||
'ah-1',
|
||||
'ah-64',
|
||||
'an-26',
|
||||
'av8bna',
|
||||
'b-1',
|
||||
'b-17',
|
||||
'b-2',
|
||||
'b-52',
|
||||
'b707',
|
||||
'bf109',
|
||||
'bomb',
|
||||
'c-101',
|
||||
'c-130',
|
||||
'c-17',
|
||||
'c-5',
|
||||
'ch-47',
|
||||
'ch-53',
|
||||
'christeneagleii',
|
||||
'e-2',
|
||||
'e-3',
|
||||
'eurofighter',
|
||||
'f-111',
|
||||
'f-117',
|
||||
'f-14',
|
||||
'f-15',
|
||||
'f-16',
|
||||
'f-18',
|
||||
'f-22',
|
||||
'f-35',
|
||||
'f-4',
|
||||
'f-5',
|
||||
'f-86',
|
||||
'fw190',
|
||||
'general1',
|
||||
'gripen',
|
||||
'h-6',
|
||||
'hawk',
|
||||
'helicopter1',
|
||||
'i-16',
|
||||
'il-76',
|
||||
'j-10',
|
||||
'j-20',
|
||||
'j-7',
|
||||
'jf-17',
|
||||
'ju-88',
|
||||
'ka-27',
|
||||
'ka-50',
|
||||
'kc-10',
|
||||
'kc-135',
|
||||
'l-159',
|
||||
'l-39',
|
||||
'm2000',
|
||||
'mi-24',
|
||||
'mi-26',
|
||||
'mi-28',
|
||||
'mi-8',
|
||||
'mig-15',
|
||||
'mig-19',
|
||||
'mig-21',
|
||||
'mig-23',
|
||||
'mig-25',
|
||||
'mig-29',
|
||||
'mosquito',
|
||||
'multiengine',
|
||||
'oh-58',
|
||||
'p-47',
|
||||
'p-51',
|
||||
'rafale',
|
||||
'rq-1',
|
||||
'rq-4',
|
||||
's-3',
|
||||
'sa-342',
|
||||
'spitfire',
|
||||
'su-17',
|
||||
'su-24',
|
||||
'su-25',
|
||||
'su-27',
|
||||
'su-34',
|
||||
'su-57',
|
||||
'tornado',
|
||||
'tu-160',
|
||||
'tu-22',
|
||||
'tu-95',
|
||||
'u-28',
|
||||
'uh-1',
|
||||
'uh-60',
|
||||
'viggen',
|
||||
'yak-40',
|
||||
'yak-52'
|
||||
]
|
||||
@@ -205,72 +205,3 @@ unitTypes.vehicles.Unarmed = [
|
||||
"ZIL-131 KUNG",
|
||||
"ZIL-4331"
|
||||
]
|
||||
|
||||
/* AIRPLANES */
|
||||
unitTypes.air = {}
|
||||
|
||||
unitTypes.air.CAP = [
|
||||
"F-4E",
|
||||
"F/A-18C",
|
||||
"MiG-29S",
|
||||
"F-14A",
|
||||
"Su-27",
|
||||
"MiG-23MLD",
|
||||
"Su-33",
|
||||
"MiG-25RBT",
|
||||
"Su-30",
|
||||
"MiG-31",
|
||||
"Mirage 2000-5",
|
||||
"F-15C",
|
||||
"F-5E",
|
||||
"F-16C bl.52d",
|
||||
]
|
||||
|
||||
unitTypes.air.CAS = [
|
||||
"Tornado IDS",
|
||||
"F-4E",
|
||||
"F/A-18C",
|
||||
"MiG-27K",
|
||||
"A-10C",
|
||||
"Su-25",
|
||||
"Su-34",
|
||||
"Su-17M4",
|
||||
"F-15E",
|
||||
]
|
||||
|
||||
unitTypes.air.strike = [
|
||||
"Tu-22M3",
|
||||
"B-52H",
|
||||
"F-111F",
|
||||
"Tu-95MS",
|
||||
"Su-24M",
|
||||
"Tu-160",
|
||||
"F-117A",
|
||||
"B-1B",
|
||||
"Tu-142",
|
||||
]
|
||||
|
||||
unitTypes.air.tanker = [
|
||||
"S-3B Tanker",
|
||||
"KC-135",
|
||||
"IL-78M",
|
||||
]
|
||||
|
||||
unitTypes.air.awacs = [
|
||||
"A-50",
|
||||
"E-3A",
|
||||
"E-2D",
|
||||
]
|
||||
|
||||
unitTypes.air.drone = [
|
||||
"MQ-1A Predator",
|
||||
"MQ-9 Reaper",
|
||||
]
|
||||
|
||||
unitTypes.air.transport = [
|
||||
"C-130",
|
||||
"An-26B",
|
||||
"An-30M",
|
||||
"C-17A",
|
||||
"IL-76MD",
|
||||
]
|
||||
@@ -1,6 +1,6 @@
|
||||
import * as L from 'leaflet'
|
||||
import { getMap } from '..'
|
||||
import { getUnitLabel } from './aircraftDatabase'
|
||||
import { getAircrafImage, getAircraftLabelByName } from './aircraftDatabase'
|
||||
import { AirUnit, GroundUnit, NavyUnit, Weapon } from './unit'
|
||||
|
||||
export interface MarkerOptions {
|
||||
@@ -30,7 +30,7 @@ export class UnitMarker extends L.Marker {
|
||||
constructor(options: MarkerOptions) {
|
||||
super(new L.LatLng(0, 0), { riseOnHover: true });
|
||||
this.#unitName = options.unitName;
|
||||
this.#name = getUnitLabel(options.name);
|
||||
this.#name = getAircraftLabelByName(options.name);
|
||||
this.#human = options.human;
|
||||
this.#AI = options.AI;
|
||||
|
||||
@@ -45,20 +45,21 @@ export class UnitMarker extends L.Marker {
|
||||
coalition = "neutral"
|
||||
|
||||
var icon = new L.DivIcon({
|
||||
html: `<table class="unit-marker-container" id="container">
|
||||
html: `<table class="ol-unit-marker-container" id="container">
|
||||
<tr>
|
||||
<td>
|
||||
<div class="${coalition}" id="background"></div>
|
||||
<div class="${coalition}" id="ring"></div>
|
||||
<div class="unit-marker-icon" id="icon"><img class="${coalition} unit-marker-image" src="${img}"></div>
|
||||
<div class="unit-marker-unitName" id="unitName">${this.#unitName}</div>
|
||||
<div class="unit-marker-altitude" id="altitude"></div>
|
||||
<div class="unit-marker-speed" id="speed"></div>
|
||||
<div class="unit-marker-name" id="name">${this.#name}</div>
|
||||
<div class="ol-unit-marker-icon" id="icon"><img class="${coalition} ol-unit-marker-image" src="${img}"></div>
|
||||
<div class="ol-unit-marker-unitName" id="unitName">${this.#unitName}</div>
|
||||
<div class="ol-unit-marker-altitude" id="altitude"></div>
|
||||
<div class="ol-unit-marker-speed" id="speed"></div>
|
||||
<div class="ol-unit-marker-name" id="name">${this.#name}</div>
|
||||
</td>
|
||||
</tr>
|
||||
</table>`,
|
||||
className: 'unit-marker'
|
||||
className: 'ol-unit-marker',
|
||||
iconAnchor: [30, 30]
|
||||
});
|
||||
this.setIcon(icon);
|
||||
}
|
||||
@@ -109,16 +110,16 @@ export class UnitMarker extends L.Marker {
|
||||
|
||||
if (!this.#alive)
|
||||
{
|
||||
this.getElement()?.querySelector("#icon")?.classList.add("unit-marker-dead");
|
||||
this.getElement()?.querySelector("#icon")?.classList.add("ol-unit-marker-dead");
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
setSelected(selected: boolean) {
|
||||
this.#selected = selected;
|
||||
this.getElement()?.querySelector("#icon")?.classList.remove("unit-marker-hovered");
|
||||
this.getElement()?.querySelector("#ring")?.classList.toggle("unit-marker-selected", selected);
|
||||
this.getElement()?.querySelector("#background")?.classList.toggle("unit-marker-selected", selected);
|
||||
this.getElement()?.querySelector("#icon")?.classList.remove("ol-unit-marker-hovered");
|
||||
this.getElement()?.querySelector("#ring")?.classList.toggle("ol-unit-marker-selected", selected);
|
||||
this.getElement()?.querySelector("#background")?.classList.toggle("ol-unit-marker-selected", selected);
|
||||
}
|
||||
|
||||
getSelected() {
|
||||
@@ -126,7 +127,11 @@ export class UnitMarker extends L.Marker {
|
||||
}
|
||||
|
||||
setHovered(hovered: boolean) {
|
||||
this.getElement()?.querySelector("#icon")?.classList.toggle("unit-marker-hovered", hovered && this.#alive);
|
||||
this.getElement()?.querySelector("#icon")?.classList.toggle("ol-unit-marker-hovered", hovered && this.#alive);
|
||||
}
|
||||
|
||||
getName() {
|
||||
return this.#name;
|
||||
}
|
||||
|
||||
getHuman() {
|
||||
@@ -166,19 +171,22 @@ export class AirUnitMarker extends UnitMarker {
|
||||
else
|
||||
return "minimal";
|
||||
}
|
||||
}
|
||||
|
||||
export class AircraftMarker extends AirUnitMarker {
|
||||
getUnitImage()
|
||||
{
|
||||
return new Image().src = "images/units/" + getAircrafImage(this.getName());
|
||||
}
|
||||
}
|
||||
|
||||
export class HelicopterMarker extends AirUnitMarker {
|
||||
getUnitImage()
|
||||
{
|
||||
return new Image().src = "images/units/airUnit.png"
|
||||
}
|
||||
}
|
||||
|
||||
export class AircraftMarker extends AirUnitMarker {
|
||||
}
|
||||
|
||||
export class HelicopterMarker extends AirUnitMarker {
|
||||
}
|
||||
|
||||
export class GroundUnitMarker extends UnitMarker {
|
||||
/* Are user driven units recognized as human? */
|
||||
getVisibility() {
|
||||
|
||||
@@ -20,6 +20,7 @@
|
||||
<%- include('visibilitycontrolpanel.ejs') %>
|
||||
<%- include('connectionstatuspanel.ejs') %>
|
||||
<%- include('mouseinfopanel.ejs') %>
|
||||
<%- include('logpanel.ejs') %>
|
||||
<script src="javascripts/bundle.js"></script>
|
||||
</body>
|
||||
|
||||
|
||||
3
client/views/logpanel.ejs
Normal file
3
client/views/logpanel.ejs
Normal file
@@ -0,0 +1,3 @@
|
||||
<div class="ol-panel ol-panel-transparent" id="log-panel">
|
||||
<!-- Log entries go here -->
|
||||
</div>
|
||||
@@ -1,6 +1,6 @@
|
||||
<div class="ol-panel" id="mouse-info-panel">
|
||||
<div id="measure-position-container" class="rectangular-container"><img src="images/pin.png"><div id="measure-position">---° / --- NM</div></div>
|
||||
<div id="unit-position-container" class="rectangular-container"><img src="images/unit.png"><div id="unit-position">---° / --- NM</div></div>
|
||||
<div class="rectangular-container"><img src="images/BEBlue.png"><div id="bullseye-2">---° / --- NM</div></div>
|
||||
<div class="rectangular-container"><img src="images/BERed.png"><div id="bullseye-1">---° / --- NM</div></div>
|
||||
<div id="measure-position-container" class="ol-rectangular-container"><img src="images/pin.png"><div id="measure-position">---° / --- NM</div></div>
|
||||
<div id="unit-position-container" class="ol-rectangular-container"><img src="images/unit.png"><div id="unit-position">---° / --- NM</div></div>
|
||||
<div class="ol-rectangular-container"><img src="images/BEBlue.png"><div id="bullseye-2">---° / --- NM</div></div>
|
||||
<div class="ol-rectangular-container"><img src="images/BERed.png"><div id="bullseye-1">---° / --- NM</div></div>
|
||||
</div>
|
||||
@@ -1,24 +1,21 @@
|
||||
<div class="ol-panel" id="unit-control-panel">
|
||||
<div class="ol-panel" id="unit-control-buttons">
|
||||
<div class="ol-button" id="slow-button"></div>
|
||||
<div class="ol-button" id="fast-button"></div>
|
||||
<div class="ol-button" id="descend-button"></div>
|
||||
<div class="ol-button" id="climb-button"></div>
|
||||
</div>
|
||||
|
||||
<div id="title-label">Selected units</div>
|
||||
<!--
|
||||
<div id="ol-title-label">Selected units</div>
|
||||
|
||||
<div id="selected-units-container" class="ol-scrollable">
|
||||
<!-- This is where all the unit selection buttons will be shown-->
|
||||
<!--
|
||||
</div>
|
||||
|
||||
|
||||
<div id="formation-creation-container">
|
||||
<div class="rectangular-button white" id="create-formation"><img src="images\buttons\create.svg">Create formation</div>
|
||||
<div class="rectangular-button white" id="undo-formation"><img src="images\buttons\erase.svg">Undo formation</div>
|
||||
<div class="ol-rectangular-button white" id="create-formation"><img src="images\buttons\create.svg">Create formation</div>
|
||||
<div class="ol-rectangular-button white" id="undo-formation"><img src="images\buttons\erase.svg">Undo formation</div>
|
||||
</div>
|
||||
<div class="hl"></div>
|
||||
<div class="ol-hl"></div>
|
||||
-->
|
||||
|
||||
<div id="section-label">Controls</div>
|
||||
<div class="ol-title-label">Controls</div>
|
||||
<div id="flight-controls-buttons-container">
|
||||
<div class="slider-container flight-control-slider" id="altitude-slider">
|
||||
<div class="flight-control-title">Altitude</div>
|
||||
@@ -32,34 +29,36 @@
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<!--
|
||||
<div id="section-label">Formation</div>
|
||||
<div id="formation-buttons-container">
|
||||
<div class="rectangular-button">Echelon</div>
|
||||
<div class="rectangular-button">Fingertip</div>
|
||||
<div class="rectangular-button">Trail</div>
|
||||
<div class="rectangular-button">Line abreast</div>
|
||||
<div class="ol-rectangular-button">Echelon</div>
|
||||
<div class="ol-rectangular-button">Fingertip</div>
|
||||
<div class="ol-rectangular-button">Trail</div>
|
||||
<div class="ol-rectangular-button">Line abreast</div>
|
||||
</div>
|
||||
-->
|
||||
|
||||
<div class="hl"></div>
|
||||
<div class="ol-hl"></div>
|
||||
|
||||
<div id="section-label">Rules of engagement</div>
|
||||
<div class="ol-title-label">Rules of engagement</div>
|
||||
<div id="roe-buttons-container">
|
||||
<div class="rectangular-button" id="free">Free</div>
|
||||
<div class="rectangular-button" id="designated-free">Designated free</div>
|
||||
<div class="rectangular-button" id="designated">Designated</div>
|
||||
<div class="rectangular-button" id="return">Return</div>
|
||||
<div class="rectangular-button" id="hold">Hold</div>
|
||||
<div class="ol-rectangular-button" id="free">Free</div>
|
||||
<div class="ol-rectangular-button" id="designated-free">Designated free</div>
|
||||
<div class="ol-rectangular-button" id="designated">Designated</div>
|
||||
<div class="ol-rectangular-button" id="return">Return</div>
|
||||
<div class="ol-rectangular-button" id="hold">Hold</div>
|
||||
</div>
|
||||
|
||||
<div class="hl"></div>
|
||||
<div class="ol-hl"></div>
|
||||
|
||||
<div id="section-label">Reaction to threat</div>
|
||||
<div class="ol-title-label">Reaction to threat</div>
|
||||
<div id="reaction-to-threat-buttons-container">
|
||||
<div class="rectangular-button" id="none">None</div>
|
||||
<div class="rectangular-button" id="passive">Passive</div>
|
||||
<div class="rectangular-button" id="evade">Evade</div>
|
||||
<div class="rectangular-button" id="escape">Escape</div>
|
||||
<div class="rectangular-button" id="abort">Abort</div>
|
||||
<div class="ol-rectangular-button" id="none">None</div>
|
||||
<div class="ol-rectangular-button" id="passive">Passive</div>
|
||||
<div class="ol-rectangular-button" id="evade">Evade</div>
|
||||
<div class="ol-rectangular-button" id="escape">Escape</div>
|
||||
<div class="ol-rectangular-button" id="abort">Abort</div>
|
||||
</div>
|
||||
|
||||
</div>
|
||||
@@ -1,11 +1,11 @@
|
||||
<div class="ol-panel padding-large" id="unit-info-panel">
|
||||
<div id="general">
|
||||
<div id="unit-name"></div>
|
||||
<div class="rectangular-container" id="name"></div>
|
||||
<div class="rectangular-container" id="group-name"></div>
|
||||
<div class="rounded-container" id="task"></div>
|
||||
<div class="ol-rectangular-container" id="name"></div>
|
||||
<div class="ol-rectangular-container" id="group-name"></div>
|
||||
<div class="ol-rounded-container" id="task"></div>
|
||||
</div>
|
||||
<div class="vl h-margin-largest"></div>
|
||||
<div class="ol-vl h-margin-largest"></div>
|
||||
<div id="flight-data">
|
||||
<div id="flight-data-label">Flight data</div>
|
||||
<div id="latitude"></div>
|
||||
@@ -20,7 +20,7 @@
|
||||
<div class="flight-data-label">Heading</div>
|
||||
<div class="flight-data-value" id="heading"></div>
|
||||
</div>
|
||||
<div class="vl h-margin-largest"></div>
|
||||
<div class="ol-vl h-margin-largest"></div>
|
||||
<div id="loadout-data">
|
||||
<div id="loadout-label">Loadout</div>
|
||||
<img class="flight-data-icon" src="images/icons/fuel.svg">
|
||||
|
||||
@@ -19,7 +19,7 @@
|
||||
<input type="checkbox" id="weapon-visibility" checked>
|
||||
</div>
|
||||
|
||||
<div class="vl"></div>
|
||||
<div class="ol-vl"></div>
|
||||
|
||||
<div class="label">Full: </div>
|
||||
<div>
|
||||
@@ -36,7 +36,7 @@
|
||||
<input type="radio" id="minimal-visibility" name="labels" value="minimal">
|
||||
</div>
|
||||
|
||||
<div class="vl"></div>
|
||||
<div class="ol-vl"></div>
|
||||
<div class="label">Olympus only: </div>
|
||||
<div>
|
||||
<input type="checkbox" id="uncontrolled-visibility">
|
||||
|
||||
Reference in New Issue
Block a user