Calcul angle moyen avec itérations non listés

Pour toutes les discussions javascript, jQuery et autres frameworks
Avatar du membre
Frosty
Messages : 123
Enregistré le : 20 juil. 2017, 13:23
Localisation : Grenoble

Re: Calcul angle moyen avec itérations non listés

Message par Frosty » 25 mars 2018, 21:59

Pour convertir des valeurs de type chaine (ex."-50°") en entiers (ex. -50), un appel a parseInt(maVariable, 10) devrait faire le job
Je te suggère fortement au passage de mettre le 2eme paramètre aux appels à parseInt() qui se trouvent déjà dans ton code.

Je ne vois pas de fonction twaCalc() ? Ou est elle définie et appelée ?

GeGaX
Messages : 26
Enregistré le : 20 févr. 2018, 21:56

Re: Calcul angle moyen avec itérations non listés

Message par GeGaX » 26 mars 2018, 00:20

Salut Frosty,
Merci pour le

Code : Tout sélectionner

parseInt
, je m'obstinais à vouloir supprimer le " ° " et ensuite à convertir la chaine en entier avec

Code : Tout sélectionner

parseInt
Vu et corrigé pour la base 10, merci ;)
Je te mets le code de popup.js au complet

Code : Tout sélectionner

var background = chrome.extension.getBackgroundPage();

function createCell(value, row) {
    var cell = document.createElement("td");
    cell.innerHTML = value;
    row.appendChild(cell);
}

function ttwStyling(value, cell) {
    cell.align = "left";
    cell.innerHTML = value;
}

function dtwStyling(value, cell) {
    cell.align = "left";
    cell.innerHTML = value;
}

function dtgStyling(value, cell) {
    cell.align = "left";
    cell.innerHTML = value;
}

function twsStyling(value1, value2, cell) {
    var tws_foil = value1.replace(" kt", "");
    var twa_bd = value2.replace("\u00B0", "");
    if (tws_foil >= 11.1 && tws_foil <= 39.9 && Math.abs(twa_bd) >= 71 && Math.abs(twa_bd) <= 169) {
        cell.style.backgroundColor = "black";
        cell.style.color = "white";
    } else {
        cell.style.backgroundColor = "white";
        cell.style.color = "black";
    }
    cell.innerHTML = tws_foil + " kt";
}

function twaStyling(value, cell) {
    var twa_bd = value.replace("\u00B0", "");
    if (twa_bd >= 0) {
        cell.style.color = "green";
    } else {
        cell.style.color = "red";
    }
    cell.innerHTML = Math.abs(twa_bd) + "\u00B0";
}

function btwStyling(value, cell) {
    cell.style.color = "blue";
    cell.innerHTML = value;
}

function sailStyling(value, cell) {
    switch (value.trim()) {
    // Upwind sail
    case "Jib":
        cell.style.backgroundColor = "#FFD479";
        break;
    case "LJ":
        cell.style.backgroundColor = "#FFFC79";
        break;
    case "Stay":
        cell.style.backgroundColor = "#D4FB79";
        break;
    // Downwind sail
    case "Spi":
        cell.style.backgroundColor = "#76D6FF";
        break;
    case "LG":
        cell.style.backgroundColor = "#7A81FF";
        break;
    case "HG":
        cell.style.backgroundColor = "#D783FF";
        break;
    // Reaching sail
    case "C0":
        cell.style.backgroundColor = "#FF7E79";
        break;
    }
    cell.innerHTML = value;
}

/*
function twamStyling(value, cell) {
    if (value >= 0) {
        cell.style.color = "green";
    } else {
        cell.style.color = "red";
    }
    if (value !== "-") {
        cell.innerHTML = Math.abs(value) + "\u00B0";
    } else {
        cell.style.color = "black";
        cell.innerHTML = value;
    }
}
*/

/*
function btwmStyling(value, cell) {
    cell.style.color = "blue";
    if (value !== "-") {
        cell.innerHTML = value + "\u00B0";
    } else {
        cell.style.color = "black";
        cell.innerHTML = value;
    }
}
*/

function createCellWithCustomStyling(value, row, customStyling) {
    var cell = document.createElement("td");
    customStyling(value, cell);
    row.appendChild(cell);
}

function createCellWithCustomStyling2(value1, value2, row, customStyling) {
    var cell = document.createElement("td");
    customStyling(value1, value2, cell);
    row.appendChild(cell);
}

//Nouveau calcul twam ( calcul trigo )
/*
var twaList = [];

function twamCalc() {
    const
    twaData = twaList;
    Math.radians = function (degrees) {
        return degrees * Math.PI / 180.0;
    },
    Math.degrees = function (radians) {
        return radians * 180.0 / Math.PI;
    };
 
    let
    arX = [],
    arY = [],
    somX = 0.0,
    somY = 0.0,
    moyX = 0.0,
    moyY = 0.0,
    twam = 0.0;
    
    for (const [i, angle] of twaData.entries()) {
        arX[i] = Math.cos(Math.radians(angle));
        arY[i] = Math.sin(Math.radians(angle));
    }
 
    for (const value of arX) {
	   somX += value;
    }
    moyX = somX / arX.length;
 
    for (const value of arY) {
	   somY += value;
    }
    moyY = somY / arY.length;
 
    twam = Math.round((Math.degrees(Math.atan2(moyY, moyX)) * 10)) / 10;
 
    return twam;
}
*/

//Nouveau calcul btwm ( calcul trigo )
/*
var btwList = [];

function btwmCalc() {
    const
    btwData = btwList;
    Math.radians = function (degrees) {
        return degrees * Math.PI / 180.0;
    },
    Math.degrees = function (radians) {
        return radians * 180.0 / Math.PI;
    };
 
    let
    arX = [],
    arY = [],
    somX = 0.0,
    somY = 0.0,
    moyX = 0.0,
    moyY = 0.0,
    btwm = 0.0;
 
    for (const [i, angle] of btwData.entries()) {
        arX[i] = Math.cos(Math.radians(angle));
        arY[i] = Math.sin(Math.radians(angle));
    }
 
    for (const value of arX) {
	   somX += value;
    }
    moyX = somX / arX.length;
 
    for (const value of arY) {
	   somY += value;
    }
    moyY = somY / arY.length;
 
    btwm = Math.round((Math.degrees(Math.atan2(moyY, moyX)) * 10)) / 10;
    if (btwm < 0) {
        btwm += 360
    }
    return btwm;
}
*/

