Carte Lovelace pour la santé?

Oui voici :

type: custom:bar-card
entities:
  - entity: sensor.garmin_connect_total_steps
    name: Pas du jour
    icon: mdi:foot-print
max: 10000
min: 0
height: 30px
decimal: 0
positions:
  icon: inside
  name: inside
  value: inside
color_gradient:
  - "#3498db"
  - "#2ecc71"
card_mod:
  style: |
    ha-card {
      box-shadow: 10px;
      margin: 0px;
      padding: 0px;
      }
    bar-card-backgroundbar {
      border-radius: 10px;
      border: 1px solid;
      background: linear-gradient(to right, red 15%,
      orange 40%, green 75%); border-radius: 10px
       }
    bar-card-currentbar {
      background: linear-gradient(to right, red 15%,orange
      35%, yellow 60%, green 85%); clip-path: polygon(0 0, var(--bar-percent) 0,
      var(--bar-percent) 100%, 0 100%); border-radius: 10px }

C’est qu’elle carte en particulier les graphs avec les colonnes je cherche justement ça pour mon temps de chauffe etc. Depuis mon thermostat.

Je vais copier ton code, merci

c’est la carte statistics-graph (Graphique des statistiques en français).

1 « J'aime »

Hé ben dis donc que de réponses en deux jours à ma question :smiley: je pensais pas que c’était un sujet aussi actif parmi les membres :rofl:
Bon j’ai plus qu’à choisir ce qui me va le mieux parmi toutes vos propositions pour mes quelques données que j’ai (tout ce qui est pas et compagnie malheureusement je les ai toujours pas dans HA n’ayant pas réussi à interfacer Gadgetbridge avec HA :confused:

Merci pour toutes vos idées en tout cas et bonnes fêtes

Faut que je regarde de mon coté pour avoir les infos de mi fitness… pour la balance @WarC0zes a déjà donné les infos donc ça va le faire de ce coté là.

Je me suis amusé avec une autre piste, c’était aussi pour comprendre la carte dual-gauge que j’ai fait ce test.

type: custom:dual-gauge-card
name: Pas du jour
gauge_size: 200
inner_gauge_size: 130
hide_card: false
gauges:
  - entity: sensor.garmin_connect_daily_step_goal
    min: 0
    max: 15000
    unit: cible
    leds_count: 60
    led_size: 2
    smooth_transitions: true
    animation_duration: 1000
    center_shadow: true
    center_shadow_blur: 25
    center_shadow_spread: 10
    markers:
      - value: 5630
        color: "#ffeb3b"
    zones:
      - from: 0
        to: 2000
        color: "#FF0000"
        opacity: 0.3
      - from: 2000
        to: 4000
        color: "#FF7700"
        opacity: 0.4
      - from: 4001
        to: 5630
        color: "#2ACC18"
        opacity: 0.3
      - from: 5631
        to: 15000
        color: "#40FF2B"
        opacity: 0.3
  - entity: sensor.garmin_connect_total_steps
    min: 0
    max: 15000
    unit: Pas
    smooth_transitions: true
    animation_duration: 1000
    center_shadow: true
    center_shadow_blur: 25
    center_shadow_spread: 10
    decimals: 0
    leds_count: 150
    severity:
      - color: "#4caf50"
        value: 1000
      - color: "#ff9800"
        value: 3000
      - color: "#f44336"
        value: 5000
    markers:
      - value: 5630
        color: "#ffeb3b"
        label: Mini
      - value: 9000
        color: "#ffeb3b"
        label: objectif 9000
      - value: 14000
        color: "#ffeb3b"
        label: Au top 14000

1 « J'aime »

Ici tu as les infos d’objectif et ce qui reste à faire comme pas. :

image

une fois l’objectif atteins, la barre sera complète et le surplus sera quand même affiché

type: custom:bar-card
entities:
  - entity: sensor.garmin_connect_total_steps
    name: Pas du jour
    icon: mdi:foot-print
    target: sensor.garmin_connect_daily_step_goal
min: 0
max: 5630
height: 35px
decimal: 0
positions:
  icon: inside
  name: inside
  value: inside
card_mod:
  style: |
    bar-card-currentbar {
      border-radius: 10px;
      background: linear-gradient(to right, #e74c3c 0%, #f1c40f 50%, #2ecc71 100%) !important;
      clip-path: polygon(0 0, var(--bar-percent) 0, var(--bar-percent) 100%, 0 100%);
    }
    bar-card-backgroundbar {
      border-radius: 10px;
      background: rgba(255,255,255,0.1) !important;
    }
    /* Injection du texte personnalisé (Objectif et Reste) */
    bar-card-value::after {
      content: " / {{ states('sensor.garmin_connect_daily_step_goal') }} (Reste: {{ states('sensor.garmin_connect_daily_step_goal') | int - states('sensor.garmin_connect_total_steps') | int }})";
      font-size: 1em;
      opacity: 0.8;
      margin-left: 5px;
    }
    ha-card {
      --bar-card-max: {{ states('sensor.garmin_connect_daily_step_goal') }};
    }

A priori custom:bar-card n’est plus maintenu mais elle peut se faire sans difficulté avec une custom:button-card (avec un peu plus de lignes de code :grin:)

3 « J'aime »

A tester :smiley:

type: custom:button-card
entity: sensor.garmin_connect_total_steps
show_name: true
show_icon: true
name: Pas du jour
icon: mdi:foot-print

# Variables pour centraliser les calculs
variables:
  goal: >
    [[[ return parseInt(states['sensor.garmin_connect_daily_step_goal'].state) || 0 ]]]
  steps: >
    [[[ return parseInt(states['sensor.garmin_connect_total_steps'].state) || 0 ]]]
  percent: >
    [[[ 
      let p = (parseInt(states['sensor.garmin_connect_total_steps'].state) / parseInt(states['sensor.garmin_connect_daily_step_goal'].state)) * 100;
      return Math.min(p, 100); 
    ]]]
  reste: >
    [[[ 
      let r = parseInt(states['sensor.garmin_connect_daily_step_goal'].state) - parseInt(states['sensor.garmin_connect_total_steps'].state);
      return r > 0 ? r : 0;
    ]]]

styles:
  grid:
    - grid-template-areas: '"i n" "bar bar"'
    - grid-template-columns: min-content 1fr
    - grid-template-rows: auto auto
  card:
    - padding: 15px
    - border-radius: 15px
  img_cell:
    - justify-self: start
    - width: 30px
  name:
    - justify-self: start
    - font-weight: bold
    - font-size: 1.1em
  custom_fields:
    bar:
      - background: rgba(255, 255, 255, 0.1)
      - border-radius: 10px
      - height: 35px
      - margin-top: 12px
      - width: 100%
      - position: relative
      - overflow: hidden

custom_fields:
  bar: >
    [[[
      /* L'astuce du background-size permet de ne voir que la partie du dégradé correspondant au pourcentage actuel */
      return `
        <div style="
          width: ${variables.percent}%;
          height: 100%;
          background: linear-gradient(to right, #e74c3c 0%, #f1c40f 50%, #2ecc71 100%);
          background-size: ${100 / (variables.percent / 100)}% 100%;
          border-radius: 10px;
          transition: width 0.8s ease-in-out;
        ">
        </div>
        <div style="
          position: absolute;
          top: 0;
          left: 10px;
          height: 100%;
          display: flex;
          align-items: center;
          font-size: 0.9em;
          font-weight: 600;
          color: white;
          text-shadow: 1px 1px 3px rgba(0,0,0,0.7);
          pointer-events: none;
          white-space: nowrap;
        ">
          ${variables.steps} / ${variables.goal} 
          <span style="opacity: 0.8; margin-left: 8px; font-weight: 400;">
            (Reste: ${variables.reste})
          </span>
        </div>
      `
    ]]]

1 « J'aime »

j’utilise ce fork :

Bonsoir à tous,

J’ai installé l’intégration Bodymiscale pour ma balance, mais ayant mi fitness pour le reste je regardais un peu et trouve Health Connect, mais j’ai zéro info sur l’utilisation ni l’installation.

J’ai mis Santé connect sur mon tel, mi fitness balance quelques données mais Home Assistant n’utilise rien de cette appli, je ne sais pas si il lui faut du temps pour se mettre à jour ou pas, mais ensuite je sais pas ou je vais pouvoir retrouver ces infos vu qu’il n’y a aucune intégration health connect directement…

J’ai pensé regardé dans application mobile et mon portable j’ai quelques infos de santé effectivement mais elles sont toutes désactivées.

Si vous avez des idées je suis preneur. merci

Bonjour ,
si jeux peux me permettre de vous déranger , je le trouve ou le mfa
Merci

Re,

Il va falloir être plus précis, la double authentification, il faut l’activer, ensuite tout dépend à quel niveau c’est activé HA ou autre.

Bref un max de précisions.

cdt

  • alors la démarche , je pense est assez simple :
  • Je me connecte sur mon compte garmin connecte et , 5 mn +tard je recois par mail un N°d’identidication
  • ce N° ( 6 chiffre ) je pense que c’est mon mfa , je le saisie sur HA( hacs, --) garmin connect–) identifiant et N° mfa )
  • voilà ma démarche --) bonne , pas bonne ?
    Merci

