Renamed files

This commit is contained in:
dpassoni
2023-03-16 15:34:35 +01:00
parent 64df9b142d
commit 53911cf314
51 changed files with 2483 additions and 60 deletions

View File

@@ -1,6 +1,6 @@
import { AICFormationContextDataInterface, AICFormationDescriptor } from "./AICFormationDescriptor";
import { AICFormationDescriptorPhrase } from "./AICFormationDescriptorPhrase";
import { AICFormationDescriptorSection } from "./AICFormationDescriptorSection";
import { AICFormationContextDataInterface, AICFormationDescriptor } from "./aicformationdescriptor";
import { AICFormationDescriptorPhrase } from "./aicformationdescriptorphrase";
import { AICFormationDescriptorSection } from "./aicformationdescriptorsection";
export interface AICFormationInterface {
"icon" : string,

View File

@@ -1,8 +1,8 @@
import { AICFormation, AICFormationInterface } from "../AICFormation";
import { AICFormationContextDataInterface } from "../AICFormationDescriptor";
import { AICFormationDescriptorSection } from "../AICFormationDescriptorSection";
import { AICFormationDescriptorComponent } from "../AICFormationDescriptorComponent";
import { AICFormationDescriptorPhrase } from "../AICFormationDescriptorPhrase";
import { AICFormation, AICFormationInterface } from "../aicformation";
import { AICFormationContextDataInterface } from "../aicformationdescriptor";
import { AICFormationDescriptorSection } from "../aicformationdescriptorsection";
import { AICFormationDescriptorComponent } from "../aicformationdescriptorcomponent";
import { AICFormationDescriptorPhrase } from "../aicformationdescriptorphrase";
export class AICFormation_Azimuth extends AICFormation implements AICFormationInterface {

View File

@@ -1,8 +1,8 @@
import { AICFormation, AICFormationInterface } from "../AICFormation";
import { AICFormationContextDataInterface } from "../AICFormationDescriptor";
import { AICFormationDescriptorSection } from "../AICFormationDescriptorSection";
import { AICFormationDescriptorComponent } from "../AICFormationDescriptorComponent";
import { AICFormationDescriptorPhrase } from "../AICFormationDescriptorPhrase";
import { AICFormation, AICFormationInterface } from "../aicformation";
import { AICFormationContextDataInterface } from "../aicformationdescriptor";
import { AICFormationDescriptorSection } from "../aicformationdescriptorsection";
import { AICFormationDescriptorComponent } from "../aicformationdescriptorcomponent";
import { AICFormationDescriptorPhrase } from "../aicformationdescriptorphrase";
export class AICFormation_Range extends AICFormation implements AICFormationInterface {

View File

@@ -1,5 +1,5 @@
import { AICFormation, AICFormationInterface } from "../AICFormation";
import { AICFormationContextDataInterface, AICFormationDescriptor } from "../AICFormationDescriptor";
import { AICFormation, AICFormationInterface } from "../aicformation";
import { AICFormationContextDataInterface, AICFormationDescriptor } from "../aicformationdescriptor";
export class AICFormation_Single extends AICFormation implements AICFormationInterface {

View File

@@ -1,9 +1,9 @@
import { AICFormation } from "./AICFormation";
import { AICFormationDescriptorSection } from "./AICFormationDescriptorSection";
import { AICFormationDescriptorSection_Formation } from "./AICFormationDescriptorSection/Formation";
import { AICFormationDescriptorSection_Unit } from "./AICFormationDescriptorSection/Unit";
import { AICFormationDescriptorSection_NumGroups } from "./AICFormationDescriptorSection/NumGroups";
import { AICFormationDescriptorSection_Who } from "./AICFormationDescriptorSection/Who";
import { AICFormation } from "./aicformation";
import { AICFormationDescriptorSection } from "./aicformationdescriptorsection";
import { AICFormationDescriptorSection_Formation } from "./aicformationdescriptorsection/formation";
import { AICFormationDescriptorSection_Unit } from "./aicformationdescriptorsection/unit";
import { AICFormationDescriptorSection_NumGroups } from "./aicformationdescriptorsection/numgroups";
import { AICFormationDescriptorSection_Who } from "./aicformationdescriptorsection/who";
export interface AICFormationContextDataInterface {

View File

@@ -1,4 +1,4 @@
import { AICFormationDescriptorComponent } from "../AICFormationDescriptorComponent";
import { AICFormationDescriptorComponent } from "../aicformationdescriptorcomponent";
export abstract class AICFormactionDescriptorComponent_Distance extends AICFormationDescriptorComponent {

View File

@@ -1,4 +1,4 @@
import { AICFormactionDescriptorComponent_Distance } from "../Distance";
import { AICFormactionDescriptorComponent_Distance } from "../distance";
export class AICFormationDescriptorComponent_Distance_Range extends AICFormactionDescriptorComponent_Distance {

View File

@@ -1,6 +1,6 @@
import { AICFormation } from "./AICFormation";
import { AICFormationContextDataInterface } from "./AICFormationDescriptor";
import { AICFormationDescriptorComponent } from "./AICFormationDescriptorComponent";
import { AICFormation } from "./aicformation";
import { AICFormationContextDataInterface } from "./aicformationdescriptor";
import { AICFormationDescriptorComponent } from "./aicformationdescriptorcomponent";
export interface AICFormationDescriptorPhraseInterface {
"generate" : CallableFunction,

View File

@@ -1,6 +1,6 @@
import { AICFormation } from "./AICFormation";
import { AICFormationContextDataInterface } from "./AICFormationDescriptor";
import { AICFormationDescriptorPhrase } from "./AICFormationDescriptorPhrase";
import { AICFormation } from "./aicformation";
import { AICFormationContextDataInterface } from "./aicformationdescriptor";
import { AICFormationDescriptorPhrase } from "./aicformationdescriptorphrase";
export interface AICFormationDescriptorSectionInterface {
"generate" : CallableFunction,

View File

@@ -1,8 +1,8 @@
import { AICFormation } from "../AICFormation";
import { AICFormationContextDataInterface } from "../AICFormationDescriptor";
import { AICFormationDescriptorSection } from "../AICFormationDescriptorSection";
import { AICFormationDescriptorComponent } from "../AICFormationDescriptorComponent";
import { AICFormationDescriptorPhrase } from "../AICFormationDescriptorPhrase";
import { AICFormation } from "../aicformation";
import { AICFormationContextDataInterface } from "../aicformationdescriptor";
import { AICFormationDescriptorSection } from "../aicformationdescriptorsection";
import { AICFormationDescriptorComponent } from "../aicformationdescriptorcomponent";
import { AICFormationDescriptorPhrase } from "../aicformationdescriptorphrase";
export class AICFormationDescriptorSection_Formation extends AICFormationDescriptorSection {

View File

@@ -1,8 +1,8 @@
import { AICFormation } from "../AICFormation";
import { AICFormationContextDataInterface } from "../AICFormationDescriptor";
import { AICFormationDescriptorSection } from "../AICFormationDescriptorSection";
import { AICFormationDescriptorComponent } from "../AICFormationDescriptorComponent";
import { AICFormationDescriptorPhrase } from "../AICFormationDescriptorPhrase";
import { AICFormation } from "../aicformation";
import { AICFormationContextDataInterface } from "../aicformationdescriptor";
import { AICFormationDescriptorSection } from "../aicformationdescriptorsection";
import { AICFormationDescriptorComponent } from "../aicformationdescriptorcomponent";
import { AICFormationDescriptorPhrase } from "../aicformationdescriptorphrase";
export class AICFormationDescriptorSection_NumGroups extends AICFormationDescriptorSection {

View File

@@ -1,8 +1,8 @@
import { AICFormation } from "../AICFormation";
import { AICFormationContextDataInterface } from "../AICFormationDescriptor";
import { AICFormationDescriptorSection } from "../AICFormationDescriptorSection";
import { AICFormationDescriptorComponent } from "../AICFormationDescriptorComponent";
import { AICFormationDescriptorPhrase } from "../AICFormationDescriptorPhrase";
import { AICFormation } from "../aicformation";
import { AICFormationContextDataInterface } from "../aicformationdescriptor";
import { AICFormationDescriptorSection } from "../aicformationdescriptorsection";
import { AICFormationDescriptorComponent } from "../aicformationdescriptorcomponent";
import { AICFormationDescriptorPhrase } from "../aicformationdescriptorphrase";
interface addUnitInformationInterface {
omitTrack?: boolean

View File

@@ -1,8 +1,8 @@
import { AICFormation } from "../AICFormation";
import { AICFormationContextDataInterface } from "../AICFormationDescriptor";
import { AICFormationDescriptorSection } from "../AICFormationDescriptorSection";
import { AICFormationDescriptorComponent } from "../AICFormationDescriptorComponent";
import { AICFormationDescriptorPhrase } from "../AICFormationDescriptorPhrase";
import { AICFormation } from "../aicformation";
import { AICFormationContextDataInterface } from "../aicformationdescriptor";
import { AICFormationDescriptorSection } from "../aicformationdescriptorsection";
import { AICFormationDescriptorComponent } from "../aicformationdescriptorcomponent";
import { AICFormationDescriptorPhrase } from "../aicformationdescriptorphrase";
export class AICFormationDescriptorSection_Who extends AICFormationDescriptorSection {

View File

@@ -1,8 +1,8 @@
import { ToggleableFeature } from "../ToggleableFeature";
import { AICFormation_Azimuth } from "./AICFormation/Azimuth";
import { AICFormation_Range } from "./AICFormation/Range";
import { AICFormation_Single } from "./AICFormation/Single";
import { AICFormationDescriptorSection } from "./AICFormationDescriptorSection";
import { ToggleableFeature } from "../toggleablefeature";
import { AICFormation_Azimuth } from "./aicformation/azimuth";
import { AICFormation_Range } from "./aicformation/range";
import { AICFormation_Single } from "./aicformation/single";
import { AICFormationDescriptorSection } from "./aicformationdescriptorsection";
export class AIC extends ToggleableFeature {

View File

@@ -0,0 +1,54 @@
import { AICFormationContextDataInterface, AICFormationDescriptor } from "./aicformationdescriptor";
import { AICFormationDescriptorPhrase } from "./aicformationdescriptorphrase";
import { AICFormationDescriptorSection } from "./aicformationdescriptorsection";
export interface AICFormationInterface {
"icon" : string,
"label" : string,
"name" : string,
"numGroups" : number,
"summary" : string,
"unitBreakdown" : string[]
}
export abstract class AICFormation {
"icon" = "";
"label" = "";
"name" = "";
"numGroups" = 1;
"summary" = "";
"unitBreakdown":string[] = []
constructor() {
this.unitBreakdown = [];
}
addToDescriptorPhrase( section: AICFormationDescriptorSection, phrase: AICFormationDescriptorPhrase, contextData: AICFormationContextDataInterface ) {
return phrase;
}
getDescriptor( contextData: AICFormationContextDataInterface ) {
return new AICFormationDescriptor().generate( this, contextData );
}
hasUnitBreakdown() {
return this.unitBreakdown.length > 0;
}
showFormationNameInDescriptor() {
return true;
}
}

View File

@@ -0,0 +1,38 @@
import { AICFormation, AICFormationInterface } from "../aicformation";
import { AICFormationContextDataInterface } from "../aicformationdescriptor";
import { AICFormationDescriptorSection } from "../aicformationdescriptorsection";
import { AICFormationDescriptorComponent } from "../aicformationdescriptorcomponent";
import { AICFormationDescriptorPhrase } from "../aicformationdescriptorphrase";
export class AICFormation_Azimuth extends AICFormation implements AICFormationInterface {
"icon" = "azimuth.png";
"label" = "Azimuth";
"name" = "azimuth";
"numGroups" = 2;
"summary" = "Two contacts, side-by-side in a line perpedicular to the perspective.";
"unitBreakdown" = [ "<compass> group", "<compass> group" ];
constructor() {
super();
}
addToDescriptorPhrase( section: AICFormationDescriptorSection, phrase: AICFormationDescriptorPhrase, contextData: AICFormationContextDataInterface ) {
switch ( section.name ) {
case "formation":
phrase.addComponent( new AICFormationDescriptorComponent( "<distance>" ) );
phrase.addComponent( new AICFormationDescriptorComponent( "track <compass>" ) );
}
return phrase;
}
}

View File

@@ -0,0 +1,38 @@
import { AICFormation, AICFormationInterface } from "../aicformation";
import { AICFormationContextDataInterface } from "../aicformationdescriptor";
import { AICFormationDescriptorSection } from "../aicformationdescriptorsection";
import { AICFormationDescriptorComponent } from "../aicformationdescriptorcomponent";
import { AICFormationDescriptorPhrase } from "../aicformationdescriptorphrase";
export class AICFormation_Range extends AICFormation implements AICFormationInterface {
"icon" = "range.png";
"label" = "Range";
"name" = "range";
"numGroups" = 2;
"summary" = "Two contacts, one behind the other";
"unitBreakdown" = [ "Lead group", "Trail group" ];
constructor() {
super();
}
addToDescriptorPhrase( section: AICFormationDescriptorSection, phrase: AICFormationDescriptorPhrase, contextData: AICFormationContextDataInterface ) {
switch ( section.name ) {
case "formation":
phrase.addComponent( new AICFormationDescriptorComponent( "<distance>" ) );
phrase.addComponent( new AICFormationDescriptorComponent( "track <compass>" ) );
}
return phrase;
}
}

View File

@@ -0,0 +1,24 @@
import { AICFormation, AICFormationInterface } from "../aicformation";
import { AICFormationContextDataInterface, AICFormationDescriptor } from "../aicformationdescriptor";
export class AICFormation_Single extends AICFormation implements AICFormationInterface {
"icon" = "single.png";
"label" = "Single";
"name" = "single";
"numGroups" = 1;
"summary" = "One contact on its own";
"unitBreakdown" = [];
constructor() {
super();
}
showFormationNameInDescriptor() {
return false;
}
}

View File

@@ -0,0 +1,55 @@
import { AICFormation } from "./aicformation";
import { AICFormationDescriptorSection } from "./aicformationdescriptorsection";
import { AICFormationDescriptorSection_Formation } from "./aicformationdescriptorsection/formation";
import { AICFormationDescriptorSection_Unit } from "./aicformationdescriptorsection/unit";
import { AICFormationDescriptorSection_NumGroups } from "./aicformationdescriptorsection/numgroups";
import { AICFormationDescriptorSection_Who } from "./aicformationdescriptorsection/who";
export interface AICFormationContextDataInterface {
"aicCallsign" : string,
"bullseyeName" : string,
"control" : "broadcast" | "tactical",
"numGroups" : number
}
export class AICFormationDescriptor {
#sections:AICFormationDescriptorSection[] = [
new AICFormationDescriptorSection_Who(),
new AICFormationDescriptorSection_NumGroups(),
new AICFormationDescriptorSection_Formation(),
new AICFormationDescriptorSection_Unit()
]
constructor() {
}
addSection( section:AICFormationDescriptorSection ) {
this.#sections.push( section );
}
getSections() {
return this.#sections;
}
generate( formation:AICFormation, contextData: AICFormationContextDataInterface ) {
let output:object[] = [];
for ( const section of this.#sections ) {
output.push(
section.generate( formation, contextData )
);
}
return output;
}
}

View File

@@ -0,0 +1,18 @@
interface ComponentInterface {
"label" : string;
"value" : string;
}
export class AICFormationDescriptorComponent implements ComponentInterface {
label = "(not set)";
value = "(not set)";
constructor( value:any, label?:string ) {
this.label = label || "(not set)";
this.value = value;
}
}

View File

@@ -0,0 +1,9 @@
import { AICFormationDescriptorComponent } from "../aicformationdescriptorcomponent";
export abstract class AICFormactionDescriptorComponent_Distance extends AICFormationDescriptorComponent {
constructor( value:string, label?:string ) {
super( value, label );
}
}

View File

@@ -0,0 +1,9 @@
import { AICFormactionDescriptorComponent_Distance } from "../distance";
export class AICFormationDescriptorComponent_Distance_Range extends AICFormactionDescriptorComponent_Distance {
constructor( value:string, label?:string ) {
super( value, label );
}
}

View File

@@ -0,0 +1,40 @@
import { AICFormation } from "./aicformation";
import { AICFormationContextDataInterface } from "./aicformationdescriptor";
import { AICFormationDescriptorComponent } from "./aicformationdescriptorcomponent";
export interface AICFormationDescriptorPhraseInterface {
"generate" : CallableFunction,
"label" : string,
"name" : string
}
export class AICFormationDescriptorPhrase {
#components : AICFormationDescriptorComponent[] = [];
label = "";
name = "";
constructor() {
}
addComponent( component:AICFormationDescriptorComponent ) {
this.#components.push( component );
return this;
}
getComponents() {
return this.#components;
}
generate( formation:AICFormation, contextData: AICFormationContextDataInterface ) {
return this;
}
}

View File

@@ -0,0 +1,40 @@
import { AICFormation } from "./aicformation";
import { AICFormationContextDataInterface } from "./aicformationdescriptor";
import { AICFormationDescriptorPhrase } from "./aicformationdescriptorphrase";
export interface AICFormationDescriptorSectionInterface {
"generate" : CallableFunction,
"label" : string,
"name" : string,
"omitSection" : boolean
}
export abstract class AICFormationDescriptorSection {
#phrases : AICFormationDescriptorPhrase[] = [];
label = "";
name = "";
omitSection = false;
constructor() {
}
addPhrase( phrase:AICFormationDescriptorPhrase ) {
this.#phrases.push( phrase );
}
generate( formation:AICFormation, contextData: AICFormationContextDataInterface ) {
return this;
}
getPhrases() {
return this.#phrases;
}
}

View File

@@ -0,0 +1,39 @@
import { AICFormation } from "../aicformation";
import { AICFormationContextDataInterface } from "../aicformationdescriptor";
import { AICFormationDescriptorSection } from "../aicformationdescriptorsection";
import { AICFormationDescriptorComponent } from "../aicformationdescriptorcomponent";
import { AICFormationDescriptorPhrase } from "../aicformationdescriptorphrase";
export class AICFormationDescriptorSection_Formation extends AICFormationDescriptorSection {
label = "Formation";
name = "formation";
constructor() {
super();
}
generate( formation:AICFormation, contextData: AICFormationContextDataInterface ) {
if ( !formation.showFormationNameInDescriptor() ) {
this.omitSection = true;
return this;
}
let phrase = new AICFormationDescriptorPhrase();
phrase.addComponent( new AICFormationDescriptorComponent( formation.label, "Formation" ) );
phrase = formation.addToDescriptorPhrase( this, phrase, contextData );
this.addPhrase( phrase );
return this;
}
}

View File

@@ -0,0 +1,35 @@
import { AICFormation } from "../aicformation";
import { AICFormationContextDataInterface } from "../aicformationdescriptor";
import { AICFormationDescriptorSection } from "../aicformationdescriptorsection";
import { AICFormationDescriptorComponent } from "../aicformationdescriptorcomponent";
import { AICFormationDescriptorPhrase } from "../aicformationdescriptorphrase";
export class AICFormationDescriptorSection_NumGroups extends AICFormationDescriptorSection {
label = "Groups";
name = "numgroups";
constructor() {
super();
}
generate( formation:AICFormation, contextData: AICFormationContextDataInterface ) {
let value = "Single group";
if ( contextData.numGroups > 1 ) {
value = contextData.numGroups + " groups";
}
let phrase = new AICFormationDescriptorPhrase();
phrase.addComponent( new AICFormationDescriptorComponent( value, "Number of groups" ) );
this.addPhrase( phrase );
return this;
}
}

View File

@@ -0,0 +1,83 @@
import { AICFormation } from "../aicformation";
import { AICFormationContextDataInterface } from "../aicformationdescriptor";
import { AICFormationDescriptorSection } from "../aicformationdescriptorsection";
import { AICFormationDescriptorComponent } from "../aicformationdescriptorcomponent";
import { AICFormationDescriptorPhrase } from "../aicformationdescriptorphrase";
interface addUnitInformationInterface {
omitTrack?: boolean
}
export class AICFormationDescriptorSection_Unit extends AICFormationDescriptorSection {
label = "Unit";
name = "unit";
constructor() {
super();
}
addUnitInformation( formation:AICFormation, contextData: AICFormationContextDataInterface, phrase: AICFormationDescriptorPhrase, options?:addUnitInformationInterface ) {
options = options || {};
const originPoint = ( contextData.control === "broadcast" ) ? contextData.bullseyeName : "BRAA";
phrase.addComponent( new AICFormationDescriptorComponent( originPoint, "Bearing origin point" ) );
phrase.addComponent( new AICFormationDescriptorComponent( "<bearing>", "Bearing" ) );
phrase.addComponent( new AICFormationDescriptorComponent( "<range>", "Range" ) );
phrase.addComponent( new AICFormationDescriptorComponent( "<altitude>", "Altitude" ) );
if ( contextData.control === "broadcast" ) {
if ( !options.hasOwnProperty( "omitTrack" ) || options.omitTrack !== true ) {
phrase.addComponent( new AICFormationDescriptorComponent( "track <compass>", "Tracking" ) );
}
} else {
phrase.addComponent( new AICFormationDescriptorComponent( "[hot|flanking [left|right]|beam <compass>|cold]", "Azimuth" ) );
}
return phrase;
}
generate( formation:AICFormation, contextData: AICFormationContextDataInterface ) {
if ( formation.hasUnitBreakdown() ) {
for ( const [ i, unitRef ] of formation.unitBreakdown.entries() ) {
let phrase = new AICFormationDescriptorPhrase();
phrase.addComponent( new AICFormationDescriptorComponent( unitRef, "Unit reference" ) );
if ( i === 0 ) {
this.addUnitInformation( formation, contextData, phrase, { "omitTrack": true } );
} else {
phrase.addComponent( new AICFormationDescriptorComponent( "<altitude>" ) );
}
phrase.addComponent( new AICFormationDescriptorComponent( "hostile" ) );
this.addPhrase( phrase );
}
} else {
this.addPhrase(
this.addUnitInformation( formation, contextData, new AICFormationDescriptorPhrase() )
);
}
return this;
}
}

View File

@@ -0,0 +1,35 @@
import { AICFormation } from "../aicformation";
import { AICFormationContextDataInterface } from "../aicformationdescriptor";
import { AICFormationDescriptorSection } from "../aicformationdescriptorsection";
import { AICFormationDescriptorComponent } from "../aicformationdescriptorcomponent";
import { AICFormationDescriptorPhrase } from "../aicformationdescriptorphrase";
export class AICFormationDescriptorSection_Who extends AICFormationDescriptorSection {
label = "Who";
name = "who";
constructor() {
super();
}
generate( formation:AICFormation, contextData: AICFormationContextDataInterface ) {
let phrase = new AICFormationDescriptorPhrase();
if ( contextData.control === "tactical" ) {
phrase.addComponent( new AICFormationDescriptorComponent( "<their callsign>", "Their callsign" ) );
}
phrase.addComponent( new AICFormationDescriptorComponent( contextData.aicCallsign, "Your callsign" ) );
this.addPhrase( phrase );
return this;
}
}

View File

@@ -1,6 +1,6 @@
import { ToggleableFeature } from "../ToggleableFeature";
import { ToggleableFeature } from "../toggleablefeature";
import Sortable from 'sortablejs';
import { ATCFLightList } from "./FlightList";
import { ATCFLightList } from "./flightlist";
export class ATC extends ToggleableFeature {

View File

@@ -1,4 +1,4 @@
import { ATCMockAPI } from "../ATCMockAPI";
import { ATCMockAPI } from "../atcmockapi";
export class ATCMockAPI_Flights extends ATCMockAPI {

View File

@@ -1,4 +1,4 @@
import { ATCMockAPI_Flights } from "./ATCMockAPI/Flights";
import { ATCMockAPI_Flights } from "./atcmockapi/flights";
export class ATCFLightList {

87
client/src/atc/atc.ts Normal file
View File

@@ -0,0 +1,87 @@
import { ToggleableFeature } from "../toggleablefeature";
import Sortable from 'sortablejs';
import { ATCFLightList } from "./flightlist";
export class ATC extends ToggleableFeature {
constructor() {
super( true );
//this.#generateFlightList();
let $list = document.getElementById( "atc-strip-board-arrivals" );
if ( $list instanceof HTMLElement ) {
Sortable.create( $list, {
"handle": ".handle"
});
}
}
#generateFlightList() {
const flightList = new ATCFLightList();
const flights:any = flightList.getFlights( true );
const $tbody = document.getElementById( "atc-flight-list-table-body" );
if ( $tbody instanceof HTMLElement ) {
if ( flights.length > 0 ) {
let flight:any = {};
let $button, i;
for ( [ i, flight ] of flights.entries() ) {
const $row = document.createElement( "tr" );
$row.dataset.status = flight.status
let $td = document.createElement( "td" );
$td.innerText = flight.name;
$row.appendChild( $td );
$td = document.createElement( "td" );
$td.innerText = flight.takeOffTime;
$row.appendChild( $td );
$td = document.createElement( "td" );
$td.innerText = "00:0" + ( 5 + i );
$row.appendChild( $td );
$td = document.createElement( "td" );
$td.innerText = flight.status;
$row.appendChild( $td );
$td = document.createElement( "td" );
$button = document.createElement( "button" );
$button.innerText = "...";
$td.appendChild( $button );
$row.appendChild( $td );
$tbody.appendChild( $row );
}
}
}
}
protected onStatusUpdate(): void {
document.body.classList.toggle( "atc-enabled", this.getStatus() );
}
}

View File

@@ -0,0 +1,7 @@
export abstract class ATCMockAPI {
constructor() {}
generateMockData() {}
}

View File

@@ -0,0 +1,40 @@
import { ATCMockAPI } from "../atcmockapi";
export class ATCMockAPI_Flights extends ATCMockAPI {
generateMockData() {
let data = [];
const statuses = [ "unknown", "checkedIn", "readyToTaxi" ]
for ( const [ i, flightName ] of [ "Shark", "Whale", "Dolphin" ].entries() ) {
data.push({
"name": flightName,
"status": statuses[ i ],
"takeOffTime": "18:0" + i
});
}
localStorage.setItem( "flightList", JSON.stringify( data ) );
}
get( generateMockDataIfEmpty?:boolean ) : object {
generateMockDataIfEmpty = generateMockDataIfEmpty || false;
let data = localStorage.getItem( "flightList" ) || "[]";
if ( data === "[]" && generateMockDataIfEmpty ) {
this.generateMockData();
}
return JSON.parse( data );
}
}

View File

@@ -0,0 +1,18 @@
import { ATCMockAPI_Flights } from "./atcmockapi/flights";
export class ATCFLightList {
constructor() {
}
getFlights( generateMockDataIfEmpty?:boolean ) {
let api = new ATCMockAPI_Flights();
return api.get( generateMockDataIfEmpty );
}
}

View File

@@ -0,0 +1,161 @@
export interface FeatureSwitchInterface {
"defaultEnabled": boolean, // default on/off state (if allowed by masterSwitch)
"label": string,
"masterSwitch": boolean, // on/off regardless of user preference
"name": string,
"onEnabled"?: CallableFunction,
"options"?: object,
"removeArtifactsIfDisabled"?: boolean
}
class FeatureSwitch {
// From config param
defaultEnabled;
label;
masterSwitch;
name;
onEnabled;
removeArtifactsIfDisabled = true;
// Self-set
userPreference;
constructor( config:FeatureSwitchInterface ) {
this.defaultEnabled = config.defaultEnabled;
this.label = config.label;
this.masterSwitch = config.masterSwitch;
this.name = config.name;
this.onEnabled = config.onEnabled;
this.userPreference = this.getUserPreference();
}
getUserPreference() {
let preferences = JSON.parse( localStorage.getItem( "featureSwitches" ) || "{}" );
return ( preferences.hasOwnProperty( this.name ) ) ? preferences[ this.name ] : this.defaultEnabled;
}
isEnabled() {
if ( !this.masterSwitch ) {
return false;
}
return this.userPreference;
}
}
export class FeatureSwitches {
#featureSwitches:FeatureSwitch[] = [
new FeatureSwitch({
"defaultEnabled": false,
"label": "AIC",
"masterSwitch": true,
"name": "aic"
}),
new FeatureSwitch({
"defaultEnabled": false,
"label": "AI Formations",
"masterSwitch": true,
"name": "ai-formations",
"removeArtifactsIfDisabled": false
}),
new FeatureSwitch({
"defaultEnabled": false,
"label": "ATC",
"masterSwitch": true,
"name": "atc"
}),
new FeatureSwitch({
"defaultEnabled": false,
"label": "Force show unit control panel",
"masterSwitch": true,
"name": "forceShowUnitControlPanel"
}),
new FeatureSwitch({
"defaultEnabled": false,
"label": "Show splash screen",
"masterSwitch": true,
"name": "splashScreen"
})
];
constructor() {
this.#testSwitches();
this.savePreferences();
}
getSwitch( switchName:string ) {
return this.#featureSwitches.find( featureSwitch => featureSwitch.name === switchName );
}
#testSwitches() {
for ( const featureSwitch of this.#featureSwitches ) {
if ( featureSwitch.isEnabled() ) {
if ( typeof featureSwitch.onEnabled === "function" ) {
featureSwitch.onEnabled();
}
} else {
document.querySelectorAll( "[data-feature-switch='" + featureSwitch.name + "']" ).forEach( el => {
if ( featureSwitch.removeArtifactsIfDisabled === false ) {
el.remove();
} else {
el.classList.add( "hide" );
}
});
}
document.body.classList.toggle( "feature-" + featureSwitch.name, featureSwitch.isEnabled() );
}
}
savePreferences() {
let preferences:any = {};
for ( const featureSwitch of this.#featureSwitches ) {
preferences[ featureSwitch.name ] = featureSwitch.isEnabled();
}
localStorage.setItem( "featureSwitches", JSON.stringify( preferences ) );
}
}

View File

@@ -6,8 +6,8 @@ import { MissionHandler } from "./missionhandler/missionhandler";
import { UnitControlPanel } from "./panels/unitcontrolpanel";
import { MouseInfoPanel } from "./panels/mouseinfopanel";
import { AIC } from "./aic/aic";
import { ATC } from "./atc/ATC";
import { FeatureSwitches } from "./FeatureSwitches";
import { ATC } from "./atc/atc";
import { FeatureSwitches } from "./featureswitches";
import { LogPanel } from "./panels/logpanel";
import { getAirbases, getBulllseye as getBulllseyes, getMission, getUnits, toggleDemoEnabled } from "./server/server";

View File

@@ -0,0 +1,35 @@
export abstract class ToggleableFeature {
#status:boolean = false;
constructor( defaultStatus:boolean ) {
this.#status = defaultStatus;
this.onStatusUpdate();
}
getStatus() : boolean {
return this.#status;
}
protected onStatusUpdate() {}
toggleStatus( force?:boolean ) : void {
if ( force ) {
this.#status = force;
} else {
this.#status = !this.#status;
}
this.onStatusUpdate();
}
}