function reinitializeDisplay() {
    document.getElementById("pointsTable").innerHTML = "";
}

function UtcToLocal(date, time) {
    var utcYear = date.split("-")[0];
    var utcMonth = (date.split("-")[1]) - 1;
    var utcDay = date.split("-")[2];
    var utcHour = time.split(":")[0];
    var utcMinutes = time.split(":")[1];
    var dateUtc = Date.UTC(utcYear, utcMonth, utcDay, utcHour, utcMinutes, 0, 0);
    
    var localDate = new Date(dateUtc);
    var year = localDate.getFullYear();
    var month = ("0" + (localDate.getMonth() + 1)).slice(-2);
    var day = ("0" + localDate.getDate()).slice(-2);
    var hours = ("0" + localDate.getHours()).slice(-2);
    var minutes = ("0" + localDate.getMinutes()).slice(-2);

    var offset = -localDate.getTimezoneOffset();
    var absOffset = Math.abs(offset);
    var sign = (offset > 0) ? "+" : "-";
    var hoursOffset = Math.trunc(absOffset) / 60;
    var MinutesHoursOffset = (hoursOffset === 0) ? "\u00b1" + "0" : sign + hoursOffset;
    var minutesOffset = absOffset % 60;
    var HoursMinutesOffset = (minutesOffset === 0) ? MinutesHoursOffset : sign + hoursOffset + ":" + minutesOffset;

    var formattedDate = year + "-" + month + "-" + day;
    var formattedTime = hours + ":" + minutes;
    var formattedTimeZone = "UTC" + HoursMinutesOffset;
    return [formattedDate, formattedTime, formattedTimeZone];
}

function getTimeZone(timezone) {
    if (timezone === "CET") {
        return "UTC+1";
    } else if (timezone === "CEST") {
        return "UTC+2";
    }
}

function displayTable(localTime) {
    points.forEach(function (element) {
        var row = document.createElement("tr");
        document.getElementById("pointsTable").appendChild(row);
        if ((localTime && element.timezone === "CET") || (localTime && element.timezone === "CEST")) {
            var ceZ = getTimeZone(element.timezone);
            createCell(element.date, row);
            createCell(element.time, row);
            createCell(ceZ, row);
        } else if (localTime && element.timezone === "UTC") {
            var localDTZ = UtcToLocal(element.date, element.time, element.timezone);
            createCell(localDTZ[0], row);
            createCell(localDTZ[1], row);
            createCell(localDTZ[2], row);
        } else {
            createCell(element.date, row);
            createCell(element.time, row);
            createCell(element.timezone, row);
        }
        createCellWithCustomStyling(element.ttw, row, ttwStyling);
        createCellWithCustomStyling(element.dtw, row, dtwStyling);
        createCellWithCustomStyling(element.dtg, row, dtgStyling);
        createCell(element.twd, row);
        createCellWithCustomStyling2(element.tws, element.twa, row, twsStyling);
        createCellWithCustomStyling(element.twa, row, twaStyling);
        createCellWithCustomStyling(element.btw, row, btwStyling);
        createCellWithCustomStyling(element.sail, row, sailStyling);
        createCell(element.stw, row);
        //createCellWithCustomStyling(twam, row, twamStyling);
        //createCellWithCustomStyling(btwm, row, btwmStyling);
        var manifest = chrome.runtime.getManifest();
        document.getElementById("version").innerHTML = manifest.version;
    });
}

var displayLocal = function () {
    reinitializeDisplay();
    if (document.getElementById("localtime").checked) {
        chrome.storage.local.set({"localTime" : true});
        displayTable(true);
    } else {
        chrome.storage.local.set({"localTime" : false});
        displayTable(false);
    }
};

document.getElementById("localtime").addEventListener("change", displayLocal);

chrome.storage.local.get("localTime", function (result) {
    if (result.localTime === true) {
        document.getElementById("localtime").checked = true;
        displayLocal();
    } else {
        document.getElementById("localtime").checked = false;
    }
});
reinitializeDisplay();
var points = background.points[background.currentTab];
displayTable(false);

var myMap = new Map();
var ttwLast = "T+ 0:00";
var twaLast = null;
var btwLast = null;
var twaList = [];
var btwList = [];

function space(val) {
    if (val < 10) {
        val = " " + val;
    }
    return val;
}

function zero(val) {
    if (val < 10) {
        val = "0" + val;
    }
    return val;
}

function genIteNext (ttwCurr) {
    var ttwCurr = ttwCurr.match(/.*?([0-9]{1,3}):([0-9]{2})/);
    var ttwHours = parseInt(ttwCurr[1], 10);
    var ttwMinutes = parseInt(ttwCurr[2], 10);
    var ttwNext = [];
    if (ttwMinutes + 10 < 60) {
        ttwNext = "T+" + space (ttwHours) + ":" + zero (ttwMinutes + 10);
    } else {
        ttwNext = "T+" + space (ttwHours + 1) + ":" + zero (ttwMinutes - 50);
    }
    return ttwNext;
}

for (var i = 0; i < points.length; i++) {
    while (points[i].ttw !== ttwLast) {
        myMap.set (ttwLast, {twa : twaLast, btw : btwLast} );
        ttwLast = genIteNext(ttwLast);
        if (twaList.length !== 0) {
            if (parseInt(twaLast, 10) * parseInt(twaList[0], 10) < 0) {
                twaList = [];
            }
        }
        twaList.push(twaLast);
    }
    ttwLast = points[i].ttw;
    twaLast = parseInt(points[i].twa, 10);
    btwLast = parseInt(points[i].btw, 10);
    myMap.set(points[i].ttw, {twa : points[i].twa, btw : points[i].btw} );
}
console.log(twaList);
console.log(myMap);
Mais ça fonctionne pas mon truc :evil: ( ça aurait été trop beau évidement )

