Need help to set conditional var in Javascript

HI,
for a button config, I need to set a conditional variable in a template, hope this gives you an idea if what I am trying to establish:

        label:
          - color: >
              [[[ var state = {if (states['sensor.trash_today'].state != 'Geen') return states['sensor.trash_today'].state;
                  return states['sensor.trash_tomorrow'].state;}
                 if (state == 'papier') return 'blue';
                 if (state == 'gft' ) return 'green';
                 if (state == 'plastic') return 'orange';
                 if (state == 'restafval') return 'black';
                 return 'ivory'; ]]]

this obviously doesn’t work, but I am not sure how to proceed. Would appreciate some JS assistance :wink:

update
as an intermediary solution, Ive found this to work, but it is less elegant because the hardcoded vars are in all templates, which I would hope to prevent using a better template…

  - type: custom:button-card
    template: button_body
    entity: automation.mark_trash_as_moved_outside_from_notification
    name: Mark trash outside
    label: >
      [[[var today = states['sensor.trash_today'].state;
         var tomorrow = states['sensor.trash_tomorrow'].state;
         if (today == 'papier' || tomorrow == 'papier') return 'Papier';
         if (today == 'gft' || tomorrow == 'gft' ) return 'Gft';
         if (today == 'plastic' || tomorrow == 'plastic') return 'Plastic';
         if (today == 'restafval' || tomorrow == 'restafval') return 'Restafval';
         return 'Geen';
      ]]]

    icon: mdi:delete-alert
    show_state: false
    styles:
      card:
        - animation: blink 2s ease infinite
        - background-color: lightgrey
      label:
        - color: >
            [[[var today = states['sensor.trash_today'].state;
               var tomorrow = states['sensor.trash_tomorrow'].state;
               if (today == 'papier' || tomorrow == 'papier') return 'blue';
               if (today == 'gft' || tomorrow == 'gft' ) return 'green';
               if (today == 'plastic' || tomorrow == 'plastic') return 'orange';
               if (today == 'restafval' || tomorrow == 'restafval') return 'darkblue';
               return 'ivory';
            ]]]
      icon:
        - color: >
            [[[var today = states['sensor.trash_today'].state;
               var tomorrow = states['sensor.trash_tomorrow'].state;
               if (today == 'papier' || tomorrow == 'papier') return 'blue';
               if (today == 'gft' || tomorrow == 'gft' ) return 'green';
               if (today == 'plastic' || tomorrow == 'plastic') return 'orange';
               if (today == 'restafval' || tomorrow == 'restafval') return 'darkblue';
               return 'ivory';
            ]]]

thanks

That’s what I think you need to do for your state variable in the first example:

var state = states['sensor.trash_today'].state != 'Geen' ? states['sensor.trash_today'].state : states['sensor.trash_tomorrow'].state;

But I don’t quite understand what you call conditional variable?

Sorry if I was expressing myself cluttered…

What I want was, in case of states['sensor.trash_today'].state != 'Geen' I would need

var state = states['sensor.trash_today'].state

else ( in case of states['sensor.trash_tomorrow'].state != 'Geen' ) i would need

var state = states['sensor.trash_tomorrow'].state

so I can follow up with

                 if (state == 'papier') return 'blue';
                 if (state == 'gft' ) return 'green';
                 if (state == 'plastic') return 'orange';
                 if (state == 'restafval') return 'black';
                 return 'ivory'; ]]]

making that:

[[[ var state = states['sensor.trash_today'].state != 'Geen' ? states['sensor.trash_today'].state : states['sensor.trash_tomorrow'].state;
if (state == 'papier') return 'blue';
if (state == 'gft' ) return 'green';
if (state == 'plastic') return 'orange';
if (state == 'restafval') return 'black';
return 'ivory'; ]]]

I think your solution is exactly what I was looking for… thanks, will test immediately. Could that be written in an if: else construction also?

and if I may ask what I asked here too: can we use a mapper for the state in Javascript?

would make it even snappier :wink:

update

