Widget HTML ipxv5

Bonjour , je n’ai pas vu d’explications sur ce widget , qui pourrait me dire à quoi cela sert ?

Merci

Bonsoir @artnow ,
Ce widget peut vous permettre par exemple de créer vos propres widgets customisés :wink:

1 « J'aime »

Bonsoir,

Vous avez un bon exemple de ce que ce widget permet de faire ici :

Image + texte dynamique en fonction de l’état d’un relais (de mémoire l’image ne fonctionne qu’après une modification)

Tout le contenu du widget est simplement ajouté à la page de votre dashboard : celà permet d’utiliser l’api rest pour contrôler la v5, d’afficher des données dynamiques, etc…
Attention juste si vous essayez de dupliquer ce widget, il faudra mettre à jour les identifiants.

2 « J'aime »

J’en profite pour vous partager l’exemple de François que j’ai modifié pour:

  • corriger l’icône quand le garage est fermé
  • corriger le changement d’icône ouvert/fermé qui ne fonctionnait pas pour moi (Firefox)
  • Inclure le tout dans un iframe ce qui permet de dupliquer le Widget sans avoir à changer le nom des fonctions et des ID des éléments HTML. Ça permet de transposer à une autre porte très facilement.

→ Proposition d’amélioration pour les Widgets HTML @GCE: inclure le code HTML dans un iframe par défaut et y ajouter tous les styles automatiquement (gce-color-styles, gce-glyph.min, etc…)

Il n’y a qu’à modifier la clef API

<iframe srcdoc='
    <link rel="stylesheet" href="assets/lib/gce-glyph/gce-glyph.min.css">
    <script type="text/javascript">
      /* Get state and set widget */
      function init() {
        let lockColor,
            lockIcon,
            stateMsg;
        
        getState((ipx) => {
          let garageState = ipx.ioRelayState[0]; // Isolated relay state
          
          if (garageState == "off") {
            lockColor = "#FF0000"; // red
            lockIcon = "icon-lock-open_security";
            stateMsg = "Porte ouverte";
          } else if (garageState == "on") {
            lockColor = "#32CD32";  // green
            lockIcon = "icon-lock_security";
            stateMsg = "Porte fermée";
          }
          
          setIcon(lockIcon, lockColor);
          setMessage(stateMsg, lockColor);
          setState(garageState, lockColor);
        });
      }
      /***/
      
      /* Get data from API */
      function getState(cb) {
        fetch("/api/system/ipx?ApiKey=API_KEY", {method: "GET"}).then((ret) => { // Get IPX object
          ret.json().then((ipx) => {
            cb(ipx); // Return IPX state from API
          });
        });
      }
      /***/
      
      /* Set icon and color */
      function setIcon(icon, color) {
        let myIcon = document.getElementById("myIcon");
        myIcon.style.color = color;
        myIcon.className = "";
        myIcon.classList.add("gce-glyph");
        myIcon.classList.add(icon);
      }
      /***/
      
      /* Set state message */
      function setMessage(text, color) {
        let msg = document.getElementById("myStateMsg");
        msg.style.color = color;
        msg.innerHTML = text;
      }
      /***/
      
      /* Set garage state */
      function setState(text, color) {
        let garage = document.getElementById("myGarageState");
        garage.style.color = color;
        garage.innerHTML = text;
      }
      /***/
      
      /* Auto refresh (optional) */
      function autoRefresh() {
        setInterval(() => {
          init();
        }, 1000); // 1 sec
      }
      /***/
      
      init();
      autoRefresh(); // Optional
    </script>
    
    <table width="100%" style="padding: 10px">
      <tr style="display: flex; align-item: center; justify-content: space-between">
        <!--Icon -->
        <td>
          <i id="myIcon" class="gce-glyph"></i>
        </td>
        <!---->
        
        <!-- State message -->
        <td>
          <span id="myStateMsg" style="font-size: 15px"></span>
        </td>
        <!---->
        
        <!-- Garage state -->
        <td>
          <span id="myGarageState" style="font-size: 15px;"></span>
        </td>
        <!---->
      </tr>
    </table>