Je pensais que ça me générerais un tableau qui s'incrémenterait à chaque tour de boucle mais nan il n'y a qu'une valeur twa a chaque fois ...

Avatar du membre
Frosty
Messages : 123
Enregistré le : 20 juil. 2017, 13:23
Localisation : Grenoble

Re: Calcul angle moyen avec itérations non listés

Message par Frosty » 27 mars 2018, 10:36

Ok j'ai essayé de comprendre un peu le code de popup.js

SI je comprends bien :
- la variable "points" contient uniquement les données des lignes à afficher
- la boucle "for" sur ce tableau "points", que tu as créée à la fin du fichier, est censée te "sortir" dans la variable "myMap" toutes les données (même celles non listées). Apparemment on prend toujours la "prochaine" valeur de twa et btw disponible dans "points" pour compléter les lignes manquantes.

Logiquement l'appel à displayTable() devrait être fait après la boucle for sur le tableau "points".

Dans la boucle "for" après le "while" en fait on traite chaque ligne à afficher
Logiquement tu dois pouvoir ajouter quelque chose dans le style :

Code : Tout sélectionner

points[i].twam = twamCalc(twaList);
points[i].btwm = btwmCalc(btwList);
Et au lieu de

Code : Tout sélectionner

function twamCalc() {
    const
    twaData = twaList;
tu aurais simplement

Code : Tout sélectionner

function twamCalc(twaData) {
(de manière générale, c'est un peu plus sûr de passer des paramètres que de faire appel à des variables globales)

Voilà, en mettant des console.log() pour voir ce qui se passe aux endroits stratégiques ça devrait te permettre de pas mal avancer.

Si je ne me trompe pas, tu auras seulement besoin de twaList et btwList dans la boucle "for" pour les calculs de TWAm et BTWm. Tu peux donc virer toutes les lignes avec "myMap", je crois qu'au final elles ne serviront à rien ;)

GeGaX
Messages : 26
Enregistré le : 20 févr. 2018, 21:56

Re: Calcul angle moyen avec itérations non listés

Message par GeGaX » 28 mars 2018, 23:16

Salut Frosty ;),
Frosty a écrit :
27 mars 2018, 10:36
SI je comprends bien :
- la variable "points" contient uniquement les données des lignes à afficher
- la boucle "for" sur ce tableau "points", que tu as créée à la fin du fichier, est censée te "sortir" dans la variable "myMap" toutes les données (même celles non listées). Apparemment on prend toujours la "prochaine" valeur de twa et btw disponible dans "points" pour compléter les lignes manquantes.
# Oui, la variable "points" contient les données, extraites des instructions listées du code source, et seront affichées dans un tableau html.
Ici aucun calcul juste des modifications d'affichages.
- TWS => couleur de fond noire, couleur de police blanche : indique que les foils sont actifs.
- TWA => rouge : valeur de TWA négative (vent venant de la gauche - bâbord), vert : valeur TWA positive (vent venant de la droite - tribord).
- BTW => bleu : uniquement pour le rendre plus lisible et facilement identifiable.
- Sail => Plusieurs couleurs de fond : uniquement pour mettre en avant un changement de voile.

# Oui, la boucle "for" sur la variable points me permet de créer un nouveau tableau (pour l'instant c'est plutôt une map) en complétant les itérations manquantes.
Je prends un exemple simple
TTW = T+ 0:00, TWA = -150° (donc 150° rouge car négatif).
TTW = T+ 0:10, TWA = -145° (idem que ci dessus).
TTW = T+ 0:30, TWA = -149° (//).
Ici on remarque qu'il manque une itération (T+ 0:20) et contrairement à ce que tu as marqué ci dessus j'attribue pas la valeur de suivante ( donc celle de T+ 0:30) mais la valeur précedente (celle de T+ 0:10) soit TTW = T+ 0:20, TWA = -145°.
Frosty a écrit :
27 mars 2018, 10:36
Logiquement l'appel à displayTable() devrait être fait après la boucle for sur le tableau "points".
J'y avais pensé mais un forumeur est parti de ce tableau points, si je modifie "l'emplacement" mon code ne fonctionnera pas puisque la variable "points" ne sera pas encore déclarée, il me faudrait donc modifier ce code (ça je peux y réfléchir, je devrais en être capable - enfin j'espère ...)
Frosty a écrit :
27 mars 2018, 10:36
Dans la boucle "for" après le "while" en fait on traite chaque ligne à afficher
Logiquement tu dois pouvoir ajouter quelque chose dans le style :

Code : Tout sélectionner

points[i].twam = twamCalc(twaList);
points[i].btwm = btwmCalc(btwList);
Et au lieu de

Code : Tout sélectionner

function twamCalc() {
    const
    twaData = twaList;
tu aurais simplement

Code : Tout sélectionner

function twamCalc(twaData) {
Ça je capte, tu crée les "points" twam et btwm en leurs attribuant leurs fonctions respectives.
Frosty a écrit :
27 mars 2018, 10:36
(de manière générale, c'est un peu plus sûr de passer des paramètres que de faire appel à des variables globales)
Là tu me perds, on m'a déjà fait la remarque, sauf que dans mon bouquin (le JS pour les nuls - et oui des fois c'est mieux le bouquin qu'internet alors j'en ai pris un à la hauteur de mes connaissances...) les histoires de paramètres et variables globales, ben c'est pas expliqué ...
Frosty a écrit :
27 mars 2018, 10:36
Voilà, en mettant des console.log() pour voir ce qui se passe aux endroits stratégiques ça devrait te permettre de pas mal avancer.
Je commence à faire connaissance avec console.log(), c'est très pratique encore faut il savoir le placer correctement.
C'est grâce à lui que j'ai détecté que mon formatage de sortie de la fonction "genIteNext", n'était pas bon et j'ai donc pu corriger le tir.
Frosty a écrit :
27 mars 2018, 10:36
Si je ne me trompe pas, tu auras seulement besoin de twaList et btwList dans la boucle "for" pour les calculs de TWAm et BTWm. Tu peux donc virer toutes les lignes avec "myMap", je crois qu'au final elles ne serviront à rien ;)
Au fur et à mesure que mon code avance, j'ai eu cette réflexion, mais le forumeur m'a dit de garder la map ...
Au final je suis pas sur qu'on pense à la même finalité, surement du à de mauvaises explications de ma part.

Avatar du membre
Frosty
Messages : 123
Enregistré le : 20 juil. 2017, 13:23
Localisation : Grenoble

Re: Calcul angle moyen avec itérations non listés

Message par Frosty » 30 mars 2018, 11:42

Ici on remarque qu'il manque une itération (T+ 0:20) et contrairement à ce que tu as marqué ci dessus j'attribue pas la valeur de suivante ( donc celle de T+ 0:30) mais la valeur précedente (celle de T+ 0:10) soit TTW = T+ 0:20, TWA = -145°.
Ok. C'est bien ce que j'avais compris mais je m'étais mal exprimé.
histoires de paramètres et variables globales
https://msdn.microsoft.com/fr-fr/librar ... s.94).aspx
Au final je suis pas sur qu'on pense à la même finalité, surement du à de mauvaises explications de ma part.
Si j'ai bien compris le but est de faire afficher le tableau modifié (= avec les valeurs de TWAm et TBWm en plus) par la fonction displayTable()
Pour cela je pense qu'il faut effectivement parcourir et modifier directement le tableau points comme indiqué dans mon message précédent (donc pas besoin d'une Map en plus), et que tu étais sur la bonne voie avec ceci en commentaire dans displayTable() :

Code : Tout sélectionner

        //createCellWithCustomStyling(twam, row, twamStyling);
        //createCellWithCustomStyling(btwm, row, btwmStyling); 
Je pense qu'une fois que les propriétés twam et btwm seront définies au niveau des éléments du tableau "points" tu pourras faire

Code : Tout sélectionner

        createCellWithCustomStyling(element.twam, row, twamStyling);
        createCellWithCustomStyling(element.btwm, row, btwmStyling); 
Décommenter également les méthodes twamStyling() et btwmStyling() (si ça pose trop de problème dans un 1er temps, utilise simplement createCell() au lieu de createCellWithCustomStyling()).

Voilà, en espérant ne pas me planter ;)

GeGaX
Messages : 26
Enregistré le : 20 févr. 2018, 21:56

Re: Calcul angle moyen avec itérations non listés

Message par GeGaX » 02 avr. 2018, 21:34

Salut Frosty ;),
Merci de tes conseils, j'viens de faire un ENORME pas en avant aujourd'hui, tout n'est pas comme je le souhaite mais j'obtiens mes valeurs dans mon tableau :D
Ça fait quelques semaines que ça n'était pas arrivé ... du coup je suis hyper content j'commençais à desespérer

Voici le popup.js testé

Code : Tout sélectionner

var background = chrome.extension.getBackgroundPage();

function createCell(value, row) {
    var cell = document.createElement("td");
    cell.innerHTML = value;
    row.appendChild(cell);
}

function ttwStyling(value, cell) {
    cell.align = "left";
    cell.innerHTML = value;
}

function dtwStyling(value, cell) {
    cell.align = "left";
    cell.innerHTML = value;
}

function dtgStyling(value, cell) {
    cell.align = "left";
    cell.innerHTML = value;
}

function twsStyling(value1, value2, cell) {
    var tws_foil = value1.replace(" kt", "");
    var twa_bd = value2.replace("\u00B0", "");
    if (tws_foil >= 11.1 && tws_foil <= 39.9 && Math.abs(twa_bd) >= 71 && Math.abs(twa_bd) <= 169) {
        cell.style.backgroundColor = "black";
        cell.style.color = "white";
    } else {
        cell.style.backgroundColor = "white";
        cell.style.color = "black";
    }
    cell.innerHTML = tws_foil + " kt";
}

function twaStyling(value, cell) {
    var twa_bd = value.replace("\u00B0", "");
    if (twa_bd >= 0) {
        cell.style.color = "green";
    } else {
        cell.style.color = "red";
    }
    cell.innerHTML = Math.abs(twa_bd) + "\u00B0";
}

function btwStyling(value, cell) {
    cell.style.color = "blue";
    cell.innerHTML = value;
}

function sailStyling(value, cell) {
    switch (value.trim()) {
    // Upwind sail
    case "Jib":
        cell.style.backgroundColor = "#FFD479";
        break;
    case "LJ":
        cell.style.backgroundColor = "#FFFC79";
        break;
    case "Stay":
        cell.style.backgroundColor = "#D4FB79";
        break;
    // Downwind sail
    case "Spi":
        cell.style.backgroundColor = "#76D6FF";
        break;
    case "LG":
        cell.style.backgroundColor = "#7A81FF";
        break;
    case "HG":
        cell.style.backgroundColor = "#D783FF";
        break;
    // Reaching sail
    case "C0":
        cell.style.backgroundColor = "#FF7E79";
        break;
    }
    cell.innerHTML = value;
}

function twamStyling(value, cell) {
    if (value >= 0) {
        cell.style.color = "green";
    } else {
        cell.style.color = "red";
    }
    if (value !== "-") {
        cell.innerHTML = Math.abs(value) + "\u00B0";
    } else {
        cell.style.color = "black";
        cell.innerHTML = value;
    }
}

function btwmStyling(value, cell) {
    cell.style.color = "blue";
    if (value !== "-") {
        cell.innerHTML = value + "\u00B0";
    } else {
        cell.style.color = "black";
        cell.innerHTML = value;
    }
}

function createCellWithCustomStyling(value, row, customStyling) {
    var cell = document.createElement("td");
    customStyling(value, cell);
    row.appendChild(cell);
}

function createCellWithCustomStyling2(value1, value2, row, customStyling) {
    var cell = document.createElement("td");
    customStyling(value1, value2, cell);
    row.appendChild(cell);
}

function twamCalc(twaList) {
    const
    twaData = twaList;
    Math.radians = function (degrees) {
        return degrees * Math.PI / 180.0;
    },
    Math.degrees = function (radians) {
        return radians * 180.0 / Math.PI;
    };
 
    let
    arX = [],
    arY = [],
    somX = 0.0,
    somY = 0.0,
    moyX = 0.0,
    moyY = 0.0,
    twam = 0.0;
    
    for (const [i, angle] of twaData.entries()) {
        arX[i] = Math.cos(Math.radians(angle));
        arY[i] = Math.sin(Math.radians(angle));
    }
 
    for (const value of arX) {
	   somX += value;
    }
    moyX = somX / arX.length;
 
    for (const value of arY) {
	   somY += value;
    }
    moyY = somY / arY.length;
    
    twam = Math.round(Math.degrees(Math.atan2(moyY, moyX)));
    
    return twam ;
}

function btwmCalc(btwList) {
    const
    btwData = btwList;
    Math.radians = function (degrees) {
        return degrees * Math.PI / 180.0;
    },
    Math.degrees = function (radians) {
        return radians * 180.0 / Math.PI;
    };
 
    let
    arX = [],
    arY = [],
    somX = 0.0,
    somY = 0.0,
    moyX = 0.0,
    moyY = 0.0,
    btwm = 0.0;
 
    for (const [i, angle] of btwData.entries()) {
        arX[i] = Math.cos(Math.radians(angle));
        arY[i] = Math.sin(Math.radians(angle));
    }
 
    for (const value of arX) {
	   somX += value;
    }
    moyX = somX / arX.length;
 
    for (const value of arY) {
	   somY += value;
    }
    moyY = somY / arY.length;
    
    btwm = Math.round(Math.degrees(Math.atan2(moyY, moyX)));
    if (btwm < 0) {
        btwm += 360;
    }
    return btwm;
}

function reinitializeDisplay() {
    document.getElementById("pointsTable").innerHTML = "";
}

function UtcToLocal(date, time) {
    var utcYear = date.split("-")[0];
    var utcMonth = (date.split("-")[1]) - 1;
    var utcDay = date.split("-")[2];
    var utcHour = time.split(":")[0];
    var utcMinutes = time.split(":")[1];
    var dateUtc = Date.UTC(utcYear, utcMonth, utcDay, utcHour, utcMinutes, 0, 0);
    
    var localDate = new Date(dateUtc);
    var year = localDate.getFullYear();
    var month = ("0" + (localDate.getMonth() + 1)).slice(-2);
    var day = ("0" + localDate.getDate()).slice(-2);
    var hours = ("0" + localDate.getHours()).slice(-2);
    var minutes = ("0" + localDate.getMinutes()).slice(-2);

    var offset = -localDate.getTimezoneOffset();
    var absOffset = Math.abs(offset);
    var sign = (offset > 0) ? "+" : "-";
    var hoursOffset = Math.trunc(absOffset) / 60;
    var MinutesHoursOffset = (hoursOffset === 0) ? "\u00b1" + "0" : sign + hoursOffset;
    var minutesOffset = absOffset % 60;
    var HoursMinutesOffset = (minutesOffset === 0) ? MinutesHoursOffset : sign + hoursOffset + ":" + minutesOffset;

    var formattedDate = year + "-" + month + "-" + day;
    var formattedTime = hours + ":" + minutes;
    var formattedTimeZone = "UTC" + HoursMinutesOffset;
    return [formattedDate, formattedTime, formattedTimeZone];
}

function getTimeZone(timezone) {
    if (timezone === "CET") {
        return "UTC+1";
    } else if (timezone === "CEST") {
        return "UTC+2";
    }
}

function displayTable(localTime) {
    points.forEach(function (element) {
        var row = document.createElement("tr");
        document.getElementById("pointsTable").appendChild(row);
        if ((localTime && element.timezone === "CET") || (localTime && element.timezone === "CEST")) {
            var ceZ = getTimeZone(element.timezone);
            createCell(element.date, row);
            createCell(element.time, row);
            createCell(ceZ, row);
        } else if (localTime && element.timezone === "UTC") {
            var localDTZ = UtcToLocal(element.date, element.time, element.timezone);
            createCell(localDTZ[0], row);
            createCell(localDTZ[1], row);
            createCell(localDTZ[2], row);
        } else {
            createCell(element.date, row);
            createCell(element.time, row);
            createCell(element.timezone, row);
        }
        createCellWithCustomStyling(element.ttw, row, ttwStyling);
        createCellWithCustomStyling(element.dtw, row, dtwStyling);
        createCellWithCustomStyling(element.dtg, row, dtgStyling);
        createCell(element.twd, row);
        createCellWithCustomStyling2(element.tws, element.twa, row, twsStyling);
        createCellWithCustomStyling(element.twa, row, twaStyling);
        createCellWithCustomStyling(element.btw, row, btwStyling);
        createCellWithCustomStyling(element.sail, row, sailStyling);
        createCell(element.stw, row);
        createCellWithCustomStyling(element.twam, row, twamStyling);
        createCellWithCustomStyling(element.btwm, row, btwmStyling);
        var manifest = chrome.runtime.getManifest();
        document.getElementById("version").innerHTML = manifest.version;
    });
}

var displayLocal = function () {
    reinitializeDisplay();
    if (document.getElementById("localtime").checked) {
        chrome.storage.local.set({"localTime" : true});
        displayTable(true);
    } else {
        chrome.storage.local.set({"localTime" : false});
        displayTable(false);
    }
};

document.getElementById("localtime").addEventListener("change", displayLocal);

chrome.storage.local.get("localTime", function (result) {
    if (result.localTime === true) {
        document.getElementById("localtime").checked = true;
        displayLocal();
    } else {
        document.getElementById("localtime").checked = false;
    }
});
reinitializeDisplay();
var points = background.points[background.currentTab];
displayTable(false);

var twaList = [];
var btwList = [];
var ttwLast = "T+ 0:00";
var twaLast = undefined;
var btwLast = undefined;

function space(val) {
    if (val < 10) {
        val = " " + val;
    }
    return val;
}

function zero(val) {
    if (val < 10) {
        val = "0" + val;
    }
    return val;
}

function genIteNext (ttwCurr) {
    var ttwCurr = ttwCurr.match(/.*?([0-9]{1,3}):([0-9]{2})/);
    var ttwHours = parseInt(ttwCurr[1], 10);
    var ttwMinutes = parseInt(ttwCurr[2], 10);
    var ttwNext = [];
    if (ttwMinutes + 10 < 60) {
        ttwNext = "T+" + space (ttwHours) + ":" + zero (ttwMinutes + 10);
    } else {
        ttwNext = "T+" + space (ttwHours + 1) + ":" + zero (ttwMinutes - 50);
    }
    return ttwNext;
}

for (var i = 0; i < points.length; i++) {
    while (points[i].ttw !== ttwLast) {
        twaList.push(parseInt(twaLast,10));
        btwList.push(parseInt(btwLast,10));
        ttwLast = genIteNext(ttwLast);
        points[i].twam = twamCalc(twaList);
        points[i].btwm = btwmCalc(btwList);
    }
    twaLast = parseInt(points[i].twa, 10);
    btwLast = parseInt(points[i].btw, 10);
    if (twaList.length === 0) {
        twaList.push(twaLast);
        btwList.push(btwLast);
    } else if (twaList[0] * twaLast < 0) {
        twaList = [twaLast];
        btwList = [btwLast];
    } else {
        twaList.push(twaLast);
        btwList.push(btwLast);
    }
    ttwLast = genIteNext(ttwLast);
    points[i].twam = twamCalc(twaList);
    points[i].btwm = btwmCalc(btwList);
}
Mes 2 soucis résiduels, et oui c'est pas encore parfait...

# Au premier clic sur l'extension j'obtiens que des NaN° et undefined°
Image
Au second clic, j'obtiens ceci
Image

Je pense que ça se trouve dans l'organisation de mon code, tout est placé à la fin de popup.js concernant la création des itérations manquantes et la génération de twaList et btwList pour les fonctions twamCalc et btwmCalc qui elles se trouvent au milieu du code global ainsi que l'affichage du tableau html
J'veux bien des conseils là dessus.

# Mon second soucis, est que je n'ai pas le décalage dont j'ai besoin
sur la ligne T+ 0:00 je dois obtenir (pour twam et btwm) " - " (un tiret) car je suis déja sur ce point donc pas de valeur, la ligne suivante quand à elle doit avoir les valeurs twam et btwm que j'obtiens actuellement pour la ligne T+ 0:00
soit

Code : Tout sélectionner

point[i].ttw correspond aux valeurs points[i-1].twam / points[i-1].btwm
J'suis également preneur de conseils pour mettre ça en oeuvre.

Je tiens le bon bout après de nombreux soir à me mettre le cerveau en ébullition donc je lâche rien ;)

Avatar du membre
Frosty
Messages : 123
Enregistré le : 20 juil. 2017, 13:23
Localisation : Grenoble

Re: Calcul angle moyen avec itérations non listés

Message par Frosty » 02 avr. 2018, 22:55

Réponse rapide depuis mon mobile, je m'excuse d'avance pour le manque de mise en forme...

Content que tu aies bien avancé ;)

