SOLVED - Numerous nth child in a menu. How to set different colors in a short short way?

Hello,

I have a 29 values menu, and i'd like to set different colors to its pop up.
For example the 6 first options would be colored red, then 4 would be blue...

So i tried to adapt this :

.item:nth-child(1) {
background: rgba(282,9,48,1);
}
.item:nth-child(2) {
background: rgba(262,9,48,1);
}
.item:nth-child(3) {
background: rgba(242,9,48,1);
}
// ...

with a few things, such as using this:

for(n=0;n<8;n++)   // associated to .item:nth-child(n)

But i really don't know how to get there...

So once again, any help appreciated :slight_smile: Thank you

Not sure there is a quicker way tbh.

You could maybe use a class for each colour type? You’d still need to add for each of the nth child lines initially but would save time and effort if you wanted to change them again- you could change just the theme file and not have to go back and amend each one.

Thank you.

I've just found a solution :thinking: :upside_down_face: :+1: :crazy_face:, adapting this code somewhere found here, initially made to change text-on colors in a switch :

JS{{
var colors = ["transparent", "green", "green", "orange"]
var css = ''
for (var i = 0; i < colors.length; i++) {
  css += "value:nth-child(" + (i+1) + "){--color-text-on:" + colors[i] + ";}\n"
}
return css
}}

To that :

JS{{
var colors = ["purple", "green", "red", "orange"]
var css = ''
for (var i = 0; i < colors.length; i++) {
  css += ".item:nth-child(" + (i+1) + "){background:" + colors[i] + ";}\n"
}
return css
}}

It works well with 4 values... now let's go for the 29... hmm... 30, i forgot 1 ! :laughing:

However, i'll try to adapt it again, in order to avoid writing ["blue","blue","blue","blue","red","red","red","red",...] :smiley:

@jean-emmanuel, if you read me : in this case, what's the difference between value:nth-child... and .item:nth-child... ?... some chance lead me to this, but i'd like to understand better :wink: Thank you

Edit: done... Here is my final step (unless there's some better way to do - I think here that the var colors is useless... just have to write it directly after "background") :

Edit Edit : Yep... works well too this way... :

JS{{
var css = ''
for (var i = 0; i < 3; i++) {
  css += ".item:nth-child(" + (i+1) + "){background:" + "purple" + ";}\n"
}
for (var i = 3; i < 6; i++) {
  css += ".item:nth-child(" + (i+1) + "){background:" + "green" + ";}\n"
}
for (var i = 6; i < 17; i++) {
  css += ".item:nth-child(" + (i+1) + "){background:" + "red" + ";}\n"
}
for (var i = 17; i < 25; i++) {
  css += ".item:nth-child(" + (i+1) + "){background:" + "orange" + ";}\n"
}

return css
}}

@jean-emmanuel again : what do mean those syntaxes " + ... +" and \n and +=???

2 Likes

value and .item are different css selectors (respectively for an html element <value></value> and an html element that has the item class) , which selector should be used can be determined by using the browser inspector (f12).

@jean-emmanuel again : what do mean those syntaxes " + ... +" and \n and +=

+ is used here for string concatenation, \n is an escaped new line character, += is a shorthand for performing an addition on a variable.

@jean-emmanuel Thank you very much !

I've just realised i was reading the wrong way, despite of the colors... i was reading ("+ ... +") instead of "..." + "..." :slightly_smiling_face:

Just to make sure i understand : css += "..."\n means in a way "write this css where i=0, go to new line (\n), write this one (+=) where i=1, go to new line, write this one..." ? Is it a good computer-to-human translation ?

And two more questions :

  • i'm totally lost in the browser inspector... where do i have to look to determine a selector ?...
  • Is it possible to attribute a gradient to a text color ?...

Cause here i am now:

I'd like to set the opposite direction of gradient color to the texts... don't know if i really like it, but at least i've learned a few good tips :slight_smile:

Thanks again

Is there a way to put the nth child (not just the colours) into the theme file?

  • Swayrian

I don't think so - but my skills are not that high!

what do you mean ?

For instance I have on a menu multiple nth-child in its CSS field as follow:

So basically, I'm trying to find a way to group them all into one single class into the theme file that way I would later recall that one single class in the CSS field of the menu (or multiple menus at once).

However, from what I understood nth-child is already a pseudo class which are classified into the class .item in this case so I wonder if that's possible or not.

Did you ever encounter this way of working ?

Swayrian

You can combine multiple selectors in css like this in your theme:

.my_class .item:nth-child(1) {}
.my_class .item:nth-child(2) {}
/* etc */

and add the my_class class to your widget by adding this to its css property:

class: my_class;
2 Likes

I guess you’d still need a class per button if each one was to be different Still, Useful to know this - I have a set of 60 buttons on one particular menus in my setup, but I think the real benefit would come if you want to repeat the widgets multiple times and so would only need to update once in the theme.

I've edited this a bit further. Hopefully it comes in handy for one or another:

JS{{
var row_colors = ["yellow", "orange", "blue", "purple"]
var color_hover = ["white"]
var items_opacity = .2

var gridx = @{this.gridTemplate}
var gridy = Math.ceil(Object.keys(@{this.values}).length / gridx)
if (gridx == "") {
  console.log("ERROR. Need value in gridTemplate for "+@{this.id})
  return
}
if (row_colors.length != gridy) {
  console.log("ERROR in "+@{this}+". Specified colors (currently "+row_colors.length+") don't match amount of rows of widget (currently "+gridy+").")
  return
}
var colors_off = []
for (var i = 0; i < row_colors.length; i++) {
  colors_off = colors_off.concat(Array(gridx).fill(row_colors[i]))
}
var css = ''
for (var i = 0; i < colors_off.length; i++) {
  css += ".item:nth-child(" + (i+1) + "){background:" + colors_off[i] + "; opacity: "+items_opacity+"}\n"
  css += ".item:nth-child(" + (i+1) + "):hover{background: "+ color_hover + ";\nopacity: 1}\n"
  
}
css += ".item.on{opacity: 1;}"
return css
}}

The idea is to have the menu's props set to:
css: [see script]
layout: grid
gridTemplate: 2 [example for number of rows]
values: { "Value 1": 1, "Value 2": 2, "Menu Entry": 3, "Menu Entry 2": 4, "Menu Entry 3": 5, "Hello World!": 6, "Another Entry 1": 7 } [example]

I scripted this, so one only needs to change the first 3 variables in css (see code) to taste. In the last effective line of the code, you can add additional css properties => In the code above it's for example css += ".item.on{opacity: 1;}"

Feel free to ask/edit/modify to your liking.
Cheers to you all and happy coding! :smiley:

4 Likes

nice mate, many thanks!