So im making a compass in node-red, it should have course in degrees (int) as input and string(course) as output:
So i need function that takes in integer and gives me heading in string. How to do it simple and reliable?
I have to convert course 0-360 degrees in string for example: NORTH, NORTH-EAST, EAST......
I tried the following:
var course = parseInt(courseFloatDegrees);
var courseTxt = "";
if (course >= 349 && course <= 11 || course <= 359 && course >= 349 || course === 0) courseTxt = "N";
else if (course >= 11 && course <= 33) courseTxt = "NNE";
else if (course >= 33 && course <= 56) courseTxt = "NE";
else if (course >= 56 && course <= 78) courseTxt = "ENE";
else if (course >= 78 && course <= 101 || course == 90) courseTxt = "E";
else if (course >= 101 && course <= 124) courseTxt = "ESE";
else if (course >= 124 && course <= 146) courseTxt = "SE";
else if (course >= 146 && course <= 168) courseTxt = "SSE";
else if (course >= 168 && course <= 191 || course == 180) courseTxt = "S";
else if (course >= 191 && course <= 214) courseTxt = "SSW";
else if (course >= 214 && course <= 236) courseTxt = "SW";
else if (course >= 236 && course <= 258) courseTxt = "WSW";
else if (course >= 258 && course <= 281 || course == 270) courseTxt = "W";
else if (course >= 281 && course <= 303) courseTxt = "WNW";
else if (course >= 303 && course <= 326) courseTxt = "NW";
else if (course >= 326 && course <= 349) courseTxt = "NNW";
else courseTxt = "INVALID"
But sometimes i get nothing(null-empty string) or "INVALID". Does anybody know fast and simple way to do this without that much else if statements?
There could be ways of doing this more 'simply' in code, but your approach should work. The reason it doesn't is because your if statements are messed up around the 'N' region.
if ((course >= 349 && course <= 11) || (course <= 359 && course >= 349) || (course === 0)) courseTxt = "N";
If you look at the very first two conditions, they are illogical. More than 349 but less than 11? That's never going to happen. If you have a course of 7 degrees, that doesn't meet any of the specified criteria currently.
So the first thing to do is resolve that problem. You need to adjust the line to use OR instead of AND
if(course < 11 || course > 349) courseTxt = "N";
Now your code will be able to handle the settings either side of 360/0 degrees.
That should be enough to get your current code to work, assuming course is always less or equal to 360.
You asked if there is a way to avoid all the if statements. There are probably hundreds of ways to do this, but the simplest, other than if or case statements would probably be to use an array to look up the heading. Here is an example of how it could be done. You could obviously hardcode the step value, but this way you could update your array with any number of more granular headings, and it will still work.e
function getCourse(course)
{
// define our values
var degs = 360;
var strs =
["N","NNE","NE","ENE","E","ESE","SE","SSE","S","SSW","SW","WSW","W","WNW","NW","NNW"];
// make sure course is always within the expected range in case it is incremented past 360
course = course % degs;
// get the step amount based on the number of compass headings we have
var step = degs/strs.length;
// adjust for the last few degrees on the scale which will be north
if(course > degs - (step/2)) course += step/2;
// now just divide the course by the step and read off the relevant heading
var index = Math.floor(course / step);
return strs[index];
}