Send recolor code via lv_obj_add_event_cb

How properly send text with recolor code via lv_obj_add_event_cb message

What MCU/Processor/Board and compiler are you using? ESP32-S3 on PlatformIO

What LVGL version are you using? 8.3.0 dev

What do you want to achieve? Recolor part of text send via lv_obj_add_event_cb message

What have you tried so far?

I am beginner in C / C++ programing but have experience in other languages Lisp, VBA, Pascal. That’s why I a bit confused with all those types / references etc.

I have simple code which is based on some events like pushbutton, and should change something. For this exercise I want to recolor only integer value of concatenated text: Volume: #ff0000 18# or Volume: #00ff00 7# or Volume: Muted (when level is == 0)
Sending result to Serial.print gives expected results as above, but when using function it result with ? or H? rubbish on the screen. Only Volume: Muted pass OK as this is purely string.
How to properly pass those #ff0000# and other color codes.

Code to reproduce

    String color_code;
    cur_volume++;
    cur_volume = cur_volume % 21; // 0...21
    color_code = "Volume: "; // prefix
    if (cur_volume == 0) {
      color_code += "Muted"; // plain white
    } else if (cur_volume > 0 and cur_volume < 15) {
      color_code += "#00ff00 "; // green
      color_code += cur_volume;
      color_code += "#";
    } else {
      color_code += "#ff0000 "; // red
      color_code += cur_volume;
      color_code += "#";
    }
    Serial.print("Color Code: ");
    Serial.println(color_code);
    lv_msg_send(MSG_NEW_VOLUME, &color_code);

Result in terminal:
Color Code: Volume: #ff0000 20#
Color Code: Volume: Muted
Color Code: Volume: #00ff00 1#
  lv_obj_t *volume_label = lv_label_create(tileView);
  lv_obj_align_to(volume_label, bat_label, LV_ALIGN_OUT_BOTTOM_LEFT, 0, 5); //align to other element on screen
  lv_label_set_recolor(volume_label, true); 
  lv_label_set_text(volume_label, "Volume: #00ff00 10#"); // default value works too
  lv_obj_add_event_cb(volume_label, update_text_subscriber_cb, LV_EVENT_MSG_RECEIVED, NULL);
  lv_msg_subsribe_obj(MSG_NEW_VOLUME, volume_label, (void *)"%s");

static void update_text_subscriber_cb(lv_event_t *e) {
  lv_obj_t *label = lv_event_get_target(e);
  lv_msg_t *m = lv_event_get_msg(e);

  const char *fmt = (const char *)lv_msg_get_user_data(m);
  const char *t = (const char *)lv_msg_get_payload(m);

  lv_label_set_text_fmt(label, fmt, t);
}

Where I am doing error?
Thanks

Hmm, I think the problem is, that you have to convert cur_volume to a String first, and then concatenate it.
Maybe putting it into String (cur_volume) will help, e.g.:

      color_code += "#00ff00 "; // green
      color_code += String (cur_volume);
      color_code += "#";

See String

Nope. This is not good.
I have figured solution, but not sure if that is correct or fast way etc.
Changed type to char and sprintf

char color_code[20];

sprintf(color_code, "Volume: #ff0000 %d#", cur_volume);

If it works, then do not change, but improvements are welcome.

Be careful with sprintf!
Currently your buffer is large enough to hold that string with decimal values up to 99.
Better use snprintf.
If you need string/char functions in C try to use all the function with the ‘n’, e.g. strncat, strncpy…
Many problems in C programming come from buffer overflow! And the C-String functions (without the ‘n’) are predestined for it.

Thanks. Luckily cur_volume can be only in range 0-21 in my case, but suggestion noted.