Hello, j’aimerai faire le même principe, mais inversé pour le poids
Genre une jauge qui atteint l’objectif au poids fixé.

genre 85- 90Kg max en rouge
80-84 en orange
75-19 en vert
avec un reste 6 kg à perdre

type: custom:button-card
entity: sensor.withings_poids_3
show_name: true
show_icon: true
name: Objectif poids
icon: mdi:weight-kilogram
variables:
  goal: |
    [[[ return parseInt(states['sensor.withings_weight_goal'].state) || 0 ]]]
  steps: |
    [[[ return parseInt(states['sensor.withings_poids_3'].state) || 0 ]]]
  percent: |
    [[[ 
      let p = (parseInt(states['sensor.withings_poids_3'].state) / parseInt(states['sensor.withings_weight_goal'].state)) * 100;
      return Math.min(p, 100); 
    ]]]
  reste: |
    [[[ 
      let r = parseInt(states['sensor.withings_weight_goal'].state) - parseInt(states['sensor.withings_poids_3'].state);
      return r > 0 ? r : 0;
    ]]]
styles:
  grid:
    - grid-template-areas: "\"i n\" \"bar bar\""
    - grid-template-columns: min-content 1fr
    - grid-template-rows: auto auto
  card:
    - padding: 15px
    - border-radius: 15px
  img_cell:
    - justify-self: start
    - width: 30px
  name:
    - justify-self: start
    - font-weight: bold
    - font-size: 1.1em
  custom_fields:
    bar:
      - background: rgba(255, 255, 255, 0.1)
      - border-radius: 10px
      - height: 35px
      - margin-top: 12px
      - width: 100%
      - position: relative
      - overflow: hidden