Concernant les NaN et undefined au 1er clic, cela vient du fait que displayTable() devrait être appelé après la boucle for qui va calculer / enregistrer les valeurs de twam et btwm dans le tableau points.
Sinon cela revient à afficher le tableau avec les 2 nouvelles colonnes sans avoir les valeurs.

Concernant le décalage du début, je regarde demain depuis mon PC, mais je peux déjà dire que les 2 lignes

Code : Tout sélectionner

points[i].twam = twamCalc(...)
points[i].btwm = btwmCalc(...) 
situées dans le "while" me font peur ;)

Avatar du membre
Frosty
Messages : 123
Enregistré le : 20 juil. 2017, 13:23
Localisation : Grenoble

Re: Calcul angle moyen avec itérations non listés

Message par Frosty » 03 avr. 2018, 13:42

Rectification : ces lignes ne me font pas peur, c'est juste qu'elles me paraissent inutiles

Je tenterais bien ceci pour ta boucle for (+ while) de calcul des points

Code : Tout sélectionner

for (var i = 0; i < points.length; i++) {
    // d'abord on modifie twam/btwm avec les données précédemment récupérées (s'il y en a)
    points[i].twam = twamCalc(twaList);
    points[i].btwm = btwmCalc(btwList);
    // ensuite on remplit twaList / btwList autant que nécessaire
    while (points[i].ttw !== ttwLast) {
        twaList.push(parseInt(twaLast,10));
        btwList.push(parseInt(btwLast,10));
        ttwLast = genIteNext(ttwLast);
    }
    twaLast = parseInt(points[i].twa, 10);
    btwLast = parseInt(points[i].btw, 10);
    if (twaList[0] * twaLast < 0) {
        twaList = [twaLast];
        btwList = [btwLast];
    } else {
        twaList.push(twaLast);
        btwList.push(btwLast);
    }
    ttwLast = genIteNext(ttwLast);
}
Par contre pas sûr que twamCalc() et btwmCalc() réagissent bien lorsqu'on leur fournit un tableau vide en paramètre
A voir dans un console.log() ce qu'elles retournent et adapter l'affichage en conséquence :-)