'></iframe>
3 « J'aime »

Bonjour,
Je cherche un moyen de créer un widget html pour afficher les valeurs multiples d’une ana8.
Cette ana8 qui est associée à un objet lecture modbus peut prendre plusieurs valeurs dont chaqu’une représente un état.
Par exemple la valeur 0 correspond à OFF, 6 correspond à chauffage ON…ainsi de suite.
J’aimerais pouvoir afficher ces états avec un seul widget et utiliser les icônes de la V5 pour les représenter.
Est ce que quelqu’un peut me mettre sur la piste avec un début de code à intégrer dans un widget html?
Merci

Bonjour,
J’ai tenté d’adapter le code donné par @fgtoul un peu plus haut en adaptant la requête à la valeur ana.

/* Get data from API */
  function getState(cb) {
    fetch("/api/core/ana/196656?ApiKey=monAPIKEY", {method: "GET"}).then((ret) => { // Get IPX object
      ret.json().then((ipx) => {
        cb(ipx); // Return IPX state from API

Par contre, comme j’ai donné l’ID de mon ana, je doit mettre quoi à la place de:

let garageState = ipx.ioRelays[0]; // Isolated relay state

Je ne trouve pas d’où sort ipx.ioRelays

Bonjour @patam ,

Voici un exemple de widget html qui

  1. Récupère tout le groupe de données ANA
  2. Extrait la variable Analog voulue en utilisant son ID (facilement modifiable pour chercher par le nom de la variable plutôt que par l’ID)
  3. Affiche le nom de la variable Analog
  4. Affiche texte/icône/couleur selon la valeur de la variable (un bon gros switch case)
    ça montre comment gérer si l’ID recherché n’existe pas
    ça ne « gère » que 3 valeurs possibles, mais ça se modifie facilement

Voici ma variable Ana8 créée pour l’exemple
2022-01-16 16_14_04-IPX-800-V5 — Mozilla Firefox
Et un aperçu du dashboard d’exemple
2022-01-16 16_14_54-IPX-800-V5 — Mozilla Firefox

Voici le contenu du widget html
    <link rel="stylesheet" href="assets/lib/gce-glyph/gce-glyph.min.css">
    <script type="text/javascript">

      let anaId = 196741;
      
      /* Get state and set widget */
      function updateData() {
        let dataColor,
            dataIcon,
            dataText,
            titleText;
        
        getAna((ana) => {
          const anaFound = ana.find( analog => analog._id === anaId);
          if (undefined == anaFound) {
            dataColor = "#FF0000"; // red
            dataIcon = "icon-circle-remove";
            dataText = "ANA id = " + anaId + " non trouvée"
            titleText = "Erreur"
          } else {
            switch (anaFound.value) {
              case 0: // value = 0
                dataColor = "#32CD32";  // green
                dataIcon = "icon-lamp_light";
                dataText = "Valeur 0"
                break;
              case 1: // value = 1
                dataColor = "#32CD32";  // green
                dataIcon = "icon-lamp2_light";
                dataText = "Valeur 1"
                break;
              case 2: // value = 2
                dataColor = "#32CD32";  // green
                dataIcon = "icon-lamp4_light";
                dataText = "Valeur 2"
                break;
              default: // Any other value
                dataColor = "#FF7C00"; // orange
                dataIcon = "icon-circle-question";
                dataText = "Valeur = " + anaFound.value + " non définie";
              }
              titleText = anaFound.name;
          }
          
          setIcon(dataIcon, dataColor);
          setText(dataText, dataColor);
          setTitle(titleText);
        });
      }
      /***/
      
      /* Get data from API */
      function getAna(cb) {
        fetch("/api/core/ana?ApiKey=API_KEY", {method: "GET"}).then((ret) => { // Get ANA group
          ret.json().then((ana) => {
            cb(ana); // Return ANA group from API
          });
        });
      }
      /***/
      
      /* Set icon and color */
      function setIcon(icon, color) {
        let myIcon = document.getElementById("myIcon");
        myIcon.style.color = color;
        myIcon.className = "";
        myIcon.classList.add("gce-glyph");
        myIcon.classList.add(icon);
      }
      /***/
      
      /* Set text and color */
      function setText(text, color) {
        let msg = document.getElementById("myDataText");
        msg.style.color = color;
        msg.innerHTML = text;
      }
      /***/
      
      /* Set title */
      function setTitle(text) {
        let msg = document.getElementById("myTitle");
        msg.innerHTML = text;
      }
      /***/
      
      /* Auto refresh (optional) */
      function autoRefresh() {
        setInterval(() => {
          updateData();
        }, 1000); // 1 sec
      }
      /***/
      
      updateData();
      autoRefresh(); // Optional
    </script>
    
    <table width="100%" style="padding: 10px">
      <thead>
        <tr>
          <!-- Title -->
          <th colspan="2">
            <span id="myTitle" style="font-size: 15px; text-align:center"></span>
          </th>
          <!---->
        </tr>
      </thead>
      <tbody>
        <tr style="display: flex; align-item: center; justify-content: space-between">
          <!-- Icon -->
          <td>
            <i id="myIcon" class="gce-glyph"></i>
          </td>
          <!---->

          <!-- Text -->
          <td>
            <span id="myDataText" style="font-size: 15px"></span>
          </td>
          <!---->
        </tr>
      </tbody>
    </table>

Et pour finir le dashboard exemple Exemple_ANA8.zip (2,2 Ko)
Pour tester il faudra adapter l’ID de la variable et comme d’habitude l’API_KEY.

Bon week-end !

2 « J'aime »

Merci beaucoup @jbbeauf !!
J’étais loin du résultat… :rofl:
J’ai trouvé comment supprimer le titre, le message avec la valeur… même si je pense qu’il y a mieux que de mettre // devant les lignes…
Par contre j’arrive à augmenter la taille de l’icone mais je n’arrive pas à la centrer dans la tuile.

    <link rel="stylesheet" href="assets/lib/gce-glyph/gce-glyph.min.css">
    <script type="text/javascript">

      let anaId = 196656;
      
      /* Get state and set widget */
      function updateData() {
        let dataColor,
            dataIcon,
            dataText,
            titleText;
        
        getAna((ana) => {
          const anaFound = ana.find( analog => analog._id === anaId);
          if (undefined == anaFound) {
            dataColor = "#FF0000"; // red
            dataIcon = "icon-circle-remove";
            dataText = "ANA id = " + anaId + " non trouvée"
            titleText = "Erreur"
          } else {
            switch (anaFound.value) {
              case 0: // value = 0
                dataColor = "#32CD32";  // green
                dataIcon = "icon-lamp_light";
                dataText = "Valeur 0"
                break;
              case 1: // value = 1
                dataColor = "#32CD32";  // green
                dataIcon = "icon-lamp2_light";
                dataText = "Valeur 1"
                break;
              case 2: // value = 2
                dataColor = "#32CD32";  // green
                dataIcon = "icon-lamp4_light";
                dataText = "Valeur 2"
                break;
              case 3: // value = 3
                dataColor = "#32CD32";  // green
                dataIcon = "icon-lamp4_light";
                dataText = "Valeur 2"
                break;
              default: // Any other value
                dataColor = "#FF7C00"; // orange
                dataIcon = "icon-circle-question";
                dataText = "Valeur = " + anaFound.value + " non définie";
              }
              titleText = anaFound.name;
          }
          
          setIcon(dataIcon, dataColor);
          //setText(dataText, dataColor);
          //setTitle(titleText);
        });
      }
      /***/
      
      /* Get data from API */
      function getAna(cb) {
        fetch("/api/core/ana?ApiKey=monapikey", {method: "GET"}).then((ret) => { // Get ANA group
          ret.json().then((ana) => {
            cb(ana); // Return ANA group from API
          });
        });
      }
      /***/
      
      /* Set icon and color */
      function setIcon(icon, color) {
        let myIcon = document.getElementById("myIcon");
        myIcon.style.color = color;
        myIcon.className = "";
        myIcon.classList.add("gce-glyph");
        myIcon.classList.add(icon);
      }
      /***/
      
      /* Set text and color */
      function setText(text, color) {
        let msg = document.getElementById("myDataText");
        msg.style.color = color;
        msg.innerHTML = text;
      }
      /***/
      
      /* Set title */
      function setTitle(text) {
        let msg = document.getElementById("myTitle");
        msg.innerHTML = text;
      }
      /***/
      
      /* Auto refresh (optional) */
      function autoRefresh() {
        setInterval(() => {
          updateData();
        }, 1000); // 1 sec
      }
      /***/
      
      updateData();
      autoRefresh(); // Optional
    </script>
    
    <table width="100%" style="padding: 10px">
      <thead>
        <tr>
          <!-- Title -->
          <th colspan="2">
            <span id="myTitle" style="font-size: 15px; text-align:center"></span>
          </th>
          <!---->
        </tr>
      </thead>
      <tbody>
        <tr style="display: flex; align-item: center; justify-content: space-between">
          <!-- Icon -->
          <td>
            <i id="myIcon" class="gce-glyph" style="font-size: 40px"></i>
          </td>
          <!---->

          <!-- Text -->
          <td>
            <span id="myDataText" style="font-size: 15px"></span>
          </td>
          <!---->
        </tr>
      </tbody>
    </table>

De rien @patam

Il vaut mieux supprimer tout ce qui ne sert à rien dans le widget: appel de fonction, fonction elle même, éléments graphiques etc… ça pendra moins de place en mémoire dans le dashboard.

Il ne reste que l’icône après avoir tout supprimé :sweat_smile:
Voici ce que ça donne en supprimant tout l’objet < table > et en ne gardant que l’icône agrandie
image

   .......
      updateData();
      autoRefresh(); // Optional
    </script>
<i id="myIcon" class="gce-glyph" style="font-size:48px"></i>
1 « J'aime »

Bonjour,
Merci encore pour votre aide, j’ai finalement gardé le nom pour plus de lisibilité.

image

image

C’est top!

1 « J'aime »

Bonjour,
Ça ne fonctionne pas chez moi,
Vous avez changer seulement les infos : ID & API_KEY ?
Merci

Bonjour,
Attention à rafraichir votre navigateur quand vous faites des changements dans le widget html. Sinon, oui j’ai juste adapté l’ID et l’Apikey.

Merci pour cette information…
Je vais essayer de faire un widget pour mon eco-device avec les conso… et si j’y arrive je déposerai mon code
:grin:

2 « J'aime »

Bonjour,
Je reviens sur ce fil car j’ai tenté d’ajouter plusieurs widget html sur un dashboard mais de ce que j’ai compris, il faut soit changer les id soit mettre le code dans un iframe.
Je pense que le plus simple est d’utiliser la balise iframe, mais je n’y arrive pas…
N’étant pas spécialiste du code, je vous le mets pour que les connaisseurs y jettent un coup d’oeil!

Merci pour votre aide

<iframe srcdoc='
<link rel="stylesheet" href="assets/lib/gce-glyph/gce-glyph.min.css">
    <script type="text/javascript">

      let anaId = 262250;
      
      /* Get state and set widget */
      function updateData() {
        let dataColor,
            dataIcon;

        getAna((ana) => {
          const anaFound = ana.find( analog => analog._id === anaId);
          if (undefined == anaFound) {
            dataColor = "#FF0000"; // red
            dataIcon = "icon-circle-remove"

          } else {
            switch (anaFound.value) {
              case 0: // value = 0
                dataColor = "#666565";  // grey
                dataIcon = "icon-power_power"
                break;
              case 1: // value = 1
                dataColor = "#666565";  // grey
                dataIcon = "icon-fan_power"
                break;
              case 2: // value = 2
                dataColor = "#32CD32";  // green
                dataIcon = "icon-fan_power"
                break;
              case 3: // value = 2
                dataColor = "#32CD32";  // green
                dataIcon = "icon-lamp4_light"
                break;   
              default: // Any other value
                dataColor = "#FF7C00"; // orange
                dataIcon = "icon-circle-question"
              }
              
          }
          
          setIcon(dataIcon, dataColor);

        });
      }
      /***/
      
      /* Get data from API */
      function getAna(cb) {
        fetch("/api/core/ana?ApiKey=ulmWrsx0QvdoWvH", {method: "GET"}).then((ret) => { // Get ANA group
          ret.json().then((ana) => {
            cb(ana); // Return ANA group from API
          });
        });
      }
      /***/
      
      /* Set icon and color */
      function setIcon(icon, color) {
        let myIcon = document.getElementById("myIcon");
        myIcon.style.color = color;
        myIcon.className = "";
        myIcon.classList.add("gce-glyph");
        myIcon.classList.add(icon);
      }
 
      /***/

      /* Auto refresh (optional) */
      function autoRefresh() {
        setInterval(() => {
          updateData();
        }, 5000); // 5 sec
      }
      /***/
      
      updateData();
      autoRefresh(); // Optional
    </script>
    
    <i id="myIcon" class="gce-glyph" style="font-size:48px"></i>
    '></iframe>

Bonjour,
il faut retarder l’exécution de la fonction updateData comme ceci

setTimeout(() => {updateData();}, 50)

bonne journée

Bonjour @fgtoul,

C’est à mettre où?
Le problème c’est que mon code ne semble plus reconnu comme tel lorsque jele place dans le iframe. Sur mon post, il y a plusieurs couleur dans le code, mais sur l’éditeur de l’IPX le code est d’une seule couleur.

dans le code, il faut remplacer

 updateData();
 autoRefresh(); // Optional

par

setTimeout(() => {updateData();}, 50)
autoRefresh(); // Optional

l’éditeur de l’ipx a raison de supprimer les couleurs du code, car avec l’iframe, le code devient une simple chaine de caractères entre 2 apostrophes (srcdoc='').
Discourse (le forum) applique une coloration syntaxique qui n’a pas lieu d’être car le javascript n’est pas reconnu (code non précisé derrière la chaîne ```)
En précisant le type de code, la coloration du texte devient correcte.
Modif faite dans votre message.

Merci pour votre aide.
Ci-dessous le code corrigé, mais le widget ne fonction pas avec l’ajout du iframe.

<iframe srcdoc='
<link rel="stylesheet" href="assets/lib/gce-glyph/gce-glyph.min.css">
    <script type="text/javascript">

      let anaId = 262258;
      
      /* Get state and set widget */
      function updateData() {
        let dataColor,
            dataIcon;

        getAna((ana) => {
          const anaFound = ana.find( analog => analog._id === anaId);
          if (undefined == anaFound) {
            dataColor = "#FF0000"; // red
            dataIcon = "icon-circle-remove"

          } else {
            switch (anaFound.value) {
              case 0: // value = 0
                dataColor = "#666565";  // grey
                dataIcon = "icon-power_power"
                break;
              case 1: // value = 1
                dataColor = "#666565";  // grey
                dataIcon = "icon-fan_power"
                break;
              case 2: // value = 2
                dataColor = "#32CD32";  // green
                dataIcon = "icon-fan_power"
                break;
              case 3: // value = 3
                dataColor = "#32CD32";  // green
                dataIcon = "icon-lamp4_light"
                break;   
              default: // Any other value
                dataColor = "#FF7C00"; // orange
                dataIcon = "icon-circle-question"
              }
              
          }
          
          setIcon(dataIcon, dataColor);

        });
      }
      /***/
      
      /* Get data from API */
      function getAna(cb) {
        fetch("/api/core/ana?ApiKey=ulmWrsx0QvdoWvH", {method: "GET"}).then((ret) => { // Get ANA group
          ret.json().then((ana) => {
            cb(ana); // Return ANA group from API
          });
        });
      }
      /***/
      
      /* Set icon and color */
      function setIcon(icon, color) {
        let myIcon = document.getElementById("myIcon");
        myIcon.style.color = color;
        myIcon.className = "";
        myIcon.classList.add("gce-glyph");
        myIcon.classList.add(icon);
      }
 
      /***/

      /* Auto refresh (optional) */
      function autoRefresh() {
        setInterval(() => {
          updateData();
        }, 5000); // 5 sec
        
      }
      /***/
      
      setTimeout(() => {updateData();}, 50)
      autoRefresh(); // Optional
    </script>
    
    <i id="myIcon" class="gce-glyph" style="font-size:48px"></i>
    '></iframe>

vous avez essayé le widget en taille 2x2 ?
perso j’obtiens bien un affichage, mais décalé. Il y a un un peu de css à faire.
Je n’ai pas vos valeurs analogiques, je ne peux donc pas dire si ce que j’obtiens est normal.

voici un code qui fonctionne :

<iframe srcdoc='
<link rel="stylesheet" href="assets/lib/gce-glyph/gce-glyph.min.css">
    <script type="text/javascript">

      let anaId = 262258;
      
      /* Get state and set widget */
      function updateData() {
        let dataColor,
            dataIcon;

        getAna((ana) => {
          const anaFound = ana.find( analog => analog._id === anaId);
          if (undefined == anaFound) {
            dataColor = "#FF0000"; // red
            dataIcon = "icon-circle-remove"

          } else {
            switch (anaFound.value) {
              case 0: // value = 0
                dataColor = "#666565";  // grey
                dataIcon = "icon-power_power"
                break;
              case 1: // value = 1
                dataColor = "#666565";  // grey
                dataIcon = "icon-fan_power"
                break;
              case 2: // value = 2
                dataColor = "#32CD32";  // green
                dataIcon = "icon-fan_power"
                break;
              case 3: // value = 2
                dataColor = "#32CD32";  // green
                dataIcon = "icon-lamp4_light"
                break;   
              default: // Any other value
                dataColor = "#FF7C00"; // orange
                dataIcon = "icon-circle-question"
              }
              
          }
          
          setIcon(dataIcon, dataColor);

        });
      }
      /***/
      
      /* Get data from API */
      function getAna(cb) {
        fetch("/api/core/ana?ApiKey=ulmWrsx0QvdoWvH", {method: "GET"}).then((ret) => { // Get ANA group
          ret.json().then((ana) => {
            cb(ana); // Return ANA group from API
          });
        });
      }
      /***/
      
      /* Set icon and color */
      function setIcon(icon, color) {
        let myIcon = document.getElementById("myIcon");
        myIcon.style.color = color;
        myIcon.className = "";
        myIcon.classList.add("gce-glyph");
        myIcon.classList.add(icon);
      }
 
      /***/

      /* Auto refresh (optional) */
      function autoRefresh() {
        setInterval(() => {
          updateData();
        }, 5000); // 5 sec
      }
      /***/
      setTimeout(() => {updateData();}, 50)
 
      autoRefresh(); // Optional
    </script>
    <center>
    <div style="width:100px;font-size:48px;padding:30px">
    <span id="myIcon" class="gce-glyph" ></span></div>
    </center>
    '></iframe>

image

2 « J'aime »