Adjusting body highlight to match settings.

This commit is contained in:
punkfairie 2023-05-13 16:01:46 -07:00
parent 26b112ae9a
commit e519bdbcdf
4 changed files with 158 additions and 172 deletions

View file

@ -44,7 +44,7 @@ export class Settings {
this.maxDistance = contents.maxDistance; this.maxDistance = contents.maxDistance;
} }
static get(isPackaged: boolean): Settings { static get(isPackaged: boolean = false): Settings {
if (!Settings.#instance) { if (!Settings.#instance) {
Settings.#instance = new Settings(isPackaged); Settings.#instance = new Settings(isPackaged);
} }

View file

@ -1,44 +1,44 @@
import type { completeFsdJump, location, navRouteSystem } from "../@types/journalLines" import type { completeFsdJump, location, navRouteSystem } from '../@types/journalLines';
import * as _ from 'lodash-es' import * as _ from 'lodash-es';
import { Body } from "./Body" import { Body } from './Body';
import { EDSM } from "./EDSM" import { EDSM } from './EDSM';
export class System { export class System {
name: string name: string;
SystemAddress?: number SystemAddress?: number;
StarClass?: string StarClass?: string;
charted: boolean charted: boolean;
bodies: Body[] bodies: Body[];
// ESDM data // ESDM data
estimatedValue?: number estimatedValue?: number;
estimatedValueMapped?: number estimatedValueMapped?: number;
valuableBodies?: Body[] valuableBodies?: Body[];
constructor(line?: navRouteSystem|completeFsdJump|location) { constructor(line?: navRouteSystem|completeFsdJump|location) {
// In future, this is where we preform EDSM lookup // In future, this is where we preform EDSM lookup
if (!line) { if (!line) {
this.name = 'Unknown' this.name = 'Unknown';
} else { } else {
this.name = line.StarSystem this.name = line.StarSystem;
this.SystemAddress = line.SystemAddress this.SystemAddress = line.SystemAddress;
if ('StarClass' in line) { if ('StarClass' in line) {
this.StarClass = line.StarClass this.StarClass = line.StarClass;
} }
} }
// Set this to true initially, since it likely is and the system is technically inserted // Set this to true initially, since it likely is and the system is technically inserted
// into the UI before it's appraised. // into the UI before it's appraised.
this.charted = true this.charted = true;
this.bodies = [] this.bodies = [];
if (this.name !== 'Unknown') { if (this.name !== 'Unknown') {
this.#getValue() this.#getValue();
} }
} }
@ -46,32 +46,36 @@ export class System {
async #getValue() { async #getValue() {
// display estimatedValueMapped // display estimatedValueMapped
const data = await EDSM.getSystemValue(this) const data = await EDSM.getSystemValue(this);
if (data) { if (data) {
this.estimatedValue = data.estimatedValue this.estimatedValue = data.estimatedValue;
this.estimatedValueMapped = data.estimatedValueMapped this.estimatedValueMapped = data.estimatedValueMapped;
// If EDSM doesn't have an estimate, then it's likely undiscovered. // If EDSM doesn't have an estimate, then it's likely undiscovered.
this.charted = this.estimatedValue > 0 this.charted = this.estimatedValue > 0;
// Save valuable bodies in system, if any. // Save valuable bodies in system, if any.
if (data.valuableBodies.length > 0) { if (data.valuableBodies.length > 0) {
this.valuableBodies = [] this.valuableBodies = [];
data.valuableBodies.forEach((body) => { data.valuableBodies.forEach((body) => {
this.valuableBodies?.push(new Body(body)) this.valuableBodies?.push(new Body(body));
}) });
} }
// Let the UI know it needs to update. // Let the UI know it needs to update.
EDSM.connect().emit('SYSTEM_APPRAISED', this) EDSM.connect().emit('SYSTEM_APPRAISED', this);
} }
} }
/* -------------------------------------------------------------------------- sortBodies ---- */ /* -------------------------------------------------------------------------- sortBodies ---- */
sortBodies(): void { sortBodies(): void {
this.bodies = _.orderBy(this.bodies, ['mappedValue'], ['desc']) this.bodies = _.orderBy(
this.bodies,
['mappedValue', 'DistanceFromArrivalLS'],
['desc', 'desc'],
);
} }
} }

View file