GeGaX
Messages : 26
Enregistré le : 20 févr. 2018, 21:56

Re: Calcul angle moyen avec itérations non listés

Message par GeGaX » 03 avr. 2018, 22:34

Salut Frosty ;)
Merci grâce à toi j'ai résolu 2 des 3 points résiduels (décalage de ligne, calcul faussé), il me reste juste l'histoire du chargement au premier clic pas au second ...

voici le popup.js complet

Code : Tout sélectionner

var background = chrome.extension.getBackgroundPage();
var twaList = [];
var btwList = [];
var ttwLast = "T+ 0:00";
var twaLast = undefined;
var btwLast = undefined;

function createCell(value, row) {
    var cell = document.createElement("td");
    cell.innerHTML = value;
    row.appendChild(cell);
}

function ttwStyling(value, cell) {
    cell.align = "left";
    cell.innerHTML = value;
}

function dtwStyling(value, cell) {
    cell.align = "left";
    cell.innerHTML = value;
}

function dtgStyling(value, cell) {
    cell.align = "left";
    cell.innerHTML = value;
}

function twsStyling(value1, value2, cell) {
    var tws_foil = value1.replace(" kt", "");
    var twa_bd = value2.replace("\u00B0", "");
    if (tws_foil >= 11.1 && tws_foil <= 39.9 && Math.abs(twa_bd) >= 71 && Math.abs(twa_bd) <= 169) {
        cell.style.backgroundColor = "black";
        cell.style.color = "white";
    } else {
        cell.style.backgroundColor = "white";
        cell.style.color = "black";
    }
    cell.innerHTML = tws_foil + " kt";
}

