Skip to content

Commit

Permalink
Added abbreviated variant of calculated IAS tag item
Browse files Browse the repository at this point in the history
Removed reported IAS range options, values are now hardcoded
Added tests verifying `roundToNearest` rounding for ints and doubles
Version bump to v1.2.0
  • Loading branch information
MorpheusXAUT committed Aug 6, 2022
1 parent 8dc6fe0 commit 4f850c6
Show file tree
Hide file tree
Showing 10 changed files with 209 additions and 195 deletions.
211 changes: 60 additions & 151 deletions IASsure/IASsure.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -16,12 +16,6 @@ IASsure::IASsure::IASsure() : EuroScopePlugIn::CPlugIn(
this->RegisterTagItems();

this->debug = false;
this->minReportedIAS = 150;
this->maxReportedIAS = 400;
this->intervalReportedIAS = 5;
this->minReportedMach = 50;
this->maxReportedMach = 99;
this->intervalReportedMach = 1;

this->LoadSettings();
}
Expand All @@ -37,132 +31,13 @@ bool IASsure::IASsure::OnCompileCommand(const char* sCommandLine)
if (args[0] == ".ias") {
if (args.size() == 1) {
std::ostringstream msg;
msg << "Version " << PLUGIN_VERSION << " loaded. Available commands: min, max, interval, debug, reset";
msg << "Version " << PLUGIN_VERSION << " loaded. Available commands: debug, reset";

this->LogMessage(msg.str());
return true;
}

if (args[1] == "min") {
if (args.size() < 2) {
this->LogMessage("Provide value to set minimum speed of reported IAS popup", "Config");
return true;
}

int min;
try {
min = std::stoi(args[2]);
}
catch (std::invalid_argument const&) {
this->LogMessage("Invalid value for minimum reported IAS speed, ensure you enter a valid number", "Config");
return true;
}
catch (std::out_of_range const&) {
std::ostringstream msg;
msg << "Value for minimum reported IAS speed is outside of valid range (" << MIN_MIN_REPORTED_IAS << " - " << MAX_MIN_REPORTED_IAS << ")";

this->LogMessage(msg.str(), "Config");
return true;
}

if (min < MIN_MIN_REPORTED_IAS || min > MAX_MIN_REPORTED_IAS) {
std::ostringstream msg;
msg << "Value for minimum reported IAS speed is outside of valid range (" << MIN_MIN_REPORTED_IAS << " - " << MAX_MIN_REPORTED_IAS << ")";

this->LogMessage(msg.str(), "Config");
return true;
}
else if (min > this->maxReportedIAS) {
std::ostringstream msg;
msg << "Value for minimum reported IAS speed cannot be greater than configured maximum reported IAS (" << this->maxReportedIAS<< ")";

this->LogMessage(msg.str(), "Config");
return true;
}

this->minReportedIAS = min;

this->SaveSettings();
return true;
}
else if (args[1] == "max") {
if (args.size() < 2) {
this->LogMessage("Provide value to set maximum speed of reported IAS popup", "Config");
return true;
}

int max;
try {
max = std::stoi(args[2]);
}
catch (std::invalid_argument const&) {
this->LogMessage("Invalid value for maximum reported IAS speed, ensure you enter a valid number", "Config");
return true;
}
catch (std::out_of_range const&) {
std::ostringstream msg;
msg << "Value for maximum reported IAS speed is outside of valid range (" << MIN_MAX_REPORTED_IAS << " - " << MAX_MAX_REPORTED_IAS << ")";

this->LogMessage(msg.str(), "Config");
return true;
}

if (max < MIN_MAX_REPORTED_IAS || max > MAX_MAX_REPORTED_IAS) {
std::ostringstream msg;
msg << "Value for maximum reported IAS speed is outside of valid range (" << MIN_MAX_REPORTED_IAS << " - " << MAX_MAX_REPORTED_IAS << ")";

this->LogMessage(msg.str(), "Config");
return true;
}
else if (max < this->minReportedIAS) {
std::ostringstream msg;
msg << "Value for maximum reported IAS speed cannot be less than configured minimum reported IAS (" << this->minReportedIAS << ")";

this->LogMessage(msg.str(), "Config");
return true;
}

this->maxReportedIAS = max;

this->SaveSettings();
return true;
}
else if (args[1] == "interval") {
if (args.size() < 2) {
this->LogMessage("Provide value to set interval for speeds of reported IAS popup", "Config");
return true;
}

int interval;
try {
interval = std::stoi(args[2]);
}
catch (std::invalid_argument const&) {
this->LogMessage("Invalid value for interval of reported IAS speed, ensure you enter a valid number", "Config");
return true;
}
catch (std::out_of_range const&) {
std::ostringstream msg;
msg << "Value for interval of reported IAS speed is outside of valid range (" << MIN_INTERVAL_REPORTED_IAS << " - " << MAX_INTERVAL_REPORTED_IAS << ")";

this->LogMessage(msg.str(), "Config");
return true;
}

if (interval < MIN_INTERVAL_REPORTED_IAS || interval > MAX_INTERVAL_REPORTED_IAS) {
std::ostringstream msg;
msg << "Value for interval of reported IAS speed is outside of valid range (" << MIN_INTERVAL_REPORTED_IAS << " - " << MAX_INTERVAL_REPORTED_IAS << ")";

this->LogMessage(msg.str(), "Config");
return true;
}

this->intervalReportedIAS = interval;

this->SaveSettings();
return true;
}
else if (args[1] == "debug") {
if (args[1] == "debug") {
if (this->debug) {
this->LogMessage("Disabling debug mode", "Config");
}
Expand All @@ -179,7 +54,10 @@ bool IASsure::IASsure::OnCompileCommand(const char* sCommandLine)
this->LogMessage("Resetting plugin state", "Config");

this->reportedIAS.clear();
this->reportedMach.clear();
this->calculatedIASToggled.clear();
this->calculatedIASAbbreviatedToggled.clear();
this->calculatedMachToggled.clear();
return true;
}
}
Expand All @@ -197,11 +75,19 @@ void IASsure::IASsure::OnGetTagItem(EuroScopePlugIn::CFlightPlan FlightPlan, Eur
case TAG_ITEM_CALCULATED_IAS:
this->CalculateIAS(RadarTarget, sItemString, pColorCode, pRGB);
break;
case TAG_ITEM_CALCULATED_IAS_ABBREVIATED:
this->CalculateIAS(RadarTarget, sItemString, pColorCode, pRGB, true);
break;
case TAG_ITEM_CALCULATED_IAS_TOGGLABLE:
if (this->calculatedIASToggled.contains(FlightPlan.GetCallsign())) {
this->CalculateIAS(RadarTarget, sItemString, pColorCode, pRGB);
}
break;
case TAG_ITEM_CALCULATED_IAS_ABBREVIATED_TOGGLABLE:
if (this->calculatedIASAbbreviatedToggled.contains(FlightPlan.GetCallsign())) {
this->CalculateIAS(RadarTarget, sItemString, pColorCode, pRGB, true);
}
break;
case TAG_ITEM_CALCULATED_MACH:
this->CalculateMach(RadarTarget, sItemString, pColorCode, pRGB);
break;
Expand Down Expand Up @@ -230,15 +116,15 @@ void IASsure::IASsure::OnFunctionCall(int FunctionId, const char* sItemString, P
int ias;
try {
double cas = ::IASsure::calculateCAS(rt.GetPosition().GetPressureAltitude(), rt.GetPosition().GetReportedGS());
ias = ::IASsure::roundToNearest(cas, this->intervalReportedIAS);
ias = ::IASsure::roundToNearest(cas, INTERVAL_REPORTED_IAS);
}
catch (std::exception const&) {
ias = rt.GetPosition().GetReportedGS();
}

this->OpenPopupList(Area, "Speed", 1);
for (int i = this->maxReportedIAS; i >= this->minReportedIAS; i -= this->intervalReportedIAS) {
this->AddPopupListElement(std::to_string(i).c_str(), NULL, TAG_FUNC_SET_REPORTED_IAS, i >= ias && ias >= i - this->intervalReportedIAS, EuroScopePlugIn::POPUP_ELEMENT_NO_CHECKBOX, false, false);
for (int i = MAX_REPORTED_IAS; i >= MIN_REPORTED_IAS; i -= INTERVAL_REPORTED_IAS) {
this->AddPopupListElement(std::to_string(i).c_str(), NULL, TAG_FUNC_SET_REPORTED_IAS, i >= ias && ias >= i - INTERVAL_REPORTED_IAS, EuroScopePlugIn::POPUP_ELEMENT_NO_CHECKBOX, false, false);
}
this->AddPopupListElement("---", NULL, 0, false, EuroScopePlugIn::POPUP_ELEMENT_NO_CHECKBOX, true, true);
this->AddPopupListElement("Clear", NULL, TAG_FUNC_CLEAR_REPORTED_IAS, false, EuroScopePlugIn::POPUP_ELEMENT_NO_CHECKBOX, false, true);
Expand All @@ -251,6 +137,9 @@ void IASsure::IASsure::OnFunctionCall(int FunctionId, const char* sItemString, P
case TAG_FUNC_TOGGLE_CALCULATED_IAS:
this->ToggleCalculatedIAS(fp);
break;
case TAG_FUNC_TOGGLE_CALCULATED_IAS_ABBREVIATED:
this->ToggleCalculatedIAS(fp, true);
break;
case TAG_FUNC_SET_REPORTED_IAS:
this->SetReportedIAS(fp, sItemString);
break;
Expand All @@ -260,18 +149,18 @@ void IASsure::IASsure::OnFunctionCall(int FunctionId, const char* sItemString, P
return;
}

int mach;
int mach = 0;
try {
double m = ::IASsure::calculateMach(rt.GetPosition().GetPressureAltitude(), rt.GetPosition().GetReportedGS());
mach = ::IASsure::roundToNearest(m * 100, this->intervalReportedMach);
mach = ::IASsure::roundToNearest(m * 100, INTERVAL_REPORTED_MACH);
}
catch (std::exception const&) {
// no default value available
// no default selection available
}

this->OpenPopupList(Area, "Mach", 1);
for (int i = this->maxReportedMach; i >= this->minReportedMach; i -= this->intervalReportedMach) {
this->AddPopupListElement(std::to_string(i).c_str(), NULL, TAG_FUNC_SET_REPORTED_MACH, i >= mach && mach >= i - this->intervalReportedMach, EuroScopePlugIn::POPUP_ELEMENT_NO_CHECKBOX, false, false);
for (int i = MAX_REPORTED_MACH; i >= MIN_REPORTED_MACH; i -= INTERVAL_REPORTED_MACH) {
this->AddPopupListElement(std::to_string(i).c_str(), NULL, TAG_FUNC_SET_REPORTED_MACH, i >= mach && mach >= i - INTERVAL_REPORTED_MACH, EuroScopePlugIn::POPUP_ELEMENT_NO_CHECKBOX, false, false);
}
this->AddPopupListElement("---", NULL, 0, false, EuroScopePlugIn::POPUP_ELEMENT_NO_CHECKBOX, true, true);
this->AddPopupListElement("Clear", NULL, TAG_FUNC_CLEAR_REPORTED_MACH, false, EuroScopePlugIn::POPUP_ELEMENT_NO_CHECKBOX, false, true);
Expand All @@ -294,12 +183,15 @@ void IASsure::IASsure::RegisterTagItems()
{
this->RegisterTagItemType("Calculated IAS", TAG_ITEM_CALCULATED_IAS);
this->RegisterTagItemType("Calculated IAS (togglable)", TAG_ITEM_CALCULATED_IAS_TOGGLABLE);
this->RegisterTagItemType("Calculated IAS (abbreviated)", TAG_ITEM_CALCULATED_IAS_ABBREVIATED);
this->RegisterTagItemType("Calculated IAS (abbreviated, togglable)", TAG_ITEM_CALCULATED_IAS_ABBREVIATED_TOGGLABLE);
this->RegisterTagItemType("Calculated Mach", TAG_ITEM_CALCULATED_MACH);
this->RegisterTagItemType("Calculated Mach (togglable)", TAG_ITEM_CALCULATED_MACH_TOGGLABLE);

this->RegisterTagItemFunction("Open reported IAS menu", TAG_FUNC_OPEN_REPORTED_IAS_MENU);
this->RegisterTagItemFunction("Clear reported IAS", TAG_FUNC_CLEAR_REPORTED_IAS);
this->RegisterTagItemFunction("Toggle calculated IAS", TAG_FUNC_TOGGLE_CALCULATED_IAS);
this->RegisterTagItemFunction("Toggle calculated IAS (abbreviated)", TAG_FUNC_TOGGLE_CALCULATED_IAS_ABBREVIATED);
this->RegisterTagItemFunction("Open reported Mach menu", TAG_FUNC_OPEN_REPORTED_MACH_MENU);
this->RegisterTagItemFunction("Clear reported Mach", TAG_FUNC_CLEAR_REPORTED_MACH);
this->RegisterTagItemFunction("Toggle calculated Mach", TAG_FUNC_TOGGLE_CALCULATED_MACH);
Expand Down Expand Up @@ -327,18 +219,28 @@ void IASsure::IASsure::ClearReportedIAS(const EuroScopePlugIn::CFlightPlan& fp)
this->reportedIAS.erase(fp.GetCallsign());
}

void IASsure::IASsure::ToggleCalculatedIAS(const EuroScopePlugIn::CFlightPlan& fp)
void IASsure::IASsure::ToggleCalculatedIAS(const EuroScopePlugIn::CFlightPlan& fp, bool abbreviated)
{
std::string cs = fp.GetCallsign();
if (this->calculatedIASToggled.contains(cs)) {
this->calculatedIASToggled.erase(cs);
if (abbreviated) {
if (this->calculatedIASToggled.contains(cs)) {
this->calculatedIASToggled.erase(cs);
}
else {
this->calculatedIASToggled.insert(cs);
}
}
else {
this->calculatedIASToggled.insert(cs);
if (this->calculatedIASAbbreviatedToggled.contains(cs)) {
this->calculatedIASAbbreviatedToggled.erase(cs);
}
else {
this->calculatedIASAbbreviatedToggled.insert(cs);
}
}
}

void IASsure::IASsure::CalculateIAS(const EuroScopePlugIn::CRadarTarget& rt, char tagItemContent[16], int* tagItemColorCode, COLORREF* tagItemRGB)
void IASsure::IASsure::CalculateIAS(const EuroScopePlugIn::CRadarTarget& rt, char tagItemContent[16], int* tagItemColorCode, COLORREF* tagItemRGB, bool abbreviated)
{
if (!rt.IsValid()) {
return;
Expand All @@ -357,11 +259,19 @@ void IASsure::IASsure::CalculateIAS(const EuroScopePlugIn::CRadarTarget& rt, cha
}

std::ostringstream tag;
tag << "I";
if (!abbreviated) {
tag << "I";
}
tag << std::setfill('0');

auto it = this->reportedIAS.find(rt.GetCallsign());
if (it == this->reportedIAS.end()) {
tag << std::setfill('0') << std::setw(3) << std::round(cas);
if (abbreviated) {
tag << std::setw(2) << std::round(cas / 10.0);
}
else {
tag << std::setw(3) << std::round(cas);
}
}
else {
double diff = it->second - cas;
Expand All @@ -372,7 +282,12 @@ void IASsure::IASsure::CalculateIAS(const EuroScopePlugIn::CRadarTarget& rt, cha
tag << "-";
}

tag << std::setfill('0') << std::setw(3) << std::round(std::abs(diff));
if (abbreviated) {
tag << std::setw(2) << std::round(std::abs(diff / 10.0));
}
else {
tag << std::setw(3) << std::round(std::abs(diff));
}
}

strcpy_s(tagItemContent, 16, tag.str().c_str());
Expand Down Expand Up @@ -457,17 +372,14 @@ void IASsure::IASsure::LoadSettings()
if (settings) {
std::vector<std::string> splitSettings = ::IASsure::split(settings, SETTINGS_DELIMITER);

if (splitSettings.size() < 4) {
if (splitSettings.size() < 1) {
this->LogMessage("Invalid saved settings found, reverting to default.");

this->SaveSettings();
return;
}

std::istringstream(splitSettings[0]) >> this->debug;
std::istringstream(splitSettings[1]) >> this->minReportedIAS;
std::istringstream(splitSettings[2]) >> this->maxReportedIAS;
std::istringstream(splitSettings[3]) >> this->intervalReportedIAS;

this->LogDebugMessage("Successfully loaded settings.");
}
Expand All @@ -479,10 +391,7 @@ void IASsure::IASsure::LoadSettings()
void IASsure::IASsure::SaveSettings()
{
std::ostringstream ss;
ss << this->debug << SETTINGS_DELIMITER
<< this->minReportedIAS << SETTINGS_DELIMITER
<< this->maxReportedIAS << SETTINGS_DELIMITER
<< this->intervalReportedIAS;
ss << this->debug;

this->SaveDataToSettings(PLUGIN_NAME, "Settings", ss.str().c_str());
}
Expand Down
11 changes: 3 additions & 8 deletions IASsure/IASsure.h
Original file line number Diff line number Diff line change
Expand Up @@ -27,23 +27,18 @@ namespace IASsure {

private:
bool debug;
int minReportedIAS;
int maxReportedIAS;
int intervalReportedIAS;
std::unordered_map<std::string, int> reportedIAS;
std::unordered_set<std::string> calculatedIASToggled;
int minReportedMach;
int maxReportedMach;
int intervalReportedMach;
std::unordered_set<std::string> calculatedIASAbbreviatedToggled;
std::unordered_map<std::string, double> reportedMach;
std::unordered_set<std::string> calculatedMachToggled;

void RegisterTagItems();

void SetReportedIAS(const EuroScopePlugIn::CFlightPlan& fp, std::string selected);
void ClearReportedIAS(const EuroScopePlugIn::CFlightPlan& fp);
void ToggleCalculatedIAS(const EuroScopePlugIn::CFlightPlan& fp);
void CalculateIAS(const EuroScopePlugIn::CRadarTarget& rt, char tagItemContent[16], int* tagItemColorCode, COLORREF* tagItemRGB);
void ToggleCalculatedIAS(const EuroScopePlugIn::CFlightPlan& fp, bool abbreviated = false);
void CalculateIAS(const EuroScopePlugIn::CRadarTarget& rt, char tagItemContent[16], int* tagItemColorCode, COLORREF* tagItemRGB, bool abbreviated = false);

void SetReportedMach(const EuroScopePlugIn::CFlightPlan& fp, std::string selected);
void ClearReportedMach(const EuroScopePlugIn::CFlightPlan& fp);
Expand Down
Loading

0 comments on commit 4f850c6

Please sign in to comment.