bingo!

  - type: custom:button-card
    template: button_body
    entity: automation.mark_trash_as_moved_outside_from_notification
    name: Mark trash outside
    label: >
      [[[ var trash = states['sensor.trash_today'].state != 'Geen' 
          ? states['sensor.trash_today'].state : states['sensor.trash_tomorrow'].state;
      return trash.charAt(0).toUpperCase() + trash.slice(1); ]]]
    icon: mdi:delete-alert
    show_state: false
    styles:
      card:
        - animation: blink 2s ease infinite
        - background-color: lightgrey
      label:
        - color: >
            [[[ var trash = states['sensor.trash_today'].state != 'Geen' 
                ? states['sensor.trash_today'].state : states['sensor.trash_tomorrow'].state;
            if (trash == 'papier') return 'blue';
            if (trash == 'gft' ) return 'green';
            if (trash == 'plastic') return 'orange';
            if (trash == 'restafval') return 'black';
            return 'ivory'; ]]]
      icon:
        - color: >
            [[[ var trash = states['sensor.trash_today'].state != 'Geen' 
                ? states['sensor.trash_today'].state : states['sensor.trash_tomorrow'].state;
            if (trash == 'papier') return 'blue';
            if (trash == 'gft' ) return 'green';
            if (trash == 'plastic') return 'orange';
            if (trash == 'restafval') return 'black';
            return 'ivory'; ]]]

working nicely indeed, thanks you very much @RomRider!

Yes this:

var x = condition ? value_true : value_false

Is equivalent to:

var x = value_false;
if (condition)
  x = value_true;

Yes you could but there’s not much value in doing it:

var mapper = {
  papier: "blue",
  gft: "green",
  plastic: "orange",
  restafval: "black"
}
var trash = states['sensor.trash_today'].state != 'Geen' ? states['sensor.trash_today'].state : states['sensor.trash_tomorrow'].state;
return mapper[trash] ? mapper[state] : "ivory";
1 Like

thanks!
got to get accustomed to the reverse logic of this if else construction…
Can confirm it to work correctly:

 [[[ var trash = states['sensor.trash_tomorrow'].state;
     if (states['sensor.trash_today'].state == 'Geen' )
         trash = states['sensor.trash_today'].state ;]]]

is equivalent to:

[[[ var trash = states['sensor.trash_today'].state != 'Geen' 
        ? states['sensor.trash_today'].state 
        : states['sensor.trash_tomorrow'].state;]]]

will certainly add the mapper to the toolbox, since I have bigger mappers than this, and it is a fine way of streamlining templates with many states to map…

should be this I think (trash in mapper, not state)?:

var mapper = {
  papier: "blue",
  gft: "green",
  plastic: "orange",
  restafval: "black"
}
var trash = states['sensor.trash_today'].state != 'Geen' ? states['sensor.trash_today'].state : states['sensor.trash_tomorrow'].state;
return mapper[trash] ? mapper[trash] : "ivory";

thanks again!

You’re right, it’s a mistake :slight_smile: I’ve updated the post.

nevermind, you took my template as base for your adjustment, so my ‘fault’… helped enormously.

still getting my head around this

return mapper[trash] ? mapper[trash] : "ivory";

and how this translates to what I would say aloud:
if trash in mapper return mapper[trash] else ‘ivory’ ;

If mapper[trash] doesn’t exist it returns undefined which is equivalent to false, which then returns the ivory value. If it’s defined, it just returns the value from the map.

Btw this is called ternary operator if you want to Google for it :wink:

yes, thanks, was aware of that, only not that it was also possible setting a variable with this operator.

was still trying to do this:

 [[[ if (states['sensor.trash_today'].state != 'Geen' ) return var trash = states['sensor.trash_today'].state;
         return trash = states['sensor.trash_tomorrow'].state ;]]]

which is the order I am used to… but that doesnt pass the parser

could try this maybe?:

 [[[ var trash = states['sensor.trash_today'].state if (states['sensor.trash_today'].state != 'Geen' );
     var trash = states['sensor.trash_tomorrow'].state ;]]]

nope that doesnt do it. this does though:

                [[[ var today = states['sensor.trash_today'].state;
                    var tomorrow = states['sensor.trash_tomorrow'].state;
                    var trash;
                    if (today != 'Geen' ) trash = today;
                    trash = tomorrow;]]]

so its all about the declaring of the variable, which can also be empty and then used in the if else construction.

thanks for educating me!