function twaStyling(value, cell) {
    var twa_bd = value.replace("\u00B0", "");
    if (twa_bd >= 0) {
        cell.style.color = "green";
    } else {
        cell.style.color = "red";
    }
    cell.innerHTML = Math.abs(twa_bd) + "\u00B0";
}

function btwStyling(value, cell) {
    cell.style.color = "blue";
    cell.innerHTML = value;
}

function sailStyling(value, cell) {
    switch (value.trim()) {
    // Upwind sail
    case "Jib":
        cell.style.backgroundColor = "#FFD479";
        break;
    case "LJ":
        cell.style.backgroundColor = "#FFFC79";
        break;
    case "Stay":
        cell.style.backgroundColor = "#D4FB79";
        break;
    // Downwind sail
    case "Spi":
        cell.style.backgroundColor = "#76D6FF";
        break;
    case "LG":
        cell.style.backgroundColor = "#7A81FF";
        break;
    case "HG":
        cell.style.backgroundColor = "#D783FF";
        break;
    // Reaching sail
    case "C0":
        cell.style.backgroundColor = "#FF7E79";
        break;
    }
    cell.innerHTML = value;
}

function twamStyling(value, cell) {
    if (value >= 0) {
        cell.style.color = "green";
    } else {
        cell.style.color = "red";
    }
    if (value !== "-") {
        cell.innerHTML = Math.abs(value) + "\u00B0";
    } else {
        cell.style.color = "black";
        cell.innerHTML = value;
    }
}