custom_fields:
  bar: |
    [[[
      /* L'astuce du background-size permet de ne voir que la partie du dégradé correspondant au pourcentage actuel */
      return `
        <div style="
          width: ${variables.percent}%;
          height: 100%;
          background: linear-gradient(to right, #e74c3c 0%, #f1c40f 50%, #2ecc71 100%);
          background-size: ${100 / (variables.percent / 100)}% 100%;
          border-radius: 10px;
          transition: width 0.8s ease-in-out;
        ">
        </div>
        <div style="
          position: absolute;
          top: 0;
          left: 10px;
          height: 100%;
          display: flex;
          align-items: center;
          font-size: 0.9em;
          font-weight: 600;
          color: white;
          text-shadow: 1px 1px 3px rgba(0,0,0,0.7);
          pointer-events: none;
          white-space: nowrap;
        ">
          ${variables.steps} / ${variables.goal} 
          <span style="opacity: 0.8; margin-left: 8px; font-weight: 400;">
            (Reste: ${variables.reste})
          </span>
        </div>
      `
    ]]]

Je suis arrivé à un truc pas trop mal

3 « J'aime »

Bonsoir,

Est-ce qu’il serait possible d’avoir le code du graphique horizontal avec avec les objectifs ? Merci

type: custom:button-card
entity: sensor.withings_poids_3
name: Suivi poids
icon: mdi:scale-bathroom
show_icon: false
show_name: true
variables:
  poids: |
    [[[ 
      let p = parseFloat(states['sensor.withings_poids_3'].state) || 0;
      return Math.round(p); 
    ]]]
  objectif: |
    [[[ return parseInt(states['sensor.withings_weight_goal'].state)
    || 0 ]]]
  min: 70
  max: 90