@ -1,176 +1,186 @@
import { Settings } from './Settings';
export class UI { export class UI {
constructor() {} constructor() {}
/* ----------------------------------------------------------------------- #formatNumber ---- */ /* ----------------------------------------------------------------------- #formatNumber ---- */
static #formatNumber(number) { static #formatNumber(number) {
return Intl.NumberFormat().format(Math.round(number)) return Intl.NumberFormat().format(Math.round(number));
} }
/* --------------------------------------------------------------------- enterWitchSpace ---- */ /* --------------------------------------------------------------------- enterWitchSpace ---- */
static enterWitchSpace() { static enterWitchSpace() {
$('#scans').children().remove() $('#scans').children().remove();
$('#currentSystem').removeClass('charted').addClass('highlighted text-center') $('#currentSystem').removeClass('charted').addClass('highlighted text-center');
$('#currentSystemIcon').addClass('hidden') $('#currentSystemIcon').addClass('hidden');
$('#currentSystemName').text('> > > Hyperspace < < <') $('#currentSystemName').text('> > > Hyperspace < < <');
} }
/* -------------------------------------------------------------------- setCurrentSystem ---- */ /* -------------------------------------------------------------------- setCurrentSystem ---- */
static setCurrentSystem(system) { static setCurrentSystem(system) {
$('#scans').children().remove() $('#scans').children().remove();
$('#currentSystem').children().remove() $('#currentSystem').children().remove();
let row let row;
if (system.name === 'Unknown') { if (system.name === 'Unknown') {
row = $('<div>').addClass('row ms-1 me-1') row = $('<div>').addClass('row ms-1 me-1');
const child = $('<div>').addClass('col system highlighted text-center') const child = $('<div>').addClass('col system highlighted text-center');
child.text(system.name) child.text(system.name);
row.appendChild(child) row.appendChild(child);
} else { } else {
row = UI.createSystemRow(system) row = UI.createSystemRow(system);
} }
$('#currentSystem').appendChild(row) $('#currentSystem').appendChild(row);
} }
/* -------------------------------------------------------------------------- buildRings ---- */ /* -------------------------------------------------------------------------- buildRings ---- */
static #buildRings(body) { static #buildRings(body) {
const rings = $('<span>') const rings = $('<span>');
const seperator = $('<span>').text(' ) ') const seperator = $('<span>').text(' ) ');
rings.appendChild(seperator) rings.appendChild(seperator);
body.Rings.forEach((ring) => { body.Rings.forEach((ring) => {
const ringClass = ring.RingClass.replace('eRingClass_', '') const ringClass = ring.RingClass.replace('eRingClass_', '');
let icon = null let icon = null;
switch (ringClass) { switch (ringClass) {
case 'MetalRich': { case 'MetalRich': {
icon = 'gold-bars' icon = 'gold-bars';
break break;
} }
case 'Metalic': case 'Metalic':
case 'Metallic': { case 'Metallic': {
icon = 'ingot' icon = 'ingot';
break break;
} }
case 'Icy': { case 'Icy': {
icon = 'snowflake' icon = 'snowflake';
break break;
} }
case 'Rocky': { case 'Rocky': {
icon = 'asteroid-3' icon = 'asteroid-3';
break break;
} }
} }
if (icon !== null) { if (icon !== null) {
rings.appendChild($('<i>').addClass(`flaticon-${icon}`)) rings.appendChild($('<i>').addClass(`flaticon-${icon}`));
rings.appendChild(seperator) rings.appendChild(seperator);
} }
}) })
return rings return rings;
} }
/* ----------------------------------------------------------------------- createBodyRow ---- */ /* ----------------------------------------------------------------------- createBodyRow ---- */
static createBodyRow(body) { static createBodyRow(body) {
const chartedStyle = body.WasDiscovered && !body.DSSDone ? 'charted' : 'uncharted' const chartedStyle = body.WasDiscovered && !body.DSSDone ? 'charted' : 'uncharted';
// TODO USER SETTINGS
const valuableStyle = body.mappedValue > 2000 ? 'highlighted' : ''
const row = $('<div>').addClass('row ms-1 me-1') const settings = Settings.get();
row.attr('id', body.bodyID) let valuableStyle = '';
if (
body.mappedValue > settings.minValue
&& body.DistanceFromArrivalLS < settings.maxDistance
) {
valuableStyle = 'highlighted';
}
const row = $('<div>').addClass('row ms-1 me-1');
row.attr('id', body.bodyID);
// spacer // spacer
row.appendChild($('<div>').addClass('col-1 system')) row.appendChild($('<div>').addClass('col-1 system'));
// name // name
const name = $('<div>').addClass(`col-2 text-start system ${chartedStyle} ${valuableStyle}`) const name = $('<div>');
name.appendChild($('<i>')).addClass(`flaticon-${body.nameIcon()}`) name.addClass(`col-2 text-start system ${chartedStyle} ${valuableStyle}`)
name.appendChild($('<span>')).text(body.simpleName()) name.appendChild($('<i>')).addClass(`flaticon-${body.nameIcon()}`);
row.appendChild(name) name.appendChild($('<span>')).text(body.simpleName());
row.appendChild(name);
// type icon // type icon
const type = $('<div>').addClass(`col pe-0 me-0 system ${chartedStyle} ${valuableStyle}`) const type = $('<div>').addClass(`col pe-0 me-0 system ${chartedStyle} ${valuableStyle}`);
type.appendChild($('<i>').addClass(`flaticon-${body.typeIcon()}`)) type.appendChild($('<i>').addClass(`flaticon-${body.typeIcon()}`));
// rings // rings
if (body.Rings !== undefined) { if (body.Rings !== undefined) {
type.appendChild(UI.#buildRings(body)) type.appendChild(UI.#buildRings(body));
} }
// type // type
const typeName = body.PlanetClass || body.starType || '' const typeName = body.PlanetClass || body.starType || '';
type.appendChild($('<span>').text(` ${typeName}`)) type.appendChild($('<span>').text(` ${typeName}`));
row.appendChild(type) row.appendChild(type);
// distance // distance
const distance = $('<div>') const distance = $('<div>');
distance.addClass(`col-auto ps-2 ms-0 system ${chartedStyle} ${valuableStyle}`) distance.addClass(`col-auto ps-2 ms-0 system ${chartedStyle} ${valuableStyle}`);
distance.text(UI.#formatNumber(body.DistanceFromArrivalLS)) distance.text(UI.#formatNumber(body.DistanceFromArrivalLS));
row.appendChild(distance) row.appendChild(distance);
// info // info
const info = $('<div>').addClass(`col-1 system ${chartedStyle} ${valuableStyle}`) const info = $('<div>').addClass(`col-1 system ${chartedStyle} ${valuableStyle}`);
// terraformable // terraformable
const terraform = $('<i>').addClass('flaticon-cooling-tower opacity-0') const terraform = $('<i>').addClass('flaticon-cooling-tower opacity-0');
if (body.isPlanet && body.TerraformState) { if (body.isPlanet && body.TerraformState) {
terraform.removeClass('opacity-0') terraform.removeClass('opacity-0');
} }
info.appendChild(terraform) info.appendChild(terraform);
// was mapped // was mapped
const mapped = $('<i>') const mapped = $('<i>')
mapped.addClass('flaticon-flag-outline-on-a-pole-with-stars-around opacity-0') mapped.addClass('flaticon-flag-outline-on-a-pole-with-stars-around opacity-0');
if (body.isPlanet() && !body.WasMapped) { if (body.isPlanet() && !body.WasMapped) {
mapped.removeClass('opacity-0') mapped.removeClass('opacity-0');
} }
info.appendChild(mapped) info.appendChild(mapped);
row.appendChild(info) row.appendChild(info);
// mapped value // mapped value
const value = $('<div>').addClass(`col-2 text-end system ${chartedStyle} ${valuableStyle}`) const value = $('<div>').addClass(`col-2 text-end system ${chartedStyle} ${valuableStyle}`);
value.text(UI.#formatNumber(body.mappedValue)) value.text(UI.#formatNumber(body.mappedValue));
row.appendChild(value) row.appendChild(value);
return row return row;
} }
/* --------------------------------------------------------------------- createSystemRow ---- */ /* --------------------------------------------------------------------- createSystemRow ---- */
static createSystemRow(system) { static createSystemRow(system) {
const row = $('<div>').addClass('row ms-1 me-1') const row = $('<div>').addClass('row ms-1 me-1');
row.attr('id', system.SystemAddress) row.attr('id', system.SystemAddress);
// This is probably still the default 'true' value, but check in case the fetch() was quick. // This is probably still the default 'true' value, but check in case the fetch() was quick.
const chartedStyle = system.charted ? 'charted' : 'uncharted' const chartedStyle = system.charted ? 'charted' : 'uncharted';
// name // name
const name = $('<div>').addClass(`col system ${chartedStyle}`) const name = $('<div>').addClass(`col system ${chartedStyle}`);
name.appendChild($('<i>').addClass('flaticon-solar-system')) name.appendChild($('<i>').addClass('flaticon-solar-system'));
name.appendChild($('<span>').text(` ${system.name}`)) name.appendChild($('<span>').text(` ${system.name}`));
row.appendChild(name) row.appendChild(name);
// mapped value // mapped value
// Check if EDSM has responded yet, otherwise value will be filled in later. // Check if EDSM has responded yet, otherwise value will be filled in later.
const value = $('<div>').addClass(`col-2 text-end system ${chartedStyle} value`) const value = $('<div>').addClass(`col-2 text-end system ${chartedStyle} value`);
if ('estimatedValueMapped' in system) { if ('estimatedValueMapped' in system) {
value.text(UI.#formatNumber(system.estimatedValueMapped)) value.text(UI.#formatNumber(system.estimatedValueMapped));
} }
row.appendChild(value) row.appendChild(value);
return row return row;
} }
/* ---------------------------------------------------------------------------- setValue ---- */ /* ---------------------------------------------------------------------------- setValue ---- */
static setValue(row, value) { static setValue(row, value) {
row.children().filter('.value').text(UI.#formatNumber(value)) row.children().filter('.value').text(UI.#formatNumber(value));
} }
} }

View file

@ -1,130 +1,102 @@
/** import 'bootstrap/dist/css/bootstrap.css';
* This file will automatically be loaded by vite and run in the "renderer" context. import './assets/index.css';
* To learn more about the differences between the "main" and the "renderer" context in import './icons/flaticon.css';
* Electron, visit:
*
* https://electronjs.org/docs/tutorial/application-architecture#main-and-renderer-processes
*
* By default, Node.js integration in this file is disabled. When enabling Node.js integration
* in a renderer process, please be aware of potential security implications. You can read
* more about security risks here:
*
* https://electronjs.org/docs/tutorial/security
*
* To enable Node.js integration in this file, open up `main.js` and enable the `nodeIntegration`
* flag:
*
* ```
* // Create the browser window.
* mainWindow = new BrowserWindow({
* width: 800,
* height: 600,
* webPreferences: {
* nodeIntegration: true
* }
* });
* ```
*/
import 'bootstrap/dist/css/bootstrap.css' import './assets/ldom.min';
import './assets/index.css'
import './icons/flaticon.css'
import './assets/ldom.min' const { app, ipcRenderer } = require('electron');
const { app, ipcRenderer } = require('electron') import { Safari } from './models/Safari';
import { Settings } from './models/Settings';
import { Safari } from './models/Safari' import { UI } from './models/UI';
import { Settings } from './models/Settings' import { Body } from './models/Body';
import { UI } from './models/UI' import { EDSM } from './models/EDSM';
import { Body } from './models/Body'
import { EDSM } from './models/EDSM'
// Grab app.isPackaged from main process // Grab app.isPackaged from main process
let isPackaged = false let isPackaged = false;
window.process.argv.forEach((item) => { window.process.argv.forEach((item) => {
if (item.includes('EDS-ENV')) { if (item.includes('EDS-ENV')) {
isPackaged = (item.split('=').pop() === 'true') isPackaged = (item.split('=').pop() === 'true');
} }
}) })
/* ------------------------------------------------------------------------------- app setup ---- */ /* ------------------------------------------------------------------------------- app setup ---- */
const safari = Safari.start(isPackaged) const safari = Safari.start(isPackaged);
const settings = Settings.get(isPackaged) const settings = Settings.get(isPackaged);
const journal = safari.journal const journal = safari.journal;
const edsm = EDSM.connect() const edsm = EDSM.connect();
if (!journal) { if (!journal) {
// handle error // TODO handle error
} }
safari.watchJournalDir() safari.watchJournalDir();
journal.watch() journal.watch();
/* -------------------------------------------------------------------- close window handler ---- */ /* -------------------------------------------------------------------- close window handler ---- */
$('#closeBtn').on('click', () => { $('#closeBtn').on('click', () => {
ipcRenderer.send('CLOSE_WINDOW') ipcRenderer.send('CLOSE_WINDOW');
}) })
/* ----------------------------------------------------------------- settings button handler ---- */ /* ----------------------------------------------------------------- settings button handler ---- */
$('#settingsBtn').on('click', () => { $('#settingsBtn').on('click', () => {
ipcRenderer.send('LOAD_SETTINGS') ipcRenderer.send('LOAD_SETTINGS');
}) })
/* ------------------------------------------------------------------------- build body list ---- */ /* ------------------------------------------------------------------------- build body list ---- */
journal.once('BUILD_BODY_LIST', () => { journal.once('BUILD_BODY_LIST', () => {
if (journal.location?.bodies?.length > 0) { if (journal.location?.bodies?.length > 0) {
journal.location.sortBodies() journal.location.sortBodies();
journal.location.bodies.forEach((body) => { journal.location.bodies.forEach((body) => {
const row = UI.createBodyRow(body) const row = UI.createBodyRow(body);
$('#scans').appendChild(row) $('#scans').appendChild(row);
}) })
} }
}) })
/* ----------------------------------------------------------------- started hyperspace jump ---- */ /* ----------------------------------------------------------------- started hyperspace jump ---- */
journal.on('ENTERING_WITCH_SPACE', () => UI.enterWitchSpace()) journal.on('ENTERING_WITCH_SPACE', () => UI.enterWitchSpace());
/* ---------------------------------------------------------------------- entered new system ---- */ /* ---------------------------------------------------------------------- entered new system ---- */
journal.on('ENTERED_NEW_SYSTEM', () => { journal.on('ENTERED_NEW_SYSTEM', () => {
UI.setCurrentSystem(journal.location) UI.setCurrentSystem(journal.location);
$('#navRoute').children().filter(`#${CSS.escape(journal.location.SystemAddress)}`).remove() $('#navRoute').children().filter(`#${CSS.escape(journal.location.SystemAddress)}`).remove();
// verify that the internal navRoute matches the UI navRoute, and rebuild it if not // verify that the internal navRoute matches the UI navRoute, and rebuild it if not
if ($('#navRoute').children().length !== journal.navRoute.length) { if ($('#navRoute').children().length !== journal.navRoute.length) {
journal.emit('SET_NAV_ROUTE') journal.emit('SET_NAV_ROUTE');
} }
}) })
/* ---------------------------------------------------------------------- body scan detected ---- */ /* ---------------------------------------------------------------------- body scan detected ---- */
journal.on('BODY_SCANNED', (body, DSS) => { journal.on('BODY_SCANNED', (body, DSS) => {
journal.location.sortBodies() journal.location.sortBodies();
// If this is a DSS scan, it's very likely that the body already exists in our list so we just // If this is a DSS scan, it's very likely that the body already exists in our list so we just
// need to remove the highlighting if applicable // need to remove the highlighting if applicable
if (DSS) { if (DSS) {
const bodyRow = $(`#${body.BodyID}`) const bodyRow = $(`#${body.BodyID}`);
if (bodyRow.length > 0) { // check just in case body was missed in earlier scans if (bodyRow.length > 0) { // check just in case body was missed in earlier scans
bodyRow.removeClass('highlighted uncharted').addClass('charted') bodyRow.removeClass('highlighted uncharted').addClass('charted');
} else { } else {
const row = UI.createBodyRow(body) const row = UI.createBodyRow(body);
$('#scans').appendChild(row) $('#scans').appendChild(row);
} }
} else { // else it's an FSS/auto scan and won't be in the list yet } else { // else it's an FSS/auto scan and won't be in the list yet
const row = UI.createBodyRow(body) const row = UI.createBodyRow(body);
$('#scans').appendChild(row) $('#scans').appendChild(row);
} }
}) })
@ -132,17 +104,17 @@ journal.on('BODY_SCANNED', (body, DSS) => {
journal.on('SET_NAV_ROUTE', () => { journal.on('SET_NAV_ROUTE', () => {
// clear previous nav route, if any // clear previous nav route, if any
$('#navRoute').children().remove() $('#navRoute').children().remove();
if (journal.navRoute.length > 0) { if (journal.navRoute.length > 0) {
journal.navRoute.forEach((system) => { journal.navRoute.forEach((system) => {
// duplicate check // duplicate check
// CSS.escape is needed since CSS technically doesn't allow numeric IDs // CSS.escape is needed since CSS technically doesn't allow numeric IDs
const systemRow = $(`#${CSS.escape(system.SystemAddress)}`) const systemRow = $(`#${CSS.escape(system.SystemAddress)}`);
if (systemRow.length === 0) { if (systemRow.length === 0) {
const row = UI.createSystemRow(system) const row = UI.createSystemRow(system);
$('#navRoute').appendChild(row) $('#navRoute').appendChild(row);
} }
}) })
} }
@ -151,9 +123,9 @@ journal.on('SET_NAV_ROUTE', () => {
/* ------------------------------------------------------------------------ system value set ---- */ /* ------------------------------------------------------------------------ system value set ---- */
edsm.on('SYSTEM_APPRAISED', (system) => { edsm.on('SYSTEM_APPRAISED', (system) => {
const systemRow = $(`#${CSS.escape(system.SystemAddress)}`) const systemRow = $(`#${CSS.escape(system.SystemAddress)}`);
if (systemRow.length > 0) { if (systemRow.length > 0) {
UI.setValue(systemRow, system.estimatedValueMapped) UI.setValue(systemRow, system.estimatedValueMapped);
} }
}) })