function btwmStyling(value, cell) {
    cell.style.color = "blue";
    if (value !== "-") {
        cell.innerHTML = value + "\u00B0";
    } else {
        cell.style.color = "black";
        cell.innerHTML = value;
    }
}

function createCellWithCustomStyling(value, row, customStyling) {
    var cell = document.createElement("td");
    customStyling(value, cell);
    row.appendChild(cell);
}

function createCellWithCustomStyling2(value1, value2, row, customStyling) {
    var cell = document.createElement("td");
    customStyling(value1, value2, cell);
    row.appendChild(cell);
}

function twamCalc(twaList) {
    const
    twaData = twaList;
    Math.radians = function (degrees) {
        return degrees * Math.PI / 180.0;
    },
    Math.degrees = function (radians) {
        return radians * 180.0 / Math.PI;
    };
 
    let
    arX = [],
    arY = [],
    somX = 0.0,
    somY = 0.0,
    moyX = 0.0,
    moyY = 0.0,
    twam = 0.0;
    
    for (const [i, angle] of twaData.entries()) {
        arX[i] = Math.cos(Math.radians(angle));
        arY[i] = Math.sin(Math.radians(angle));
    }
 
    for (const value of arX) {
	   somX += value;
    }
    moyX = somX / arX.length;
 
    for (const value of arY) {
	   somY += value;
    }
    moyY = somY / arY.length;
    
    twam = Math.round((Math.degrees(Math.atan2(moyY, moyX)) * 10)) / 10;
    if (isNaN (twam)) {
        twam = "-";
    }
    return twam ;
}

function btwmCalc(btwList) {
    const
    btwData = btwList;
    Math.radians = function (degrees) {
        return degrees * Math.PI / 180.0;
    },
    Math.degrees = function (radians) {
        return radians * 180.0 / Math.PI;
    };
 
    let
    arX = [],
    arY = [],
    somX = 0.0,
    somY = 0.0,
    moyX = 0.0,
    moyY = 0.0,
    btwm = 0.0;
 
    for (const [i, angle] of btwData.entries()) {
        arX[i] = Math.cos(Math.radians(angle));
        arY[i] = Math.sin(Math.radians(angle));
    }
 
    for (const value of arX) {
	   somX += value;
    }
    moyX = somX / arX.length;
 
    for (const value of arY) {
	   somY += value;
    }
    moyY = somY / arY.length;
    
    btwm = Math.round((Math.degrees(Math.atan2(moyY, moyX)) * 10))/ 10;
    if (isNaN (btwm)) {
        btwm = "-";
    } else if (btwm < 0) {
        btwm += 360;
    }
    return btwm;
}

function reinitializeDisplay() {
    document.getElementById("pointsTable").innerHTML = "";
}

function UtcToLocal(date, time) {
    var utcYear = date.split("-")[0];
    var utcMonth = (date.split("-")[1]) - 1;
    var utcDay = date.split("-")[2];
    var utcHour = time.split(":")[0];
    var utcMinutes = time.split(":")[1];
    var dateUtc = Date.UTC(utcYear, utcMonth, utcDay, utcHour, utcMinutes, 0, 0);
    
    var localDate = new Date(dateUtc);
    var year = localDate.getFullYear();
    var month = ("0" + (localDate.getMonth() + 1)).slice(-2);
    var day = ("0" + localDate.getDate()).slice(-2);
    var hours = ("0" + localDate.getHours()).slice(-2);
    var minutes = ("0" + localDate.getMinutes()).slice(-2);

    var offset = -localDate.getTimezoneOffset();
    var absOffset = Math.abs(offset);
    var sign = (offset > 0) ? "+" : "-";
    var hoursOffset = Math.trunc(absOffset) / 60;
    var MinutesHoursOffset = (hoursOffset === 0) ? "\u00b1" + "0" : sign + hoursOffset;
    var minutesOffset = absOffset % 60;
    var HoursMinutesOffset = (minutesOffset === 0) ? MinutesHoursOffset : sign + hoursOffset + ":" + minutesOffset;

    var formattedDate = year + "-" + month + "-" + day;
    var formattedTime = hours + ":" + minutes;
    var formattedTimeZone = "UTC" + HoursMinutesOffset;
    return [formattedDate, formattedTime, formattedTimeZone];
}

