DB2 switch-node change color on standard icon

I am desperately trying to change the colours of the default icon.
I tried it with the following css class. But it does not work.
What am I doing wrong?

/*
 * Custom CSS for ui-switch
 * Class: .custom-switch-colors
 */

/* off */
.custom-switch-colors .v-switch__track {
    background-color: red;
    opacity: 0.6;
    /* Vuetify Standard-Deckkraft */
}

.custom-switch-colors .v-switch__thumb {
    background-color: red;
}

/* on */
.custom-switch-colors.v-selection-control--dirty .v-switch__track {
    background-color: green;
    opacity: 0.6;
    /* Vuetify Standard-Deckkraft */
}

.custom-switch-colors.v-selection-control--dirty .v-switch__thumb {
    background-color: green;
}

With Claude's help, I was able to find the necessary CSS selectors.
If anyone else wants to change the default appearance/behavior of the DB2 ui-switch, the selectors I found may be helpful.

I have stored a collection of switch custom CSS classes in a DB2 HTML template node that can be used to customize the ui-switch.

The following properties are supported:

  • Compact layout - Like custom-switch-compact (4px gap, smaller margin)
  • Green/red colors - Like custom-switch (green for ON, red for OFF)
  • Label above switch - Vertically centered Hover effects - Static or dynamic tooltip Support for status icons - Icons are not cropped

A detailed description can be found in the description of the template-node.

Prerequisite in the ui switch
When using custom classes, the layout setting must be selected as shown in the image:

One more warning.
I am not a web developer. And even though the classes serve their purpose for me, there are certainly more optimal solutions.
Perhaps someone has a tip on how to define the classes independently of the layout setting in ui-switch.

Demo Flow

