Incremental colour selector - Coding Help Please

Hi All,

I’m no good at coding complex new ideas with HA (when they involve templates), but I think that’s the way to achieve an idea I have.

I want to set up a Xiaomi cube to run through the colours of a colour wheel when rotated so the colour of a light can be selected. I was thinking that the rotate function could increment the RGB numbers as per:

Start: RGB(244, 66 66) increment to RGB(244, 244, 66)
then decrement from RGB(244, 244, 66) to RGB(66, 244, 66)
then increment from RGB(66, 244, 66) to RGB(66, 244, 244)
then decrement from RGB(66, 244, 244) to RGB(66, 66, 244)
then increment from RGB(66, 66, 244) to RGB(244, 66, 244)
then decrement from RGB(244, 66, 244) to RGB(244, 66, 66) which gets it back to the starting point.

… with the ability to rotate the cube either direction to go through the colours in forward or reverse sequence.

I know its a lot to ask but the final product would be awesome if someone has the skills to help with the code. I already have code for the cube which I use to control volume but I’m not sure how to tackle the various number sequences required for this.

Thanks in advance for any help

Typically it’s difficult to provide a value for the light.turn_on service’s rgb_color parameter with templates, mainly because rgb_color wants a list, whereas a template can only return a string. So typically it’s much easier to use color_name or profile which take a string, or color_temp or kelvin which takes only one number.

Assuming, e.g., you can find reasonable color names for the six RGB combinations you wanted (I took a guess below! :slight_smile:), then something like the following might work. (Or if you prefer profile, etc., adjust accordingly.) If doesn’t work for you, then you should look into using a python_script.

First we need an input_number as a color “index”:

input_number:
  color_index:
    min: 0
    max: 5
    step: 1

Then you have one automation that changes the value of the input_number based on cube rotation. Not sure how the cube indicates it has rotated and the direction, but something roughly like:

- alias: Change color index
  trigger:
    # Appropriate trigger for cube rotation
  action:
    service: input_number.set_value
    entity_id: input_number.color_index
    data_template:
      value: >
        # Set increment value to true if incrementing, false otherwise
        {% set increment = ??? %}
        {% set current = states('input_number.color_index')|int %}
        {% if increment %}
          {{ 0 if current == 5 else current + 1 }}
        {% else %}
          {{ 5 if current == 0 else current - 1 }}
        {% endif %}

Now you can use the input_number to change the light color:

- alias: Change color
  trigger:
    platform: state
    entity_id: input_number.color_index
  action:
    service: light.turn_on
    entity_id: light.WHATEVER
    data_template:
      color_name: >
        {{ ['crimson', 'yellow', 'limegreen', 'turquoise', 'royalblue', 'orchid']
           [states('input_number.color_index')|int(0)] }}

This could probably be made into one automation, but the advantage to keeping them separate is you can also change the light color by using the input_number “slider” in the frontend.

hi @pnbruckner , I think maybe I didn’t explain my idea enough. Rather than 6 colours I actually want the colour to gradually change through all of the different numbers for each of the R, G and B values as per the ‘table’ above. So for the first line it would increment the G value by 1, from 66 through to 244, then start decrementing the R value from 244 down to 66, etc.

Ok. Then I think you at least need to look at using a python_script. I think this is too difficult using templates.

Thanks, I’ll look into it. I don’t have Python experience but hopefully there are enough examples around that I can stitch together…

So basically the script would use hass.services.call('light', 'turn_on', {'entity_id': 'LIGHT_ENTITY_ID', 'rgb_color': [r,g,b]}) to turn the light on to the specified RGB color. The trick will be to control the time between the calls, and to decide when to stop. I suspect this might not work too well (e.g., might not run fast enough, might run too fast, might run inconsistently, etc.) But it might be worth a shot. Good luck!