function getTimeZone(timezone) {
    if (timezone === "CET") {
        return "UTC+1";
    } else if (timezone === "CEST") {
        return "UTC+2";
    }
}

function displayTable(localTime) {
    points.forEach(function (element) {
        var row = document.createElement("tr");
        document.getElementById("pointsTable").appendChild(row);
        if ((localTime && element.timezone === "CET") || (localTime && element.timezone === "CEST")) {
            var ceZ = getTimeZone(element.timezone);
            createCell(element.date, row);
            createCell(element.time, row);
            createCell(ceZ, row);
        } else if (localTime && element.timezone === "UTC") {
            var localDTZ = UtcToLocal(element.date, element.time, element.timezone);
            createCell(localDTZ[0], row);
            createCell(localDTZ[1], row);
            createCell(localDTZ[2], row);
        } else {
            createCell(element.date, row);
            createCell(element.time, row);
            createCell(element.timezone, row);
        }
        createCellWithCustomStyling(element.ttw, row, ttwStyling);
        createCellWithCustomStyling(element.dtw, row, dtwStyling);
        createCellWithCustomStyling(element.dtg, row, dtgStyling);
        createCell(element.twd, row);
        createCellWithCustomStyling2(element.tws, element.twa, row, twsStyling);
        createCellWithCustomStyling(element.twa, row, twaStyling);
        createCellWithCustomStyling(element.btw, row, btwStyling);
        createCellWithCustomStyling(element.sail, row, sailStyling);
        createCell(element.stw, row);
        createCellWithCustomStyling(element.twam, row, twamStyling);
        createCellWithCustomStyling(element.btwm, row, btwmStyling);
        var manifest = chrome.runtime.getManifest();
        document.getElementById("version").innerHTML = manifest.version;
    });
}

var displayLocal = function () {
    reinitializeDisplay();
    if (document.getElementById("localtime").checked) {
        chrome.storage.local.set({"localTime" : true});
        displayTable(true);
    } else {
        chrome.storage.local.set({"localTime" : false});
        displayTable(false);
    }
};

document.getElementById("localtime").addEventListener("change", displayLocal);

chrome.storage.local.get("localTime", function (result) {
    if (result.localTime === true) {
        document.getElementById("localtime").checked = true;
        displayLocal();
    } else {
        document.getElementById("localtime").checked = false;
    }
});
reinitializeDisplay();
var points = background.points[background.currentTab];
displayTable(false);

function space(val) {
    if (val < 10) {
        val = " " + val;
    }
    return val;
}

function zero(val) {
    if (val < 10) {
        val = "0" + val;
    }
    return val;
}

function genIteNext (ttwCurr) {
    var ttwCurr = ttwCurr.match(/.*?([0-9]{1,3}):([0-9]{2})/);
    var ttwHours = parseInt(ttwCurr[1], 10);
    var ttwMinutes = parseInt(ttwCurr[2], 10);
    var ttwNext = [];
    if (ttwMinutes + 10 < 60) {
        ttwNext = "T+" + space (ttwHours) + ":" + zero (ttwMinutes + 10);
    } else {
        ttwNext = "T+" + space (ttwHours + 1) + ":" + zero (ttwMinutes - 50);
    }
    return ttwNext;
}

for (var i = 0; i < points.length; i++) {
    points[i].twam = twamCalc(twaList);
    points[i].btwm = btwmCalc(btwList);
    while (points[i].ttw !== ttwLast) {
        twaList.push(parseInt(twaLast,10));
        btwList.push(parseInt(btwLast,10));
        ttwLast = genIteNext(ttwLast);
    }
    twaLast = parseInt(points[i].twa, 10);
    btwLast = parseInt(points[i].btw, 10);
    if (twaList.length === 0) {
        twaList.push(twaLast);
        btwList.push(btwLast);
    } else if (twaList[0] * twaLast < 0) {
        twaList = [twaLast];
        btwList = [btwLast];
    } else {
        twaList.push(twaLast);
        btwList.push(btwLast);
    }
    ttwLast = genIteNext(ttwLast);
}
Pour adapter la ligne T+ 0:00 ou twam et btwm me retourne un NaN j'ai fait ceci

Code : Tout sélectionner

if (isNaN (twam)) { 
        twam = "-";
    }
et
if (isNaN (btwm)) {
        btwm = "-";
    }
C'est parfait et me donne ceci dans le tableau final
Image

Concernant le chargement, là je bloque ...dès que je déplace le code au dessus de la fonction displayTable il n'est plus capable de comprendre points.length j'suis vert je croyais dur comme fer que j'allais pouvoir sortir la MAJ ce soir mais nan ... J'veux bien un dernier coup de pouce

Avatar du membre
Frosty
Messages : 123
Enregistré le : 20 juil. 2017, 13:23
Localisation : Grenoble

Re: Calcul angle moyen avec itérations non listés

Message par Frosty » 03 avr. 2018, 23:33

Salut,
Pas besoin de déplacer le code au dessus de la fonction displayTable().
Je me suis peut être mal fait comprendre, c'est l'appel à cette fonction displayTable() qui doit être fait après la boucle for sur le tableau points.
Autrement dit, il devrait te suffire de déplacer la ligne

Code : Tout sélectionner

displayTable(false);
à la fin de ton fichier, pour résoudre ce dernier problème.

Répondre