styles:
  grid:
    - grid-template-areas: "\"n\" \"bar\""
    - grid-template-columns: 1fr
    - grid-template-rows: auto auto
  card:
    - padding: 20px 20px 50px 20px
    - border-radius: 20px
    - overflow: visible
  name:
    - font-weight: bold
    - font-size: 1.4em
    - margin-bottom: 40px
    - justify-self: center
  custom_fields:
    bar:
      - width: 100%
      - overflow: visible
custom_fields:
  bar: |
    [[[
      const min = variables.min;
      const max = variables.max;
      const cible = variables.objectif;
      const actuel = variables.poids;

      let posPoids = ((actuel - min) / (max - min)) * 100;
      posPoids = Math.min(Math.max(posPoids, 0), 100);
      
      let posObjectif = ((cible - min) / (max - min)) * 100;
      posObjectif = Math.min(Math.max(posObjectif, 0), 100);

      return `
        <div style="position:relative; width:100%; height:30px; isolation: isolate;">
          
          <div style="position:absolute; inset:0; background: linear-gradient(to right, #2ecc71 0%, #2ecc71 50%, #f39c12 50%, #f39c12 75%, #e74c3c 75%, #e74c3c 100%); border-radius:15px; z-index:0;"></div>

          <div style="position:absolute; top:35px; left:0; right:0; display:flex; justify-content:space-between; font-size:11px; font-weight:bold; color: var(--primary-text-color); opacity: 0.7; z-index:1;">
            <span>70kg</span>
            <span>80kg</span>
            <span>90kg</span>
          </div>

          <div style="position:absolute; left:${posObjectif}%; top:0; width:2px; height:30px; border-left: 2px dashed rgba(255,255,255,0.7); z-index:2;">
            <div style="position:absolute; top:48px; left:50%; transform: translateX(-50%); font-size:11px; font-weight:bold; color: #2ecc71; background: rgba(0,0,0,0.5); padding: 3px 8px; border-radius: 6px; white-space: nowrap; border: 1px solid #2ecc71;">
              But: ${cible}kg
            </div>
          </div>

          <div style="position:absolute; left:calc(${posPoids}% - 1px); top:-8px; width:3px; height:46px; background:white; z-index:3; box-shadow: 0 0 8px rgba(0,0,0,0.4); border-radius: 2px;">
            <div style="position:absolute; top:-30px; left:50%; transform: translateX(-50%); font-size:11px; font-weight:bold; color: white; background: rgba(0,0,0,0.7); padding: 3px 8px; border-radius: 6px; white-space: nowrap; border: 1px solid white;">
              Actuel: ${actuel}kg
            </div>
          </div>

        </div>
      `;
    ]]]

2 « J'aime »

Bonjour,