[
    {
        "id": "117a220cc6542071",
        "type": "ui-switch",
        "z": "0ec70a05b327bed4",
        "name": "sw1 without class",
        "label": "switch1",
        "group": "0983f10af9c18be0",
        "order": 1,
        "width": "2",
        "height": "1",
        "passthru": false,
        "decouple": false,
        "topic": "topic",
        "topicType": "msg",
        "style": "",
        "className": "",
        "layout": "row-spread",
        "clickableArea": "switch",
        "onvalue": "true",
        "onvalueType": "bool",
        "onicon": "",
        "oncolor": "green",
        "offvalue": "false",
        "offvalueType": "bool",
        "officon": "",
        "offcolor": "red",
        "x": 630,
        "y": 180,
        "wires": [
            []
        ]
    },
    {
        "id": "24ce4d9763f2b849",
        "type": "function",
        "z": "0ec70a05b327bed4",
        "name": "Static tooltip",
        "func": "const tooltipConfig = {\n    onText: \"This Text shows, is switch on\",\n    offText: \"This Text shows, is switch off\",\n    labelText: \"switch1\", // The visible label text\n    staticTooltip: \"This is a static Tooltip\"\n};\n\n\n// Option 1: Static tooltip\nmsg.ui_update = {\n    label: `<span title=\"${tooltipConfig.staticTooltip}\">${tooltipConfig.labelText}</span>`\n};\n\n// Option 2: Dynamic tooltip \n/*\nconst dynamicTooltip = msg.payload ? tooltipConfig.onText : tooltipConfig.offText;\nmsg.ui_update = {\n    label: `<span title=\"${dynamicTooltip}\">${tooltipConfig.labelText}</span>`\n};\n*/\n\n// Option 3: Enhanced with icons and status\n/*\nconst statusIcon = msg.payload ? \"🟢\" : \"🔴\";\nconst statusText = msg.payload ? \"EIN\" : \"AUS\";\nconst tooltipText = `Status: ${statusText} - ${msg.payload ? tooltipConfig.onText : tooltipConfig.offText}`;\n\nmsg.ui_update = {\n    label: `<span title=\"${tooltipText}\">${statusIcon} ${tooltipConfig.labelText}</span>`\n};\n*/\n\nreturn msg;",
        "outputs": 1,
        "timeout": 0,
        "noerr": 0,
        "initialize": "",
        "finalize": "",
        "libs": [],
        "x": 250,
        "y": 120,
        "wires": [
            [
                "117a220cc6542071"
            ]
        ]
    },
    {
        "id": "55e3b765b6caf8f6",
        "type": "inject",
        "z": "0ec70a05b327bed4",
        "name": "",
        "props": [
            {
                "p": "payload"
            },
            {
                "p": "topic",
                "vt": "str"
            }
        ],
        "repeat": "",
        "crontab": "",
        "once": false,
        "onceDelay": 0.1,
        "topic": "",
        "payload": "true",
        "payloadType": "bool",
        "x": 110,
        "y": 120,
        "wires": [
            [
                "24ce4d9763f2b849"
            ]
        ]
    },
    {
        "id": "f8eedf31eee1b8b7",
        "type": "function",
        "z": "0ec70a05b327bed4",
        "name": "Dynamic tooltip",
        "func": "const tooltipConfig = {\n    onText: \"This Text shows, is switch on\",\n    offText: \"This Text shows, is switch off\",\n    labelText: \"switch1\", // The visible label text\n    staticTooltip: \"This is a static Tooltip\"\n};\n\n\n// Option 1: Static tooltip\n/*\nmsg.ui_update = {\n    label: `<span title=\"${tooltipConfig.staticTooltip}\">${tooltipConfig.labelText}</span>`\n};\n*/\n\n// Option 2: Dynamic tooltip \nconst dynamicTooltip = msg.payload ? tooltipConfig.onText : tooltipConfig.offText;\nmsg.ui_update = {\n    label: `<span title=\"${dynamicTooltip}\">${tooltipConfig.labelText}</span>`\n};\n\n\n// Option 3: Enhanced with icons and status\n/*\nconst statusIcon = msg.payload ? \"🟢\" : \"🔴\";\nconst statusText = msg.payload ? \"ON\" : \"OFF\";\nconst tooltipText = `Status: ${statusText} - ${msg.payload ? tooltipConfig.onText : tooltipConfig.offText}`;\n\nmsg.ui_update = {\n    label: `<span title=\"${tooltipText}\">${statusIcon} ${tooltipConfig.labelText}</span>`\n};\n*/\n\nreturn msg;",
        "outputs": 1,
        "timeout": 0,
        "noerr": 0,
        "initialize": "",
        "finalize": "",
        "libs": [],
        "x": 260,
        "y": 160,
        "wires": [
            [
                "117a220cc6542071"
            ]
        ]
    },
    {
        "id": "21148a80f1176645",
        "type": "function",
        "z": "0ec70a05b327bed4",
        "name": "Enhanced with icons and status",
        "func": "const tooltipConfig = {\n    onText: \"This Text shows, is switch on\",\n    offText: \"This Text shows, is switch off\",\n    labelText: \"switch1\", // The visible label text\n    staticTooltip: \"This is a static Tooltip\"\n};\n\n\n// Option 1: Static tooltip\n/*\nmsg.ui_update = {\n    label: `<span title=\"${tooltipConfig.staticTooltip}\">${tooltipConfig.labelText}</span>`\n};\n*/\n\n// Option 2: Dynamic tooltip \n/*\nconst dynamicTooltip = msg.payload ? tooltipConfig.onText : tooltipConfig.offText;\nmsg.ui_update = {\n    label: `<span title=\"${dynamicTooltip}\">${tooltipConfig.labelText}</span>`\n};\n*/\n\n// Option 3: Enhanced with icons and status\n\nconst statusIcon = msg.payload ? \"🟢\" : \"🔴\";\nconst statusText = msg.payload ? \"ON\" : \"OFF\";\nconst tooltipText = `Status: ${statusText} - ${msg.payload ? tooltipConfig.onText : tooltipConfig.offText}`;\n\nmsg.ui_update = {\n    label: `<span title=\"${tooltipText}\">${statusIcon} ${tooltipConfig.labelText}</span>`\n};\n\n\nreturn msg;",
        "outputs": 1,
        "timeout": 0,
        "noerr": 0,
        "initialize": "",
        "finalize": "",
        "libs": [],
        "x": 310,
        "y": 200,
        "wires": [
            [
                "117a220cc6542071"
            ]
        ]
    },
    {
        "id": "141bec9a16c24236",
        "type": "inject",
        "z": "0ec70a05b327bed4",
        "name": "",
        "props": [
            {
                "p": "payload"
            },
            {
                "p": "topic",
                "vt": "str"
            }
        ],
        "repeat": "",
        "crontab": "",
        "once": false,
        "onceDelay": 0.1,
        "topic": "",
        "payload": "false",
        "payloadType": "bool",
        "x": 110,
        "y": 160,
        "wires": [
            [
                "f8eedf31eee1b8b7"
            ]
        ]
    },
    {
        "id": "620cde9ccc1cc2a8",
        "type": "inject",
        "z": "0ec70a05b327bed4",
        "name": "",
        "props": [
            {
                "p": "payload"
            },
            {
                "p": "topic",
                "vt": "str"
            }
        ],
        "repeat": "",
        "crontab": "",
        "once": false,
        "onceDelay": 0.1,
        "topic": "",
        "payload": "true",
        "payloadType": "bool",
        "x": 110,
        "y": 200,
        "wires": [
            [
                "21148a80f1176645"
            ]
        ]
    },
    {
        "id": "b3b4cc53a513ab23",
        "type": "ui-template",
        "z": "0ec70a05b327bed4",
        "group": "",
        "page": "dbc4ceee263d62e1",
        "ui": "",
        "name": "switch custom css ",
        "order": 0,
        "width": 0,
        "height": 0,
        "head": "",
        "format": "<style>\n/* Custom CSS für @flowfuse/node-red-dashboard ui-switch */\n/* Verwendung: CSS-Klasse \"custom-switch\" am ui-switch Node setzen */\n\n/* === FARBÄNDERUNGEN === */\n\n/* Switch ON - Grün (wenn checked) */\n.custom-switch .v-selection-control--dirty .v-switch__track {\n    background-color: #4CAF50 !important;\n    /* Grüner Track für ON */\n    opacity: 1 !important;\n}\n\n.custom-switch .v-selection-control--dirty .v-switch__thumb {\n    background-color: #2E7D32 !important;\n    /* Dunkelgrüner Thumb für ON */\n}\n\n/* Switch OFF - Rot (wenn nicht checked) */\n.custom-switch .v-selection-control:not(.v-selection-control--dirty) .v-switch__track {\n    background-color: #f44336 !important;\n    /* Roter Track für OFF */\n    opacity: 1 !important;\n}\n\n.custom-switch .v-selection-control:not(.v-selection-control--dirty) .v-switch__thumb {\n    background-color: #C62828 !important;\n    /* Dunkelroter Thumb für OFF */\n}\n\n/* === ALTERNATIVE FARBEN === */\n/* Verwendung: CSS-Klasse \"custom-switch-alt\" für dunklere Töne */\n\n.custom-switch-alt .v-selection-control--dirty .v-switch__track {\n    background-color: #28a745 !important;\n    /* Dunkleres Grün */\n}\n\n.custom-switch-alt .v-selection-control--dirty .v-switch__thumb {\n    background-color: #1e7e34 !important;\n    /* Sehr dunkles Grün für Thumb */\n}\n\n.custom-switch-alt .v-selection-control:not(.v-selection-control--dirty) .v-switch__track {\n    background-color: #dc3545 !important;\n    /* Dunkleres Rot */\n}\n\n.custom-switch-alt .v-selection-control:not(.v-selection-control--dirty) .v-switch__thumb {\n    background-color: #bd2130 !important;\n    /* Sehr dunkles Rot für Thumb */\n}\n\n/* === LAYOUT: LABEL ÜBER DEM SWITCH === */\n\n/* Standard Layout - Label oberhalb des Switches */\n.custom-switch.nrdb-switch.nrdb-ui-switch--row-spread,\n.custom-switch .nrdb-switch.nrdb-ui-switch--row-spread {\n    flex-direction: column !important;\n    align-items: center !important;\n    text-align: center !important;\n}\n\n.custom-switch .v-input--horizontal {\n    flex-direction: column !important;\n    align-items: center !important;\n}\n\n.custom-switch .v-label {\n    margin-bottom: 8px !important;\n    margin-right: 0 !important;\n    order: -1 !important;\n    /* Label vor dem Switch */\n}\n\n.custom-switch .v-input__control {\n    justify-content: center !important;\n}\n\n/* === KOMPAKTES LAYOUT === */\n/* Verwendung: CSS-Klasse \"custom-switch-compact\" für weniger Abstand */\n\n.custom-switch-compact.nrdb-switch.nrdb-ui-switch--row-spread,\n.custom-switch-compact .nrdb-switch.nrdb-ui-switch--row-spread {\n    flex-direction: column !important;\n    align-items: center !important;\n    gap: 4px !important;\n}\n\n.custom-switch-compact .v-label {\n    margin-bottom: 4px !important;\n    font-size: 0.9em !important;\n}\n\n/* === KOMPAKT MIT FARBEN === */\n/* Verwendung: CSS-Klasse \"custom-switch-compact-color\" für kompaktes Layout MIT Farben */\n\n.custom-switch-compact-color.nrdb-switch.nrdb-ui-switch--row-spread,\n.custom-switch-compact-color .nrdb-switch.nrdb-ui-switch--row-spread {\n    flex-direction: column !important;\n    align-items: center !important;\n    gap: 4px !important;\n}\n\n.custom-switch-compact-color .v-label {\n    margin-bottom: 4px !important;\n    font-size: 0.9em !important;\n}\n\n/* Farben für kompakte Variante - Switch ON - Grün */\n.custom-switch-compact-color .v-selection-control--dirty .v-switch__track {\n    background-color: #4CAF50 !important;\n    /* Grüner Track für ON */\n    opacity: 1 !important;\n}\n\n.custom-switch-compact-color .v-selection-control--dirty .v-switch__thumb {\n    background-color: #2E7D32 !important;\n    /* Dunkelgrüner Thumb für ON */\n}\n\n/* Farben für kompakte Variante - Switch OFF - Rot */\n.custom-switch-compact-color .v-selection-control:not(.v-selection-control--dirty) .v-switch__track {\n    background-color: #f44336 !important;\n    /* Roter Track für OFF */\n    opacity: 1 !important;\n}\n\n.custom-switch-compact-color .v-selection-control:not(.v-selection-control--dirty) .v-switch__thumb {\n    background-color: #C62828 !important;\n    /* Dunkelroter Thumb für OFF */\n}\n\n/* Fallback-Regeln für kompakte Farbvariante */\n.custom-switch-compact-color input[type=\"checkbox\"]:checked+.v-switch__track {\n    background-color: #4CAF50 !important;\n}\n\n.custom-switch-compact-color input[type=\"checkbox\"]:not(:checked)+.v-switch__track {\n    background-color: #f44336 !important;\n}\n\n.custom-switch-compact-color .bg-primary {\n    background-color: #4CAF50 !important;\n}\n\n.custom-switch-compact-color .v-switch__track:not(.bg-primary) {\n    background-color: #f44336 !important;\n}\n\n/* === HOVER-EFFEKTE === */\n\n.custom-switch .v-switch__thumb:hover,\n.custom-switch-alt .v-switch__thumb:hover,\n.custom-switch-compact .v-switch__thumb:hover,\n.custom-switch-compact-color .v-switch__thumb:hover {\n    box-shadow: 0 2px 8px rgba(0, 0, 0, 0.2) !important;\n}\n\n/* === FALLBACK-REGELN === */\n/* Zusätzliche Sicherheit falls die Struktur abweicht */\n\n.custom-switch input[type=\"checkbox\"]:checked+.v-switch__track {\n    background-color: #4CAF50 !important;\n}\n\n.custom-switch input[type=\"checkbox\"]:not(:checked)+.v-switch__track {\n    background-color: #f44336 !important;\n}\n\n.custom-switch .bg-primary {\n    background-color: #4CAF50 !important;\n}\n\n.custom-switch .v-switch__track:not(.bg-primary) {\n    background-color: #f44336 !important;\n}\n\n</style>",
        "storeOutMessages": true,
        "passthru": true,
        "resendOnRefresh": true,
        "templateScope": "page:style",
        "className": "hidden",
        "x": 630,
        "y": 100,
        "wires": [
            []
        ]
    },
    {
        "id": "d01c13b43e61cbb5",
        "type": "ui-switch",
        "z": "0ec70a05b327bed4",
        "name": "sw3 custom-switch-compact-color",
        "label": "switch3",
        "group": "0983f10af9c18be0",
        "order": 3,
        "width": "1",
        "height": "1",
        "passthru": false,
        "decouple": false,
        "topic": "switch-update",
        "topicType": "str",
        "style": "",
        "className": "custom-switch-compact-color",
        "layout": "row-spread",
        "clickableArea": "switch",
        "onvalue": "true",
        "onvalueType": "bool",
        "onicon": "",
        "oncolor": "",
        "offvalue": "false",
        "offvalueType": "bool",
        "officon": "",
        "offcolor": "",
        "x": 400,
        "y": 400,
        "wires": [
            [
                "ce85e03b6b5c2f2b"
            ]
        ]
    },
    {
        "id": "9ed7e4959fb1ba19",
        "type": "inject",
        "z": "0ec70a05b327bed4",
        "name": "",
        "props": [
            {
                "p": "payload"
            },
            {
                "p": "topic",
                "vt": "str"
            }
        ],
        "repeat": "",
        "crontab": "",
        "once": false,
        "onceDelay": 0.1,
        "topic": "",
        "payload": "true",
        "payloadType": "bool",
        "x": 110,
        "y": 460,
        "wires": [
            [
                "ce85e03b6b5c2f2b"
            ]
        ]
    },
    {
        "id": "b6076de61b2b113f",
        "type": "inject",
        "z": "0ec70a05b327bed4",
        "name": "",
        "props": [
            {
                "p": "payload"
            },
            {
                "p": "topic",
                "vt": "str"
            }
        ],
        "repeat": "",
        "crontab": "",
        "once": false,
        "onceDelay": 0.1,
        "topic": "",
        "payload": "false",
        "payloadType": "bool",
        "x": 110,
        "y": 500,
        "wires": [
            [
                "ce85e03b6b5c2f2b"
            ]
        ]
    },
    {
        "id": "ce85e03b6b5c2f2b",
        "type": "function",
        "z": "0ec70a05b327bed4",
        "name": "Dynamic tooltip \\n with separate on/off tooltip \\n over ui_update",
        "func": "// LÖSUNG 2: Elegantere Lösung mit Link-Nodes\n// Function Node der auf Switch-Output reagiert\n\nconst tooltipConfig = {\n    onText: \"This Text shows, is switch on\",\n    offText: \"This Text shows, is switch off\",\n    labelText: \"switch3\"\n};\n\n// kommt direkt vom switch => switchMsg\nconst switchMsg = (msg.topic && msg.topic === \"switch-update\") \n                ? msg : null;\nconst currentState = msg.payload;\nconst statusIcon = currentState ? \"🟢\" : \"🔴\";\nconst statusText = currentState ? \"ON\" : \"OFF\";\nconst tooltipText = `Status: ${statusText} - ${currentState ? tooltipConfig.onText : tooltipConfig.offText}`;\n\n// nur ui_update Nachricht für Switch\nconst switchUpdate = {\n    ui_update: {\n        label: `<span title=\"${tooltipText}\">${statusIcon} ${tooltipConfig.labelText}</span>`\n    },\n    payload: currentState\n};\n\n// Beide Nachrichten senden\nreturn [switchMsg, switchUpdate];\n",
        "outputs": 2,
        "timeout": 0,
        "noerr": 0,
        "initialize": "",
        "finalize": "",
        "libs": [],
        "x": 380,
        "y": 480,
        "wires": [
            [],
            [
                "277440d0f1f1fa6f"
            ]
        ],
        "inputLabels": [
            "standard payload"
        ],
        "outputLabels": [
            "switchMsg",
            "switchUpdate"
        ]
    },
    {
        "id": "277440d0f1f1fa6f",
        "type": "link out",
        "z": "0ec70a05b327bed4",
        "name": "ui_update sw2",
        "mode": "link",
        "links": [
            "e77d6773cdff7d0b"
        ],
        "x": 640,
        "y": 520,
        "wires": [],
        "l": true
    },
    {
        "id": "e77d6773cdff7d0b",
        "type": "link in",
        "z": "0ec70a05b327bed4",
        "name": "ui_update sw2_in",
        "links": [
            "277440d0f1f1fa6f"
        ],
        "x": 140,
        "y": 400,
        "wires": [
            [
                "d01c13b43e61cbb5"
            ]
        ],
        "l": true
    },
    {
        "id": "f23aca9f3ed16078",
        "type": "inject",
        "z": "0ec70a05b327bed4",
        "name": "",
        "props": [
            {
                "p": "payload"
            },
            {
                "p": "topic",
                "vt": "str"
            }
        ],
        "repeat": "",
        "crontab": "",
        "once": false,
        "onceDelay": 0.1,
        "topic": "",
        "payload": "false",
        "payloadType": "bool",
        "x": 110,
        "y": 600,
        "wires": [
            [
                "6b6da580ecda360e"
            ]
        ]
    },
    {
        "id": "6b6da580ecda360e",
        "type": "function",
        "z": "0ec70a05b327bed4",
        "name": "Dynamic tooltip",
        "func": "const tooltipConfig = {\n    labelText: \"switch4\",\n    staticTooltip: \"switch4 static Tooltip\"\n};\n\n\n// Option 1: Static tooltip\n\nmsg.ui_update = {\n    label: `<span title=\"${tooltipConfig.staticTooltip}\">${tooltipConfig.labelText}</span>`\n};\n\nreturn msg;",
        "outputs": 1,
        "timeout": 0,
        "noerr": 0,
        "initialize": "",
        "finalize": "",
        "libs": [],
        "x": 300,
        "y": 620,
        "wires": [
            [
                "1878c8c616b86e8d"
            ]
        ]
    },
    {
        "id": "1878c8c616b86e8d",
        "type": "ui-switch",
        "z": "0ec70a05b327bed4",
        "name": "sw4 custom-switch-alt",
        "label": "switch4",
        "group": "0983f10af9c18be0",
        "order": 4,
        "width": "2",
        "height": "1",
        "passthru": false,
        "decouple": false,
        "topic": "topic",
        "topicType": "msg",
        "style": "",
        "className": "custom-switch-alt",
        "layout": "row-spread",
        "clickableArea": "switch",
        "onvalue": "true",
        "onvalueType": "bool",
        "onicon": "",
        "oncolor": "green",
        "offvalue": "false",
        "offvalueType": "bool",
        "officon": "",
        "offcolor": "red",
        "x": 540,
        "y": 620,
        "wires": [
            []
        ]
    },
    {
        "id": "c18c81129292b608",
        "type": "inject",
        "z": "0ec70a05b327bed4",
        "name": "",
        "props": [
            {
                "p": "payload"
            },
            {
                "p": "topic",
                "vt": "str"
            }
        ],
        "repeat": "",
        "crontab": "",
        "once": false,
        "onceDelay": 0.1,
        "topic": "",
        "payload": "true",
        "payloadType": "bool",
        "x": 110,
        "y": 640,
        "wires": [
            [
                "6b6da580ecda360e"
            ]
        ]
    },
    {
        "id": "e86d6f177e6603ec",
        "type": "inject",
        "z": "0ec70a05b327bed4",
        "name": "",
        "props": [
            {
                "p": "payload"
            },
            {
                "p": "topic",
                "vt": "str"
            }
        ],
        "repeat": "",
        "crontab": "",
        "once": false,
        "onceDelay": 0.1,
        "topic": "",
        "payload": "false",
        "payloadType": "bool",
        "x": 130,
        "y": 280,
        "wires": [
            [
                "ebfb1c94a8263b85"
            ]
        ]
    },
    {
        "id": "ebfb1c94a8263b85",
        "type": "function",
        "z": "0ec70a05b327bed4",
        "name": "Dynamic tooltip",
        "func": "const tooltipConfig = {\n    labelText: \"switch2\",\n    staticTooltip: \"switch2 static Tooltip\"\n};\n\n\n// Option 1: Static tooltip\n\nmsg.ui_update = {\n    label: `<span title=\"${tooltipConfig.staticTooltip}\">${tooltipConfig.labelText}</span>`\n};\n\nreturn msg;",
        "outputs": 1,
        "timeout": 0,
        "noerr": 0,
        "initialize": "",
        "finalize": "",
        "libs": [],
        "x": 320,
        "y": 300,
        "wires": [
            [
                "caacb324c483f314"
            ]
        ]
    },
    {
        "id": "caacb324c483f314",
        "type": "ui-switch",
        "z": "0ec70a05b327bed4",
        "name": "sw2 custom-switch",
        "label": "switch2",
        "group": "0983f10af9c18be0",
        "order": 2,
        "width": "1",
        "height": "1",
        "passthru": false,
        "decouple": false,
        "topic": "topic",
        "topicType": "msg",
        "style": "",
        "className": "custom-switch",
        "layout": "row-spread",
        "clickableArea": "switch",
        "onvalue": "true",
        "onvalueType": "bool",
        "onicon": "",
        "oncolor": "green",
        "offvalue": "false",
        "offvalueType": "bool",
        "officon": "",
        "offcolor": "red",
        "x": 550,
        "y": 300,
        "wires": [
            []
        ]
    },
    {
        "id": "053e3fbcfdfa1be1",
        "type": "inject",
        "z": "0ec70a05b327bed4",
        "name": "",
        "props": [
            {
                "p": "payload"
            },
            {
                "p": "topic",
                "vt": "str"
            }
        ],
        "repeat": "",
        "crontab": "",
        "once": false,
        "onceDelay": 0.1,
        "topic": "",
        "payload": "true",
        "payloadType": "bool",
        "x": 130,
        "y": 320,
        "wires": [
            [
                "ebfb1c94a8263b85"
            ]
        ]
    },
    {
        "id": "986dc82ee040c903",
        "type": "ui-switch",
        "z": "0ec70a05b327bed4",
        "name": "sw5 custom-switch-compact",
        "label": "switch4",
        "group": "0983f10af9c18be0",
        "order": 5,
        "width": "2",
        "height": "1",
        "passthru": false,
        "decouple": false,
        "topic": "topic",
        "topicType": "msg",
        "style": "",
        "className": "custom-switch-compact",
        "layout": "row-spread",
        "clickableArea": "switch",
        "onvalue": "true",
        "onvalueType": "bool",
        "onicon": "",
        "oncolor": "green",
        "offvalue": "false",
        "offvalueType": "bool",
        "officon": "",
        "offcolor": "red",
        "x": 560,
        "y": 740,
        "wires": [
            []
        ]
    },
    {
        "id": "bbed1d1d5cec8e6a",
        "type": "inject",
        "z": "0ec70a05b327bed4",
        "name": "",
        "props": [
            {
                "p": "payload"
            },
            {
                "p": "topic",
                "vt": "str"
            }
        ],
        "repeat": "",
        "crontab": "",
        "once": false,
        "onceDelay": 0.1,
        "topic": "",
        "payload": "false",
        "payloadType": "bool",
        "x": 110,
        "y": 720,
        "wires": [
            [
                "d31db89edaafeba1"
            ]
        ]
    },
    {
        "id": "d31db89edaafeba1",
        "type": "function",
        "z": "0ec70a05b327bed4",
        "name": "Dynamic tooltip",
        "func": "const tooltipConfig = {\n    labelText: \"switch5\",\n    staticTooltip: \"switch5 static Tooltip\"\n};\n\n\n// Option 1: Static tooltip\n\nmsg.ui_update = {\n    label: `<span title=\"${tooltipConfig.staticTooltip}\">${tooltipConfig.labelText}</span>`\n};\n\nreturn msg;",
        "outputs": 1,
        "timeout": 0,
        "noerr": 0,
        "initialize": "",
        "finalize": "",
        "libs": [],
        "x": 300,
        "y": 740,
        "wires": [
            [
                "986dc82ee040c903"
            ]
        ]
    },
    {
        "id": "ebfbdac499c105eb",
        "type": "inject",
        "z": "0ec70a05b327bed4",
        "name": "",
        "props": [
            {
                "p": "payload"
            },
            {
                "p": "topic",
                "vt": "str"
            }
        ],
        "repeat": "",
        "crontab": "",
        "once": false,
        "onceDelay": 0.1,
        "topic": "",
        "payload": "true",
        "payloadType": "bool",
        "x": 110,
        "y": 760,
        "wires": [
            [
                "d31db89edaafeba1"
            ]
        ]
    },
    {
        "id": "0983f10af9c18be0",
        "type": "ui-group",
        "name": "switch variants",
        "page": "dbc4ceee263d62e1",
        "width": "2",
        "height": 1,
        "order": 1,
        "showTitle": true,
        "className": "",
        "visible": "true",
        "disabled": "false",
        "groupType": "default"
    },
    {
        "id": "dbc4ceee263d62e1",
        "type": "ui-page",
        "name": "css tests",
        "ui": "1f09dc2ae6515591",
        "path": "/page10",
        "icon": "home",
        "layout": "grid",
        "theme": "61191d65f2b49096",
        "breakpoints": [
            {
                "name": "Default",
                "px": "0",
                "cols": "3"
            },
            {
                "name": "Tablet",
                "px": "576",
                "cols": "6"
            },
            {
                "name": "Small Desktop",
                "px": "768",
                "cols": "9"
            },
            {
                "name": "Desktop",
                "px": "1024",
                "cols": "12"
            }
        ],
        "order": 1,
        "className": "",
        "visible": "true",
        "disabled": "false"
    },
    {
        "id": "1f09dc2ae6515591",
        "type": "ui-base",
        "name": "My Dashboard 2.0",
        "path": "/dashboard",
        "appIcon": "",
        "includeClientData": true,
        "acceptsClientConfig": [
            "ui-notification",
            "ui-control"
        ],
        "showPathInSidebar": false,
        "headerContent": "page",
        "navigationStyle": "temporary",
        "titleBarStyle": "default",
        "showReconnectNotification": true,
        "notificationDisplayTime": 1,
        "showDisconnectNotification": true,
        "allowInstall": true
    },
    {
        "id": "61191d65f2b49096",
        "type": "ui-theme",
        "name": "Default Theme",
        "colors": {
            "surface": "#ffffff",
            "primary": "#0094ce",
            "bgPage": "#eeeeee",
            "groupBg": "#ffffff",
            "groupOutline": "#cccccc"
        },
        "sizes": {
            "density": "default",
            "pagePadding": "12px",
            "groupGap": "12px",
            "groupBorderRadius": "4px",
            "widgetGap": "12px"
        }
    },
    {
        "id": "a02390413584c22b",
        "type": "global-config",
        "env": [],
        "modules": {
            "@flowfuse/node-red-dashboard": "1.26.0"
        }
    }
]

How about a template node with the switch component?

https://vuetifyjs.com/en/components/switches/#colors

Something like this:

<template>
<v-switch 
v-model="value" 
color="indigo" 
@update:model-value="send({payload: value})" 
label="Switch"></v-switch>
</template>

<script>
    export default {
        data() {
            // define variables available component-wide
            // (in <template> and component functions)
            return {}
        },
        watch: {},
        computed: {},
        methods: {},
        mounted() {
            this.$socket.on('msg-input:' + this.id, (msg) => {
                this.value = msg?.payload
            })
        }
    }
</script>

Usefull link:

In a CSS template, you should not be including HTML tabs


To affect the colour, you can locally override the CSS variable that affects the colour.

.my-red-toggle .v-selection-control__wrapper {
    --v-theme-primary: 255, 25, 25;
}

Proof:
chrome_wKMchw6CQb

Thank you for this tip and the example. You are right, this is certainly the better and more flexible option.

I thought I could save time by using the standard switch. But as soon as major changes are required, that's not the case.

Thank you for this tip. I did not know that.

Great. Can you tell me how I can change the colour for the off state in a similar way?