Slightly nicer PoC.

This commit is contained in:
PeekabooSteam 2023-04-04 23:38:08 +01:00
parent 6f64bd1622
commit 071942b632
8 changed files with 122 additions and 49 deletions

View File

@ -12,7 +12,7 @@
column-gap: 4px;
display:flex;
flex-flow: row nowrap;
padding:4px;
row-gap:4px;
}
.ol-strip-board-strip[data-flight-status="checkedin"] {
@ -20,7 +20,7 @@
}
.ol-strip-board-strip[data-flight-status="readytotaxi"] {
background-color: #ffff002A;
background-color: #ffff0063;
}
.ol-strip-board-strip[data-flight-status="clearedtotaxi"] {
@ -46,7 +46,7 @@
padding: 4px;
text-overflow: ellipsis;
white-space: nowrap;
width:70px;
width:80px;
}
.ol-strip-board-strip input[type="text"] {

View File

@ -7,6 +7,8 @@
}
#primary-toolbar {
align-items: center;
display:flex;
position: absolute;
left: 10px;
top: 10px;

View File

@ -346,6 +346,11 @@ nav.ol-panel> :last-child {
row-gap: 4px;
}
.ol-group-header {
text-align: center;
width: 100%;
}
.ol-panel .ol-group.wrap {
flex-wrap: wrap;
}
@ -545,30 +550,6 @@ nav.ol-panel> :last-child {
width: 28px;
}
#unit-selection #unit-identification [data-object|="unit"] .unit-short-label {
font-size: 12px;
}
#unit-selection #unit-identification #unit-name {
background-color: transparent;
border: none;
color: white;
font-size: 16px;
font-weight: var(--font-weight-bolder);
outline: none;
overflow: hidden;
white-space: nowrap;
width: 150px;
}
#edit-unit-name {
background-image: url("/images/buttons/edit.svg");
background-repeat: no-repeat;
height: 14px;
margin-left: 10px;
width: 15px;
}
#unit-visibility-control {
align-items: center;
}
@ -619,6 +600,18 @@ body[data-hide-navyunit] #unit-visibility-control-navyunit {
background-image: var(--visibility-control-navyunit-hidden-url);
}
#atc-navbar-control {
align-items: center;
display:flex;
flex-direction: column;
}
#atc-navbar-control button {
background:#ffffff20;
border-radius: var( --border-radius-sm );
padding:4px;
}
.toggle {
--width: 40px;

View File

@ -1,8 +1,12 @@
import { Draggable } from "leaflet";
import { Dropdown } from "../controls/dropdown";
import { zeroAppend } from "../other/utils";
import { ATC } from "./atc";
export interface ATCTemplateInterface {
"template": string
export interface StripBoardStripInterface {
"id": string,
"element": HTMLElement,
"dropdowns": {[key:string]: Dropdown}
}
export abstract class ATCBoard {
@ -14,6 +18,9 @@ export abstract class ATCBoard {
#boardElement:HTMLElement;
#clockElement:HTMLElement;
#stripBoardElement:HTMLElement;
// Content
#strips:{[key:string]: StripBoardStripInterface} = {};
// Update timing
#updateInterval:number|undefined = undefined;
@ -27,6 +34,18 @@ export abstract class ATCBoard {
this.#stripBoardElement = <HTMLElement>this.getBoardElement().querySelector( ".ol-strip-board-strips" );
this.#clockElement = <HTMLElement>this.getBoardElement().querySelector( ".ol-strip-board-clock" );
if ( this.#boardElement.classList.contains( "ol-draggable" ) ) {
let options:any = {};
let handle = this.#boardElement.querySelector( ".handle" );
if ( handle instanceof HTMLElement ) {
options.handle = handle;
}
}
setInterval( () => {
this.updateClock();
@ -35,17 +54,30 @@ export abstract class ATCBoard {
}
addStrip( strip:StripBoardStripInterface ) {
this.#strips[ strip.id ] = strip;
}
calculateTimeToGo( fromTimestamp:number, toTimestamp:number ) {
let timestamp = ( toTimestamp - fromTimestamp ) / 1000;
const hours = zeroAppend( Math.floor( timestamp / 3600 ), 2 );
const hasElapsed = ( timestamp < 0 ) ? true : false;
if ( hasElapsed ) {
timestamp = -( timestamp );
}
const hours = ( timestamp < 3600 ) ? "00" : zeroAppend( Math.floor( timestamp / 3600 ), 2 );
const rMinutes = timestamp % 3600;
const minutes = zeroAppend( Math.floor( rMinutes / 60 ), 2 );
const minutes = ( timestamp < 60 ) ? "00" : zeroAppend( Math.floor( rMinutes / 60 ), 2 );
const seconds = zeroAppend( Math.floor( rMinutes % 60 ), 2 );
return {
"elapsedMarker": ( hasElapsed ) ? "+" : "-",
"hasElapsed": hasElapsed,
"hours": hours,
"minutes": minutes,
"seconds": seconds,
@ -56,6 +88,16 @@ export abstract class ATCBoard {
}
deleteStrip( id:string ) {
if ( this.#strips.hasOwnProperty( id ) ) {
this.#strips[ id ].element.remove();
delete this.#strips[ id ];
}
}
getATC() {
return this.#atc;
}
@ -71,6 +113,16 @@ export abstract class ATCBoard {
}
getStrips() {
return this.#strips;
}
getStrip( id:string ) {
return this.#strips[ id ] || false;
}
getTemplate( key:string ) {
return this.#templates[ key ] || false;
@ -115,7 +167,9 @@ export abstract class ATCBoard {
timeToGo( timestamp:number ) {
return ( timestamp === -1 ) ? "-" : this.calculateTimeToGo( this.getATC().getMissionDateTime().getTime(), timestamp ).time;
const timeData = this.calculateTimeToGo( this.getATC().getMissionDateTime().getTime(), timestamp );
return ( timestamp === -1 ) ? "-" : timeData.elapsedMarker + timeData.time;
}

View File

@ -1,7 +1,7 @@
import { getMissionData } from "../..";
import { Dropdown } from "../../controls/dropdown";
import { ATC } from "../atc";
import { ATCBoard } from "../atcboard";
import { ATCBoard, StripBoardStripInterface } from "../atcboard";
export class ATCBoardFlight extends ATCBoard {
@ -83,7 +83,7 @@ export class ATCBoardFlight extends ATCBoard {
flights.forEach( flight => {
let strip = stripBoard.querySelector( `[data-flight-id="${flight.id}"]`);
let strip = this.getStrip( flight.id );
if ( !strip ) {
@ -104,15 +104,20 @@ export class ATCBoardFlight extends ATCBoard {
stripBoard.insertAdjacentHTML( "beforeend", template );
strip = <HTMLElement>stripBoard.lastElementChild;
strip.querySelectorAll( ".ol-select" ).forEach( select => {
strip = {
"id": flight.id,
"element": <HTMLElement>stripBoard.lastElementChild,
"dropdowns": {}
};
strip.element.querySelectorAll( ".ol-select" ).forEach( select => {
switch( select.getAttribute( "data-point" ) ) {
case "status":
new Dropdown( select.id, ( value:string, ev:MouseEvent ) => {
strip.dropdowns.status = new Dropdown( select.id, ( value:string, ev:MouseEvent ) => {
fetch( '/api/atc/flight/' + flight.id, {
method: 'PATCH',
@ -135,10 +140,7 @@ export class ATCBoardFlight extends ATCBoard {
});
strip.querySelectorAll( `input[type="text"]` ).forEach( input => {
strip.element.querySelectorAll( `input[type="text"]` ).forEach( input => {
if ( input instanceof HTMLInputElement ) {
@ -190,22 +192,26 @@ export class ATCBoardFlight extends ATCBoard {
});
this.addStrip( strip );
} else {
// TODO: change status dropdown if status is different
strip.setAttribute( "data-flight-status", flight.status );
if ( flight.status !== strip.element.getAttribute( "data-flight-status" ) ) {
strip.element.setAttribute( "data-flight-status", flight.status );
strip.dropdowns.status.selectText( flight.status );
}
strip.querySelectorAll( `input[name="takeoffTime"]:not(:focus)` ).forEach( el => {
strip.element.querySelectorAll( `input[name="takeoffTime"]:not(:focus)` ).forEach( el => {
if ( el instanceof HTMLInputElement ) {
el.value = this.timestampToLocaleTime( flight.takeoffTime );
el.dataset.previousValue = el.value;
}
});
strip.querySelectorAll( `[data-point="timeToGo"]` ).forEach( el => {
strip.element.querySelectorAll( `[data-point="timeToGo"]` ).forEach( el => {
if ( flight.takeoffTime > 0 && this.calculateTimeToGo( missionTime, flight.takeoffTime ).totalSeconds <= 120 ) {
strip?.setAttribute( "data-time-warning", "level-1" );
strip.element.setAttribute( "data-time-warning", "level-1" );
}
if ( el instanceof HTMLElement ) {
@ -217,12 +223,12 @@ export class ATCBoardFlight extends ATCBoard {
}
strip.toggleAttribute( "data-updating", false );
strip.element.toggleAttribute( "data-updating", false );
});
stripBoard.querySelectorAll( `[data-updating]` ).forEach( strip => {
strip.remove();
this.deleteStrip( strip.getAttribute( "data-flight-id" ) || "" );
});
}

View File

@ -54,6 +54,15 @@ export class Dropdown {
}));
}
selectText( text:string ) {
const index = [].slice.call( this.#options.children ).findIndex( ( opt:Element ) => opt.querySelector( "button" )?.innerText === text );
if ( index > -1 ) {
this.selectValue( index );
}
}
selectValue(idx: number)
{
if (idx < this.#optionsList.length)

View File

@ -1,4 +1,4 @@
<div class="ol-panel ol-dialog ol-strip-board" data-feature-switch="atc">
<div id="strip-board-ground" class="ol-panel ol-dialog ol-strip-board ol-draggable" data-feature-switch="atc">
<div class="ol-dialog-close" data-on-click="closeDialog"></div>

View File

@ -50,4 +50,13 @@
</div>
</div>
<div id="atc-navbar-control" class="ol-group-container" data-feature-switch="atc">
<div class="ol-group-header">ATC</div>
<div class="ol-group">
<button data-on-click="toggleElements" data-on-click-params='{"selector": "#strip-board-ground"}'>GND</button>
<button>TWR</button>
</div>
</div>
</nav>