mirror of
https://github.com/lvgl/lvgl.git
synced 2026-05-25 01:04:25 +08:00
refactor(observer): move bindings to the related widgets
This commit is contained in:
@@ -55,12 +55,6 @@ typedef struct {
|
||||
const char * value;
|
||||
} subject_set_string_user_data_t;
|
||||
|
||||
typedef struct {
|
||||
lv_subject_t * subject;
|
||||
void * element; /**< E.g. span of a span group*/
|
||||
const char * fmt;
|
||||
} bind_element_string_t;
|
||||
|
||||
typedef struct {
|
||||
lv_subject_t * subject;
|
||||
int32_t step;
|
||||
@@ -93,39 +87,6 @@ static void obj_value_changed_event_cb(lv_event_t * e);
|
||||
|
||||
static void lv_subject_notify_if_changed(lv_subject_t * subject);
|
||||
|
||||
#if LV_USE_LABEL
|
||||
static void label_text_observer_cb(lv_observer_t * observer, lv_subject_t * subject);
|
||||
#endif
|
||||
|
||||
#if LV_USE_SPAN
|
||||
static void span_text_observer_cb(lv_observer_t * observer, lv_subject_t * subject);
|
||||
#endif
|
||||
|
||||
#if LV_USE_ARC
|
||||
static void arc_value_changed_event_cb(lv_event_t * e);
|
||||
static void arc_value_observer_cb(lv_observer_t * observer, lv_subject_t * subject);
|
||||
#endif
|
||||
|
||||
#if LV_USE_SLIDER
|
||||
static void slider_value_changed_event_cb(lv_event_t * e);
|
||||
static void slider_value_observer_cb(lv_observer_t * observer, lv_subject_t * subject);
|
||||
#endif
|
||||
|
||||
#if LV_USE_ROLLER
|
||||
static void roller_value_changed_event_cb(lv_event_t * e);
|
||||
static void roller_value_observer_cb(lv_observer_t * observer, lv_subject_t * subject);
|
||||
#endif
|
||||
|
||||
#if LV_USE_DROPDOWN
|
||||
static void dropdown_value_changed_event_cb(lv_event_t * e);
|
||||
static void dropdown_value_observer_cb(lv_observer_t * observer, lv_subject_t * subject);
|
||||
#endif
|
||||
|
||||
#if LV_USE_SCALE
|
||||
static void scale_section_min_value_observer_cb(lv_observer_t * observer, lv_subject_t * subject);
|
||||
static void scale_section_max_value_observer_cb(lv_observer_t * observer, lv_subject_t * subject);
|
||||
#endif
|
||||
|
||||
static void subject_set_string_free_user_data_event_cb(lv_event_t * e);
|
||||
|
||||
/**********************
|
||||
@@ -759,192 +720,6 @@ lv_observer_t * lv_obj_bind_checked(lv_obj_t * obj, lv_subject_t * subject)
|
||||
return observable;
|
||||
}
|
||||
|
||||
#if LV_USE_LABEL
|
||||
lv_observer_t * lv_label_bind_text(lv_obj_t * obj, lv_subject_t * subject, const char * fmt)
|
||||
{
|
||||
LV_ASSERT_NULL(subject);
|
||||
LV_ASSERT_NULL(obj);
|
||||
|
||||
if(fmt == NULL) {
|
||||
if(subject->type == LV_SUBJECT_TYPE_INT) {
|
||||
fmt = "%d";
|
||||
}
|
||||
#if LV_USE_FLOAT
|
||||
else if(subject->type == LV_SUBJECT_TYPE_FLOAT) {
|
||||
fmt = "%0.1f";
|
||||
}
|
||||
#endif
|
||||
else if(subject->type != LV_SUBJECT_TYPE_STRING && subject->type != LV_SUBJECT_TYPE_POINTER) {
|
||||
LV_LOG_WARN("Incompatible subject type: %d", subject->type);
|
||||
return NULL;
|
||||
}
|
||||
}
|
||||
else {
|
||||
if(subject->type != LV_SUBJECT_TYPE_STRING && subject->type != LV_SUBJECT_TYPE_POINTER &&
|
||||
subject->type != LV_SUBJECT_TYPE_INT && subject->type != LV_SUBJECT_TYPE_FLOAT) {
|
||||
LV_LOG_WARN("Incompatible subject type: %d", subject->type);
|
||||
return NULL;
|
||||
}
|
||||
}
|
||||
|
||||
lv_observer_t * observer = lv_subject_add_observer_obj(subject, label_text_observer_cb, obj, (void *)fmt);
|
||||
return observer;
|
||||
}
|
||||
#endif /*LV_USE_LABEL*/
|
||||
|
||||
#if LV_USE_SPAN
|
||||
lv_observer_t * lv_spangroup_bind_span_text(lv_obj_t * obj, lv_span_t * span, lv_subject_t * subject, const char * fmt)
|
||||
{
|
||||
LV_ASSERT_NULL(subject);
|
||||
LV_ASSERT_NULL(obj);
|
||||
LV_ASSERT_NULL(span);
|
||||
|
||||
if(fmt == NULL) {
|
||||
if(subject->type == LV_SUBJECT_TYPE_INT) {
|
||||
fmt = "%d";
|
||||
}
|
||||
#if LV_USE_FLOAT
|
||||
else if(subject->type == LV_SUBJECT_TYPE_FLOAT) {
|
||||
fmt = "%0.1f";
|
||||
}
|
||||
#endif
|
||||
else if(subject->type != LV_SUBJECT_TYPE_STRING && subject->type != LV_SUBJECT_TYPE_POINTER) {
|
||||
LV_LOG_WARN("Incompatible subject type: %d", subject->type);
|
||||
return NULL;
|
||||
}
|
||||
}
|
||||
else {
|
||||
if(subject->type != LV_SUBJECT_TYPE_STRING && subject->type != LV_SUBJECT_TYPE_POINTER &&
|
||||
subject->type != LV_SUBJECT_TYPE_INT && subject->type != LV_SUBJECT_TYPE_FLOAT) {
|
||||
LV_LOG_WARN("Incompatible subject type: %d", subject->type);
|
||||
return NULL;
|
||||
}
|
||||
}
|
||||
|
||||
bind_element_string_t * user_data = lv_zalloc(sizeof(bind_element_string_t));
|
||||
if(user_data == NULL) {
|
||||
LV_LOG_WARN("Couldn't allocate user_data");
|
||||
LV_ASSERT_MALLOC(user_data);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
user_data->subject = subject;
|
||||
user_data->element = span;
|
||||
user_data->fmt = fmt;
|
||||
|
||||
lv_observer_t * observer = lv_subject_add_observer_obj(subject, span_text_observer_cb, obj, user_data);
|
||||
observer->auto_free_user_data = 1;
|
||||
|
||||
return observer;
|
||||
}
|
||||
#endif /*LV_USE_SPAN*/
|
||||
|
||||
|
||||
#if LV_USE_ARC
|
||||
lv_observer_t * lv_arc_bind_value(lv_obj_t * obj, lv_subject_t * subject)
|
||||
{
|
||||
LV_ASSERT_NULL(subject);
|
||||
LV_ASSERT_NULL(obj);
|
||||
|
||||
if(subject->type != LV_SUBJECT_TYPE_INT && subject->type != LV_SUBJECT_TYPE_FLOAT) {
|
||||
LV_LOG_WARN("Incompatible subject type: %d", subject->type);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
lv_obj_add_event_cb(obj, arc_value_changed_event_cb, LV_EVENT_VALUE_CHANGED, subject);
|
||||
|
||||
lv_observer_t * observer = lv_subject_add_observer_obj(subject, arc_value_observer_cb, obj, NULL);
|
||||
return observer;
|
||||
}
|
||||
#endif /*LV_USE_ARC*/
|
||||
|
||||
#if LV_USE_SLIDER
|
||||
lv_observer_t * lv_slider_bind_value(lv_obj_t * obj, lv_subject_t * subject)
|
||||
{
|
||||
LV_ASSERT_NULL(subject);
|
||||
LV_ASSERT_NULL(obj);
|
||||
|
||||
if(subject->type != LV_SUBJECT_TYPE_INT && subject->type != LV_SUBJECT_TYPE_FLOAT) {
|
||||
LV_LOG_WARN("Incompatible subject type: %d", subject->type);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
lv_obj_add_event_cb(obj, slider_value_changed_event_cb, LV_EVENT_VALUE_CHANGED, subject);
|
||||
|
||||
lv_observer_t * observer = lv_subject_add_observer_obj(subject, slider_value_observer_cb, obj, NULL);
|
||||
return observer;
|
||||
}
|
||||
#endif /*LV_USE_SLIDER*/
|
||||
|
||||
#if LV_USE_ROLLER
|
||||
lv_observer_t * lv_roller_bind_value(lv_obj_t * obj, lv_subject_t * subject)
|
||||
{
|
||||
LV_ASSERT_NULL(subject);
|
||||
LV_ASSERT_NULL(obj);
|
||||
|
||||
if(subject->type != LV_SUBJECT_TYPE_INT) {
|
||||
LV_LOG_WARN("Incompatible subject type: %d", subject->type);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
lv_obj_add_event_cb(obj, roller_value_changed_event_cb, LV_EVENT_VALUE_CHANGED, subject);
|
||||
|
||||
lv_observer_t * observer = lv_subject_add_observer_obj(subject, roller_value_observer_cb, obj, NULL);
|
||||
return observer;
|
||||
}
|
||||
#endif /*LV_USE_ROLLER*/
|
||||
|
||||
#if LV_USE_DROPDOWN
|
||||
lv_observer_t * lv_dropdown_bind_value(lv_obj_t * obj, lv_subject_t * subject)
|
||||
{
|
||||
LV_ASSERT_NULL(subject);
|
||||
LV_ASSERT_NULL(obj);
|
||||
|
||||
if(subject->type != LV_SUBJECT_TYPE_INT) {
|
||||
LV_LOG_WARN("Incompatible subject type: %d", subject->type);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
lv_obj_add_event_cb(obj, dropdown_value_changed_event_cb, LV_EVENT_VALUE_CHANGED, subject);
|
||||
|
||||
lv_observer_t * observer = lv_subject_add_observer_obj(subject, dropdown_value_observer_cb, obj, NULL);
|
||||
return observer;
|
||||
}
|
||||
#endif /*LV_USE_DROPDOWN*/
|
||||
|
||||
#if LV_USE_SCALE
|
||||
|
||||
lv_observer_t * lv_scale_bind_section_min_value(lv_obj_t * obj, lv_scale_section_t * section, lv_subject_t * subject)
|
||||
{
|
||||
LV_ASSERT_NULL(subject);
|
||||
LV_ASSERT_NULL(obj);
|
||||
|
||||
if(subject->type != LV_SUBJECT_TYPE_INT) {
|
||||
LV_LOG_WARN("Incompatible subject type: %d", subject->type);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
lv_observer_t * observer = lv_subject_add_observer_obj(subject, scale_section_min_value_observer_cb, obj, section);
|
||||
|
||||
return observer;
|
||||
}
|
||||
|
||||
lv_observer_t * lv_scale_bind_section_max_value(lv_obj_t * obj, lv_scale_section_t * section, lv_subject_t * subject)
|
||||
{
|
||||
LV_ASSERT_NULL(subject);
|
||||
LV_ASSERT_NULL(obj);
|
||||
|
||||
if(subject->type != LV_SUBJECT_TYPE_INT) {
|
||||
LV_LOG_WARN("Incompatible subject type: %d", subject->type);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
lv_observer_t * observer = lv_subject_add_observer_obj(subject, scale_section_max_value_observer_cb, obj, section);
|
||||
|
||||
return observer;
|
||||
}
|
||||
|
||||
#endif /*LV_USE_SCALE*/
|
||||
|
||||
lv_obj_t * lv_observer_get_target_obj(lv_observer_t * observer)
|
||||
{
|
||||
@@ -1154,184 +929,6 @@ static void lv_subject_notify_if_changed(lv_subject_t * subject)
|
||||
}
|
||||
}
|
||||
|
||||
#if LV_USE_LABEL
|
||||
|
||||
static void label_text_observer_cb(lv_observer_t * observer, lv_subject_t * subject)
|
||||
{
|
||||
const char * fmt = observer->user_data;
|
||||
|
||||
if(fmt == NULL) {
|
||||
lv_label_set_text(observer->target, subject->value.pointer);
|
||||
}
|
||||
else {
|
||||
switch(subject->type) {
|
||||
case LV_SUBJECT_TYPE_INT:
|
||||
lv_label_set_text_fmt(observer->target, fmt, subject->value.num);
|
||||
break;
|
||||
#if LV_USE_FLOAT
|
||||
case LV_SUBJECT_TYPE_FLOAT:
|
||||
lv_label_set_text_fmt(observer->target, fmt, subject->value.float_v);
|
||||
break;
|
||||
#endif
|
||||
case LV_SUBJECT_TYPE_STRING:
|
||||
case LV_SUBJECT_TYPE_POINTER:
|
||||
lv_label_set_text_fmt(observer->target, fmt, subject->value.pointer);
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#endif /*LV_USE_LABEL*/
|
||||
|
||||
#if LV_USE_SPAN
|
||||
|
||||
static void span_text_observer_cb(lv_observer_t * observer, lv_subject_t * subject)
|
||||
{
|
||||
bind_element_string_t * user_data = observer->user_data;
|
||||
|
||||
if(user_data->fmt == NULL) {
|
||||
lv_spangroup_set_span_text(observer->target, user_data->element, subject->value.pointer);
|
||||
}
|
||||
else {
|
||||
switch(subject->type) {
|
||||
|
||||
case LV_SUBJECT_TYPE_INT:
|
||||
lv_spangroup_set_span_text_fmt(observer->target, user_data->element, user_data->fmt, subject->value.num);
|
||||
break;
|
||||
#if LV_USE_FLOAT
|
||||
case LV_SUBJECT_TYPE_FLOAT:
|
||||
lv_spangroup_set_span_text_fmt(observer->target, user_data->element, user_data->fmt, subject->value.float_v);
|
||||
break;
|
||||
#endif
|
||||
case LV_SUBJECT_TYPE_STRING:
|
||||
case LV_SUBJECT_TYPE_POINTER:
|
||||
lv_spangroup_set_span_text_fmt(observer->target, user_data->element, user_data->fmt, subject->value.pointer);
|
||||
break;
|
||||
default:
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#endif /*LV_USE_SPAN*/
|
||||
|
||||
|
||||
#if LV_USE_ARC
|
||||
|
||||
static void arc_value_changed_event_cb(lv_event_t * e)
|
||||
{
|
||||
lv_obj_t * arc = lv_event_get_current_target(e);
|
||||
lv_subject_t * subject = lv_event_get_user_data(e);
|
||||
|
||||
if(subject->type == LV_SUBJECT_TYPE_INT) {
|
||||
lv_subject_set_int(subject, lv_arc_get_value(arc));
|
||||
}
|
||||
#if LV_USE_FLOAT
|
||||
else {
|
||||
lv_subject_set_float(subject, (float)lv_arc_get_value(arc));
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
static void arc_value_observer_cb(lv_observer_t * observer, lv_subject_t * subject)
|
||||
{
|
||||
if(subject->type == LV_SUBJECT_TYPE_INT) {
|
||||
lv_arc_set_value(observer->target, subject->value.num);
|
||||
}
|
||||
#if LV_USE_FLOAT
|
||||
else {
|
||||
lv_arc_set_value(observer->target, (int32_t)subject->value.float_v);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
#endif /*LV_USE_ARC*/
|
||||
|
||||
#if LV_USE_SLIDER
|
||||
|
||||
static void slider_value_changed_event_cb(lv_event_t * e)
|
||||
{
|
||||
lv_obj_t * slider = lv_event_get_current_target(e);
|
||||
lv_subject_t * subject = lv_event_get_user_data(e);
|
||||
|
||||
if(subject->type == LV_SUBJECT_TYPE_INT) {
|
||||
lv_subject_set_int(subject, lv_slider_get_value(slider));
|
||||
}
|
||||
#if LV_USE_FLOAT
|
||||
else {
|
||||
lv_subject_set_float(subject, (float)lv_slider_get_value(slider));
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
static void slider_value_observer_cb(lv_observer_t * observer, lv_subject_t * subject)
|
||||
{
|
||||
if(subject->type == LV_SUBJECT_TYPE_INT) {
|
||||
lv_slider_set_value(observer->target, subject->value.num, LV_ANIM_OFF);
|
||||
}
|
||||
#if LV_USE_FLOAT
|
||||
else {
|
||||
lv_slider_set_value(observer->target, (int32_t)subject->value.float_v, LV_ANIM_OFF);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
#endif /*LV_USE_SLIDER*/
|
||||
|
||||
#if LV_USE_ROLLER
|
||||
|
||||
static void roller_value_changed_event_cb(lv_event_t * e)
|
||||
{
|
||||
lv_obj_t * roller = lv_event_get_current_target(e);
|
||||
lv_subject_t * subject = lv_event_get_user_data(e);
|
||||
|
||||
lv_subject_set_int(subject, lv_roller_get_selected(roller));
|
||||
}
|
||||
|
||||
static void roller_value_observer_cb(lv_observer_t * observer, lv_subject_t * subject)
|
||||
{
|
||||
if((int32_t)lv_roller_get_selected(observer->target) != subject->value.num) {
|
||||
lv_roller_set_selected(observer->target, subject->value.num, LV_ANIM_OFF);
|
||||
}
|
||||
}
|
||||
|
||||
#endif /*LV_USE_ROLLER*/
|
||||
|
||||
#if LV_USE_DROPDOWN
|
||||
|
||||
static void dropdown_value_changed_event_cb(lv_event_t * e)
|
||||
{
|
||||
lv_obj_t * dropdown = lv_event_get_current_target(e);
|
||||
lv_subject_t * subject = lv_event_get_user_data(e);
|
||||
|
||||
lv_subject_set_int(subject, lv_dropdown_get_selected(dropdown));
|
||||
}
|
||||
|
||||
static void dropdown_value_observer_cb(lv_observer_t * observer, lv_subject_t * subject)
|
||||
{
|
||||
lv_dropdown_set_selected(observer->target, subject->value.num);
|
||||
}
|
||||
|
||||
#endif /*LV_USE_DROPDOWN*/
|
||||
|
||||
#if LV_USE_SCALE
|
||||
|
||||
static void scale_section_min_value_observer_cb(lv_observer_t * observer, lv_subject_t * subject)
|
||||
{
|
||||
lv_scale_section_t * section = observer->user_data;
|
||||
lv_scale_set_section_min_value(observer->target, section, subject->value.num);
|
||||
}
|
||||
|
||||
static void scale_section_max_value_observer_cb(lv_observer_t * observer, lv_subject_t * subject)
|
||||
{
|
||||
lv_scale_section_t * section = observer->user_data;
|
||||
lv_scale_set_section_max_value(observer->target, section, subject->value.num);
|
||||
}
|
||||
|
||||
#endif /*LV_USE_SCALE*/
|
||||
|
||||
static void subject_set_string_free_user_data_event_cb(lv_event_t * e)
|
||||
{
|
||||
subject_set_string_user_data_t * user_data = lv_event_get_user_data(e);
|
||||
|
||||
@@ -530,100 +530,6 @@ lv_observer_t * lv_obj_bind_state_if_le(lv_obj_t * obj, lv_subject_t * subject,
|
||||
*/
|
||||
lv_observer_t * lv_obj_bind_checked(lv_obj_t * obj, lv_subject_t * subject);
|
||||
|
||||
#if LV_USE_LABEL
|
||||
/**
|
||||
* Bind an integer, string, or pointer Subject to a Label.
|
||||
* @param obj pointer to Label
|
||||
* @param subject pointer to Subject
|
||||
* @param fmt optional printf-like format string with 1 format specifier (e.g. "%d °C")
|
||||
* or NULL to bind to the value directly.
|
||||
* @return pointer to newly-created Observer
|
||||
* @note `fmt == NULL` can be used only with string and pointer Subjects.
|
||||
* @note If Subject is a pointer and `fmt == NULL`, pointer must point
|
||||
* to a `\0` terminated string.
|
||||
*/
|
||||
lv_observer_t * lv_label_bind_text(lv_obj_t * obj, lv_subject_t * subject, const char * fmt);
|
||||
#endif
|
||||
|
||||
#if LV_USE_SPAN
|
||||
|
||||
/**
|
||||
* Bind an integer, string, or pointer Subject to a Spangroup's Span.
|
||||
* @param obj pointer to Spangroup
|
||||
* @param span pointer to Span
|
||||
* @param subject pointer to Subject
|
||||
* @param fmt optional printf-like format string with 1 format specifier (e.g. "%d °C")
|
||||
* or NULL to bind to the value directly.
|
||||
* @return pointer to newly-created Observer
|
||||
* @note `fmt == NULL` can be used only with string and pointer Subjects.
|
||||
* @note If `fmt == NULL` strings and pointers (`\0` terminated string) will be shown
|
||||
* as text as they are, integers as %d, floats as %0.1f
|
||||
*/
|
||||
lv_observer_t * lv_spangroup_bind_span_text(lv_obj_t * obj, lv_span_t * span, lv_subject_t * subject, const char * fmt);
|
||||
|
||||
#endif
|
||||
|
||||
#if LV_USE_ARC
|
||||
/**
|
||||
* Bind an integer subject to an Arc's value.
|
||||
* @param obj pointer to Arc
|
||||
* @param subject pointer to Subject
|
||||
* @return pointer to newly-created Observer
|
||||
*/
|
||||
lv_observer_t * lv_arc_bind_value(lv_obj_t * obj, lv_subject_t * subject);
|
||||
#endif
|
||||
|
||||
#if LV_USE_SLIDER
|
||||
/**
|
||||
* Bind an integer Subject to a Slider's value.
|
||||
* @param obj pointer to Slider
|
||||
* @param subject pointer to Subject
|
||||
* @return pointer to newly-created Observer
|
||||
*/
|
||||
lv_observer_t * lv_slider_bind_value(lv_obj_t * obj, lv_subject_t * subject);
|
||||
#endif
|
||||
|
||||
#if LV_USE_ROLLER
|
||||
/**
|
||||
* Bind an integer Subject to a Roller's value.
|
||||
* @param obj pointer to Roller
|
||||
* @param subject pointer to Subject
|
||||
* @return pointer to newly-created Observer
|
||||
*/
|
||||
lv_observer_t * lv_roller_bind_value(lv_obj_t * obj, lv_subject_t * subject);
|
||||
#endif
|
||||
|
||||
#if LV_USE_DROPDOWN
|
||||
/**
|
||||
* Bind an integer Subject to a Dropdown's value.
|
||||
* @param obj pointer to Dropdown
|
||||
* @param subject pointer to Subject
|
||||
* @return pointer to newly-created Observer
|
||||
*/
|
||||
lv_observer_t * lv_dropdown_bind_value(lv_obj_t * obj, lv_subject_t * subject);
|
||||
#endif
|
||||
|
||||
#if LV_USE_SCALE
|
||||
|
||||
/**
|
||||
* Bind an integer subject to a scales section minimum value
|
||||
* @param obj pointer to a Scale
|
||||
* @param section pointer to a Scale section
|
||||
* @param subject pointer to a Subject
|
||||
* @return pointer to newly-created Observer
|
||||
*/
|
||||
lv_observer_t * lv_scale_bind_section_min_value(lv_obj_t * obj, lv_scale_section_t * section, lv_subject_t * subject);
|
||||
|
||||
/**
|
||||
* Bind an integer subject to a scales section maximum value
|
||||
* @param obj pointer to an Scale
|
||||
* @param section pointer to a Scale section
|
||||
* @param subject pointer to a Subject
|
||||
* @return pointer to newly-created Observer
|
||||
*/
|
||||
lv_observer_t * lv_scale_bind_section_max_value(lv_obj_t * obj, lv_scale_section_t * section, lv_subject_t * subject);
|
||||
|
||||
#endif
|
||||
|
||||
/**********************
|
||||
* MACROS
|
||||
|
||||
@@ -18,6 +18,7 @@
|
||||
#include "../../misc/lv_assert.h"
|
||||
#include "../../misc/lv_math.h"
|
||||
#include "../../draw/lv_draw_arc.h"
|
||||
#include "../../others/observer/lv_observer_private.h"
|
||||
|
||||
/*********************
|
||||
* DEFINES
|
||||
@@ -50,6 +51,10 @@ static void value_update(lv_obj_t * arc);
|
||||
static int32_t knob_get_extra_size(lv_obj_t * obj);
|
||||
static bool lv_arc_angle_within_bg_bounds(lv_obj_t * obj, const lv_value_precise_t angle,
|
||||
const lv_value_precise_t tolerance_deg);
|
||||
#if LV_USE_OBSERVER
|
||||
static void arc_value_changed_event_cb(lv_event_t * e);
|
||||
static void arc_value_observer_cb(lv_observer_t * observer, lv_subject_t * subject);
|
||||
#endif /*LV_USE_OBSERVER*/
|
||||
|
||||
/**********************
|
||||
* STATIC VARIABLES
|
||||
@@ -367,6 +372,25 @@ int32_t lv_arc_get_knob_offset(const lv_obj_t * obj)
|
||||
* Other functions
|
||||
*====================*/
|
||||
|
||||
#if LV_USE_OBSERVER
|
||||
lv_observer_t * lv_arc_bind_value(lv_obj_t * obj, lv_subject_t * subject)
|
||||
{
|
||||
LV_ASSERT_NULL(subject);
|
||||
LV_ASSERT_NULL(obj);
|
||||
|
||||
if(subject->type != LV_SUBJECT_TYPE_INT && subject->type != LV_SUBJECT_TYPE_FLOAT) {
|
||||
LV_LOG_WARN("Incompatible subject type: %d", subject->type);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
lv_obj_add_event_cb(obj, arc_value_changed_event_cb, LV_EVENT_VALUE_CHANGED, subject);
|
||||
|
||||
lv_observer_t * observer = lv_subject_add_observer_obj(subject, arc_value_observer_cb, obj, NULL);
|
||||
return observer;
|
||||
}
|
||||
#endif /*LV_USE_OBSERVER*/
|
||||
|
||||
|
||||
void lv_arc_align_obj_to_angle(const lv_obj_t * obj, lv_obj_t * obj_to_align, int32_t r_offset)
|
||||
{
|
||||
LV_ASSERT_OBJ(obj, MY_CLASS);
|
||||
@@ -1025,4 +1049,36 @@ static bool lv_arc_angle_within_bg_bounds(lv_obj_t * obj, const lv_value_precise
|
||||
return false;
|
||||
}
|
||||
|
||||
#if LV_USE_OBSERVER
|
||||
|
||||
static void arc_value_changed_event_cb(lv_event_t * e)
|
||||
{
|
||||
lv_obj_t * arc = lv_event_get_current_target(e);
|
||||
lv_subject_t * subject = lv_event_get_user_data(e);
|
||||
|
||||
if(subject->type == LV_SUBJECT_TYPE_INT) {
|
||||
lv_subject_set_int(subject, lv_arc_get_value(arc));
|
||||
}
|
||||
#if LV_USE_FLOAT
|
||||
else {
|
||||
lv_subject_set_float(subject, (float)lv_arc_get_value(arc));
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
static void arc_value_observer_cb(lv_observer_t * observer, lv_subject_t * subject)
|
||||
{
|
||||
if(subject->type == LV_SUBJECT_TYPE_INT) {
|
||||
lv_arc_set_value(observer->target, subject->value.num);
|
||||
}
|
||||
#if LV_USE_FLOAT
|
||||
else {
|
||||
lv_arc_set_value(observer->target, (int32_t)subject->value.float_v);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
#endif /*LV_USE_OBSERVER*/
|
||||
|
||||
|
||||
#endif
|
||||
|
||||
@@ -18,6 +18,7 @@ extern "C" {
|
||||
#if LV_USE_ARC != 0
|
||||
|
||||
#include "../../core/lv_obj.h"
|
||||
#include "../../others/observer/lv_observer.h"
|
||||
|
||||
/*********************
|
||||
* DEFINES
|
||||
@@ -232,6 +233,17 @@ int32_t lv_arc_get_knob_offset(const lv_obj_t * obj);
|
||||
* Other functions
|
||||
*====================*/
|
||||
|
||||
#if LV_USE_OBSERVER
|
||||
/**
|
||||
* Bind an integer subject to an Arc's value.
|
||||
* @param obj pointer to Arc
|
||||
* @param subject pointer to Subject
|
||||
* @return pointer to newly-created Observer
|
||||
*/
|
||||
lv_observer_t * lv_arc_bind_value(lv_obj_t * obj, lv_subject_t * subject);
|
||||
#endif
|
||||
|
||||
|
||||
/**
|
||||
* Align an object to the current position of the arc (knob)
|
||||
* @param obj pointer to an arc object
|
||||
|
||||
@@ -20,6 +20,7 @@ extern "C" {
|
||||
#include "../../core/lv_obj.h"
|
||||
#include "../../misc/lv_anim.h"
|
||||
#include "../label/lv_label.h"
|
||||
#include "../../others/observer/lv_observer.h"
|
||||
|
||||
/*********************
|
||||
* DEFINES
|
||||
|
||||
@@ -22,6 +22,7 @@
|
||||
#include "../../misc/lv_math.h"
|
||||
#include "../../misc/lv_text_ap.h"
|
||||
#include "../../misc/lv_text_private.h"
|
||||
#include "../../others/observer/lv_observer_private.h"
|
||||
#include "../../stdlib/lv_string.h"
|
||||
|
||||
/*********************
|
||||
@@ -59,6 +60,11 @@ static uint32_t get_id_on_point(lv_obj_t * dropdown_obj, int32_t y);
|
||||
static void position_to_selected(lv_obj_t * dropdown_obj, lv_anim_enable_t anim_en);
|
||||
static lv_obj_t * get_label(const lv_obj_t * obj);
|
||||
|
||||
#if LV_USE_OBSERVER
|
||||
static void dropdown_value_changed_event_cb(lv_event_t * e);
|
||||
static void dropdown_value_observer_cb(lv_observer_t * observer, lv_subject_t * subject);
|
||||
#endif /*LV_USE_OBSERVER*/
|
||||
|
||||
/**********************
|
||||
* STATIC VARIABLES
|
||||
**********************/
|
||||
@@ -636,6 +642,27 @@ bool lv_dropdown_is_open(lv_obj_t * obj)
|
||||
return lv_obj_has_flag(dropdown->list, LV_OBJ_FLAG_HIDDEN) ? false : true;
|
||||
}
|
||||
|
||||
#if LV_USE_OBSERVER
|
||||
|
||||
lv_observer_t * lv_dropdown_bind_value(lv_obj_t * obj, lv_subject_t * subject)
|
||||
{
|
||||
LV_ASSERT_NULL(subject);
|
||||
LV_ASSERT_NULL(obj);
|
||||
|
||||
if(subject->type != LV_SUBJECT_TYPE_INT) {
|
||||
LV_LOG_WARN("Incompatible subject type: %d", subject->type);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
lv_obj_add_event_cb(obj, dropdown_value_changed_event_cb, LV_EVENT_VALUE_CHANGED, subject);
|
||||
|
||||
lv_observer_t * observer = lv_subject_add_observer_obj(subject, dropdown_value_observer_cb, obj, NULL);
|
||||
return observer;
|
||||
}
|
||||
#endif /*LV_USE_OBSERVER*/
|
||||
|
||||
|
||||
|
||||
/**********************
|
||||
* STATIC FUNCTIONS
|
||||
**********************/
|
||||
@@ -1257,4 +1284,22 @@ static lv_obj_t * get_label(const lv_obj_t * obj)
|
||||
return lv_obj_get_child(dropdown->list, 0);
|
||||
}
|
||||
|
||||
#if LV_USE_OBSERVER
|
||||
|
||||
static void dropdown_value_changed_event_cb(lv_event_t * e)
|
||||
{
|
||||
lv_obj_t * dropdown = lv_event_get_current_target(e);
|
||||
lv_subject_t * subject = lv_event_get_user_data(e);
|
||||
|
||||
lv_subject_set_int(subject, lv_dropdown_get_selected(dropdown));
|
||||
}
|
||||
|
||||
static void dropdown_value_observer_cb(lv_observer_t * observer, lv_subject_t * subject)
|
||||
{
|
||||
lv_dropdown_set_selected(observer->target, subject->value.num);
|
||||
}
|
||||
|
||||
#endif /*LV_USE_OBSERVER*/
|
||||
|
||||
|
||||
#endif
|
||||
|
||||
@@ -233,6 +233,17 @@ void lv_dropdown_close(lv_obj_t * obj);
|
||||
*/
|
||||
bool lv_dropdown_is_open(lv_obj_t * obj);
|
||||
|
||||
|
||||
#if LV_USE_OBSERVER
|
||||
/**
|
||||
* Bind an integer Subject to a Dropdown's value.
|
||||
* @param obj pointer to Dropdown
|
||||
* @param subject pointer to Subject
|
||||
* @return pointer to newly-created Observer
|
||||
*/
|
||||
lv_observer_t * lv_dropdown_bind_value(lv_obj_t * obj, lv_subject_t * subject);
|
||||
#endif
|
||||
|
||||
/**********************
|
||||
* MACROS
|
||||
**********************/
|
||||
|
||||
@@ -24,6 +24,7 @@
|
||||
#include "../../misc/lv_text_private.h"
|
||||
#include "../../stdlib/lv_sprintf.h"
|
||||
#include "../../stdlib/lv_string.h"
|
||||
#include "../../others/observer/lv_observer_private.h"
|
||||
|
||||
/*********************
|
||||
* DEFINES
|
||||
@@ -59,6 +60,10 @@ static lv_text_flag_t get_label_flags(lv_label_t * label);
|
||||
static void calculate_x_coordinate(int32_t * x, const lv_text_align_t align, const char * txt,
|
||||
uint32_t length, const lv_font_t * font, lv_area_t * txt_coords, lv_text_attributes_t * attributes);
|
||||
|
||||
#if LV_USE_OBSERVER
|
||||
static void label_text_observer_cb(lv_observer_t * observer, lv_subject_t * subject);
|
||||
#endif
|
||||
|
||||
/**********************
|
||||
* STATIC VARIABLES
|
||||
**********************/
|
||||
@@ -664,6 +669,40 @@ bool lv_label_get_recolor(const lv_obj_t * obj)
|
||||
* Other functions
|
||||
*====================*/
|
||||
|
||||
#if LV_USE_OBSERVER
|
||||
lv_observer_t * lv_label_bind_text(lv_obj_t * obj, lv_subject_t * subject, const char * fmt)
|
||||
{
|
||||
LV_ASSERT_NULL(subject);
|
||||
LV_ASSERT_NULL(obj);
|
||||
|
||||
if(fmt == NULL) {
|
||||
if(subject->type == LV_SUBJECT_TYPE_INT) {
|
||||
fmt = "%d";
|
||||
}
|
||||
#if LV_USE_FLOAT
|
||||
else if(subject->type == LV_SUBJECT_TYPE_FLOAT) {
|
||||
fmt = "%0.1f";
|
||||
}
|
||||
#endif
|
||||
else if(subject->type != LV_SUBJECT_TYPE_STRING && subject->type != LV_SUBJECT_TYPE_POINTER) {
|
||||
LV_LOG_WARN("Incompatible subject type: %d", subject->type);
|
||||
return NULL;
|
||||
}
|
||||
}
|
||||
else {
|
||||
if(subject->type != LV_SUBJECT_TYPE_STRING && subject->type != LV_SUBJECT_TYPE_POINTER &&
|
||||
subject->type != LV_SUBJECT_TYPE_INT && subject->type != LV_SUBJECT_TYPE_FLOAT) {
|
||||
LV_LOG_WARN("Incompatible subject type: %d", subject->type);
|
||||
return NULL;
|
||||
}
|
||||
}
|
||||
|
||||
lv_observer_t * observer = lv_subject_add_observer_obj(subject, label_text_observer_cb, obj, (void *)fmt);
|
||||
return observer;
|
||||
}
|
||||
#endif /*LV_USE_OBSERVER*/
|
||||
|
||||
|
||||
void lv_label_ins_text(lv_obj_t * obj, uint32_t pos, const char * txt)
|
||||
{
|
||||
LV_ASSERT_OBJ(obj, MY_CLASS);
|
||||
@@ -710,6 +749,8 @@ void lv_label_cut_text(lv_obj_t * obj, uint32_t pos, uint32_t cnt)
|
||||
lv_label_refr_text(obj);
|
||||
}
|
||||
|
||||
|
||||
|
||||
/**********************
|
||||
* STATIC FUNCTIONS
|
||||
**********************/
|
||||
@@ -1331,4 +1372,36 @@ static void calculate_x_coordinate(int32_t * x, const lv_text_align_t align, con
|
||||
}
|
||||
}
|
||||
|
||||
#if LV_USE_OBSERVER
|
||||
|
||||
static void label_text_observer_cb(lv_observer_t * observer, lv_subject_t * subject)
|
||||
{
|
||||
const char * fmt = observer->user_data;
|
||||
|
||||
if(fmt == NULL) {
|
||||
lv_label_set_text(observer->target, subject->value.pointer);
|
||||
}
|
||||
else {
|
||||
switch(subject->type) {
|
||||
case LV_SUBJECT_TYPE_INT:
|
||||
lv_label_set_text_fmt(observer->target, fmt, subject->value.num);
|
||||
break;
|
||||
#if LV_USE_FLOAT
|
||||
case LV_SUBJECT_TYPE_FLOAT:
|
||||
lv_label_set_text_fmt(observer->target, fmt, subject->value.float_v);
|
||||
break;
|
||||
#endif
|
||||
case LV_SUBJECT_TYPE_STRING:
|
||||
case LV_SUBJECT_TYPE_POINTER:
|
||||
lv_label_set_text_fmt(observer->target, fmt, subject->value.pointer);
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#endif /*LV_USE_LABEL*/
|
||||
|
||||
|
||||
#endif
|
||||
|
||||
@@ -23,6 +23,7 @@ extern "C" {
|
||||
#include "../../font/lv_symbol_def.h"
|
||||
#include "../../misc/lv_text.h"
|
||||
#include "../../draw/lv_draw.h"
|
||||
#include "../../others/observer/lv_observer.h"
|
||||
|
||||
/*********************
|
||||
* DEFINES
|
||||
@@ -227,6 +228,22 @@ bool lv_label_get_recolor(const lv_obj_t * obj);
|
||||
* Other functions
|
||||
*====================*/
|
||||
|
||||
#if LV_USE_OBSERVER
|
||||
/**
|
||||
* Bind an integer, string, or pointer Subject to a Label.
|
||||
* @param obj pointer to Label
|
||||
* @param subject pointer to Subject
|
||||
* @param fmt optional printf-like format string with 1 format specifier (e.g. "%d °C")
|
||||
* or NULL to bind to the value directly.
|
||||
* @return pointer to newly-created Observer
|
||||
* @note `fmt == NULL` can be used only with string and pointer Subjects.
|
||||
* @note If Subject is a pointer and `fmt == NULL`, pointer must point
|
||||
* to a `\0` terminated string.
|
||||
*/
|
||||
lv_observer_t * lv_label_bind_text(lv_obj_t * obj, lv_subject_t * subject, const char * fmt);
|
||||
#endif
|
||||
|
||||
|
||||
/**
|
||||
* Insert a text to a label. The label text cannot be static.
|
||||
* @param obj pointer to a label object
|
||||
@@ -245,6 +262,8 @@ void lv_label_ins_text(lv_obj_t * obj, uint32_t pos, const char * txt);
|
||||
*/
|
||||
void lv_label_cut_text(lv_obj_t * obj, uint32_t pos, uint32_t cnt);
|
||||
|
||||
|
||||
|
||||
/**********************
|
||||
* MACROS
|
||||
**********************/
|
||||
|
||||
@@ -22,6 +22,7 @@
|
||||
#include "../../indev/lv_indev_scroll.h"
|
||||
#include "../../indev/lv_indev_private.h"
|
||||
#include "../../stdlib/lv_string.h"
|
||||
#include "../../others/observer/lv_observer_private.h"
|
||||
|
||||
/*********************
|
||||
* DEFINES
|
||||
@@ -52,6 +53,11 @@ static void scroll_anim_completed_cb(lv_anim_t * a);
|
||||
static void set_y_anim(void * obj, int32_t v);
|
||||
static void transform_vect_recursive(lv_obj_t * roller, lv_point_t * vect);
|
||||
|
||||
#if LV_USE_OBSERVER
|
||||
static void roller_value_changed_event_cb(lv_event_t * e);
|
||||
static void roller_value_observer_cb(lv_observer_t * observer, lv_subject_t * subject);
|
||||
#endif /*LV_USE_OBSERVER*/
|
||||
|
||||
/**********************
|
||||
* STATIC VARIABLES
|
||||
**********************/
|
||||
@@ -328,6 +334,25 @@ uint32_t lv_roller_get_option_count(const lv_obj_t * obj)
|
||||
}
|
||||
}
|
||||
|
||||
#if LV_USE_OBSERVER
|
||||
|
||||
lv_observer_t * lv_roller_bind_value(lv_obj_t * obj, lv_subject_t * subject)
|
||||
{
|
||||
LV_ASSERT_NULL(subject);
|
||||
LV_ASSERT_NULL(obj);
|
||||
|
||||
if(subject->type != LV_SUBJECT_TYPE_INT) {
|
||||
LV_LOG_WARN("Incompatible subject type: %d", subject->type);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
lv_obj_add_event_cb(obj, roller_value_changed_event_cb, LV_EVENT_VALUE_CHANGED, subject);
|
||||
|
||||
lv_observer_t * observer = lv_subject_add_observer_obj(subject, roller_value_observer_cb, obj, NULL);
|
||||
return observer;
|
||||
}
|
||||
#endif /*LV_USE_OBSERVER*/
|
||||
|
||||
/**********************
|
||||
* STATIC FUNCTIONS
|
||||
**********************/
|
||||
@@ -915,4 +940,24 @@ static void transform_vect_recursive(lv_obj_t * roller, lv_point_t * vect)
|
||||
lv_point_transform(vect, -angle, scale_x, scale_y, &pivot, false);
|
||||
}
|
||||
|
||||
#if LV_USE_OBSERVER
|
||||
|
||||
static void roller_value_changed_event_cb(lv_event_t * e)
|
||||
{
|
||||
lv_obj_t * roller = lv_event_get_current_target(e);
|
||||
lv_subject_t * subject = lv_event_get_user_data(e);
|
||||
|
||||
lv_subject_set_int(subject, lv_roller_get_selected(roller));
|
||||
}
|
||||
|
||||
static void roller_value_observer_cb(lv_observer_t * observer, lv_subject_t * subject)
|
||||
{
|
||||
if((int32_t)lv_roller_get_selected(observer->target) != subject->value.num) {
|
||||
lv_roller_set_selected(observer->target, subject->value.num, LV_ANIM_OFF);
|
||||
}
|
||||
}
|
||||
|
||||
#endif /*LV_USE_OBSERVER*/
|
||||
|
||||
|
||||
#endif
|
||||
|
||||
@@ -129,6 +129,17 @@ const char * lv_roller_get_options(const lv_obj_t * obj);
|
||||
*/
|
||||
uint32_t lv_roller_get_option_count(const lv_obj_t * obj);
|
||||
|
||||
|
||||
#if LV_USE_OBSERVER
|
||||
/**
|
||||
* Bind an integer Subject to a Roller's value.
|
||||
* @param obj pointer to Roller
|
||||
* @param subject pointer to Subject
|
||||
* @return pointer to newly-created Observer
|
||||
*/
|
||||
lv_observer_t * lv_roller_bind_value(lv_obj_t * obj, lv_subject_t * subject);
|
||||
#endif
|
||||
|
||||
/**********************
|
||||
* MACROS
|
||||
**********************/
|
||||
|
||||
@@ -15,6 +15,7 @@
|
||||
#include "../../misc/lv_assert.h"
|
||||
#include "../../misc/lv_math.h"
|
||||
#include "../../misc/lv_text_private.h"
|
||||
#include "../../others/observer/lv_observer_private.h"
|
||||
#include "../../draw/lv_draw_arc.h"
|
||||
|
||||
/*********************
|
||||
@@ -70,6 +71,11 @@ static void scale_free_line_needle_points_cb(lv_event_t * e);
|
||||
|
||||
static bool scale_is_major_tick(lv_scale_t * scale, uint32_t tick_idx);
|
||||
|
||||
#if LV_USE_OBSERVER
|
||||
static void scale_section_min_value_observer_cb(lv_observer_t * observer, lv_subject_t * subject);
|
||||
static void scale_section_max_value_observer_cb(lv_observer_t * observer, lv_subject_t * subject);
|
||||
#endif /*LV_USE_OBSERVER*/
|
||||
|
||||
/**********************
|
||||
* STATIC VARIABLES
|
||||
**********************/
|
||||
@@ -517,6 +523,40 @@ int32_t lv_scale_get_range_max_value(lv_obj_t * obj)
|
||||
* Other functions
|
||||
*====================*/
|
||||
|
||||
#if LV_USE_OBSERVER
|
||||
|
||||
lv_observer_t * lv_scale_bind_section_min_value(lv_obj_t * obj, lv_scale_section_t * section, lv_subject_t * subject)
|
||||
{
|
||||
LV_ASSERT_NULL(subject);
|
||||
LV_ASSERT_NULL(obj);
|
||||
|
||||
if(subject->type != LV_SUBJECT_TYPE_INT) {
|
||||
LV_LOG_WARN("Incompatible subject type: %d", subject->type);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
lv_observer_t * observer = lv_subject_add_observer_obj(subject, scale_section_min_value_observer_cb, obj, section);
|
||||
|
||||
return observer;
|
||||
}
|
||||
|
||||
lv_observer_t * lv_scale_bind_section_max_value(lv_obj_t * obj, lv_scale_section_t * section, lv_subject_t * subject)
|
||||
{
|
||||
LV_ASSERT_NULL(subject);
|
||||
LV_ASSERT_NULL(obj);
|
||||
|
||||
if(subject->type != LV_SUBJECT_TYPE_INT) {
|
||||
LV_LOG_WARN("Incompatible subject type: %d", subject->type);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
lv_observer_t * observer = lv_subject_add_observer_obj(subject, scale_section_max_value_observer_cb, obj, section);
|
||||
|
||||
return observer;
|
||||
}
|
||||
|
||||
#endif /*LV_USE_OBSERVER*/
|
||||
|
||||
/**********************
|
||||
* STATIC FUNCTIONS
|
||||
**********************/
|
||||
@@ -1719,4 +1759,21 @@ static bool scale_is_major_tick(lv_scale_t * scale, uint32_t tick_idx)
|
||||
return scale->major_tick_every != 0 && tick_idx % scale->major_tick_every == 0;
|
||||
}
|
||||
|
||||
#if LV_USE_OBSERVER
|
||||
|
||||
static void scale_section_min_value_observer_cb(lv_observer_t * observer, lv_subject_t * subject)
|
||||
{
|
||||
lv_scale_section_t * section = observer->user_data;
|
||||
lv_scale_set_section_min_value(observer->target, section, subject->value.num);
|
||||
}
|
||||
|
||||
static void scale_section_max_value_observer_cb(lv_observer_t * observer, lv_subject_t * subject)
|
||||
{
|
||||
lv_scale_section_t * section = observer->user_data;
|
||||
lv_scale_set_section_max_value(observer->target, section, subject->value.num);
|
||||
}
|
||||
|
||||
#endif /*LV_USE_OBSERVER*/
|
||||
|
||||
|
||||
#endif
|
||||
|
||||
@@ -20,6 +20,7 @@ extern "C" {
|
||||
#include "../../core/lv_obj.h"
|
||||
#include "../line/lv_line.h"
|
||||
#include "../image/lv_image.h"
|
||||
#include "../../others/observer/lv_observer.h"
|
||||
|
||||
/*********************
|
||||
* DEFINES
|
||||
@@ -344,6 +345,32 @@ int32_t lv_scale_get_range_min_value(lv_obj_t * obj);
|
||||
*/
|
||||
int32_t lv_scale_get_range_max_value(lv_obj_t * obj);
|
||||
|
||||
/*=====================
|
||||
* Other functions
|
||||
*====================*/
|
||||
|
||||
#if LV_USE_OBSERVER
|
||||
|
||||
/**
|
||||
* Bind an integer subject to a scales section minimum value
|
||||
* @param obj pointer to a Scale
|
||||
* @param section pointer to a Scale section
|
||||
* @param subject pointer to a Subject
|
||||
* @return pointer to newly-created Observer
|
||||
*/
|
||||
lv_observer_t * lv_scale_bind_section_min_value(lv_obj_t * obj, lv_scale_section_t * section, lv_subject_t * subject);
|
||||
|
||||
/**
|
||||
* Bind an integer subject to a scales section maximum value
|
||||
* @param obj pointer to an Scale
|
||||
* @param section pointer to a Scale section
|
||||
* @param subject pointer to a Subject
|
||||
* @return pointer to newly-created Observer
|
||||
*/
|
||||
lv_observer_t * lv_scale_bind_section_max_value(lv_obj_t * obj, lv_scale_section_t * section, lv_subject_t * subject);
|
||||
|
||||
#endif
|
||||
|
||||
/**********************
|
||||
* MACROS
|
||||
**********************/
|
||||
|
||||
@@ -22,6 +22,7 @@
|
||||
#include "../../stdlib/lv_string.h"
|
||||
#include "../../misc/lv_math.h"
|
||||
#include "../image/lv_image.h"
|
||||
#include "../../others/observer/lv_observer_private.h"
|
||||
|
||||
/*********************
|
||||
* DEFINES
|
||||
@@ -46,6 +47,11 @@ static bool is_slider_horizontal(lv_obj_t * obj);
|
||||
static void drag_start(lv_obj_t * obj);
|
||||
static void update_knob_pos(lv_obj_t * obj, bool check_drag);
|
||||
|
||||
#if LV_USE_OBSERVER
|
||||
static void slider_value_changed_event_cb(lv_event_t * e);
|
||||
static void slider_value_observer_cb(lv_observer_t * observer, lv_subject_t * subject);
|
||||
#endif /*LV_USE_OBSERVER*/
|
||||
|
||||
/**********************
|
||||
* STATIC VARIABLES
|
||||
**********************/
|
||||
@@ -216,6 +222,25 @@ bool lv_slider_is_symmetrical(lv_obj_t * obj)
|
||||
return lv_bar_is_symmetrical(obj);
|
||||
}
|
||||
|
||||
#if LV_USE_OBSERVER
|
||||
lv_observer_t * lv_slider_bind_value(lv_obj_t * obj, lv_subject_t * subject)
|
||||
{
|
||||
LV_ASSERT_NULL(subject);
|
||||
LV_ASSERT_NULL(obj);
|
||||
|
||||
if(subject->type != LV_SUBJECT_TYPE_INT && subject->type != LV_SUBJECT_TYPE_FLOAT) {
|
||||
LV_LOG_WARN("Incompatible subject type: %d", subject->type);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
lv_obj_add_event_cb(obj, slider_value_changed_event_cb, LV_EVENT_VALUE_CHANGED, subject);
|
||||
|
||||
lv_observer_t * observer = lv_subject_add_observer_obj(subject, slider_value_observer_cb, obj, NULL);
|
||||
return observer;
|
||||
}
|
||||
#endif /*LV_USE_OBSERVER*/
|
||||
|
||||
|
||||
/**********************
|
||||
* STATIC FUNCTIONS
|
||||
**********************/
|
||||
@@ -637,4 +662,37 @@ static void update_knob_pos(lv_obj_t * obj, bool check_drag)
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
#if LV_USE_OBSERVER
|
||||
|
||||
static void slider_value_changed_event_cb(lv_event_t * e)
|
||||
{
|
||||
lv_obj_t * slider = lv_event_get_current_target(e);
|
||||
lv_subject_t * subject = lv_event_get_user_data(e);
|
||||
|
||||
if(subject->type == LV_SUBJECT_TYPE_INT) {
|
||||
lv_subject_set_int(subject, lv_slider_get_value(slider));
|
||||
}
|
||||
#if LV_USE_FLOAT
|
||||
else {
|
||||
lv_subject_set_float(subject, (float)lv_slider_get_value(slider));
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
static void slider_value_observer_cb(lv_observer_t * observer, lv_subject_t * subject)
|
||||
{
|
||||
if(subject->type == LV_SUBJECT_TYPE_INT) {
|
||||
lv_slider_set_value(observer->target, subject->value.num, LV_ANIM_OFF);
|
||||
}
|
||||
#if LV_USE_FLOAT
|
||||
else {
|
||||
lv_slider_set_value(observer->target, (int32_t)subject->value.float_v, LV_ANIM_OFF);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
#endif /*LV_USE_OBSERVER*/
|
||||
|
||||
|
||||
#endif
|
||||
|
||||
@@ -183,6 +183,17 @@ lv_slider_orientation_t lv_slider_get_orientation(lv_obj_t * slider);
|
||||
*/
|
||||
bool lv_slider_is_symmetrical(lv_obj_t * obj);
|
||||
|
||||
|
||||
#if LV_USE_OBSERVER
|
||||
/**
|
||||
* Bind an integer Subject to a Slider's value.
|
||||
* @param obj pointer to Slider
|
||||
* @param subject pointer to Subject
|
||||
* @return pointer to newly-created Observer
|
||||
*/
|
||||
lv_observer_t * lv_slider_bind_value(lv_obj_t * obj, lv_subject_t * subject);
|
||||
#endif
|
||||
|
||||
/**********************
|
||||
* MACROS
|
||||
**********************/
|
||||
|
||||
@@ -16,6 +16,7 @@
|
||||
#include "../../misc/lv_assert.h"
|
||||
#include "../../misc/lv_text_private.h"
|
||||
#include "../../misc/lv_bidi_private.h"
|
||||
#include "../../others/observer/lv_observer_private.h"
|
||||
#include "../../misc/lv_text_ap.h"
|
||||
#include "../../core/lv_global.h"
|
||||
|
||||
@@ -43,6 +44,11 @@ struct _snippet_stack {
|
||||
uint32_t index;
|
||||
};
|
||||
|
||||
typedef struct {
|
||||
lv_subject_t * subject;
|
||||
void * element; /**< span of a span group*/
|
||||
const char * fmt;
|
||||
} bind_element_string_t;
|
||||
/**********************
|
||||
* STATIC PROTOTYPES
|
||||
**********************/
|
||||
@@ -71,6 +77,9 @@ static int32_t convert_indent_pct(lv_obj_t * spans, int32_t width);
|
||||
|
||||
static lv_span_coords_t make_span_coords(const lv_span_t * prev_span, const lv_span_t * curr_span, int32_t width,
|
||||
lv_area_t padding, int32_t indent);
|
||||
#if LV_USE_OBSERVER
|
||||
static void span_text_observer_cb(lv_observer_t * observer, lv_subject_t * subject);
|
||||
#endif
|
||||
|
||||
/**********************
|
||||
* STATIC VARIABLES
|
||||
@@ -729,6 +738,54 @@ void lv_spangroup_refresh(lv_obj_t * obj)
|
||||
lv_obj_refresh_self_size(obj);
|
||||
}
|
||||
|
||||
#if LV_USE_OBSERVER
|
||||
lv_observer_t * lv_spangroup_bind_span_text(lv_obj_t * obj, lv_span_t * span, lv_subject_t * subject, const char * fmt)
|
||||
{
|
||||
LV_ASSERT_NULL(subject);
|
||||
LV_ASSERT_NULL(obj);
|
||||
LV_ASSERT_NULL(span);
|
||||
|
||||
if(fmt == NULL) {
|
||||
if(subject->type == LV_SUBJECT_TYPE_INT) {
|
||||
fmt = "%d";
|
||||
}
|
||||
#if LV_USE_FLOAT
|
||||
else if(subject->type == LV_SUBJECT_TYPE_FLOAT) {
|
||||
fmt = "%0.1f";
|
||||
}
|
||||
#endif
|
||||
else if(subject->type != LV_SUBJECT_TYPE_STRING && subject->type != LV_SUBJECT_TYPE_POINTER) {
|
||||
LV_LOG_WARN("Incompatible subject type: %d", subject->type);
|
||||
return NULL;
|
||||
}
|
||||
}
|
||||
else {
|
||||
if(subject->type != LV_SUBJECT_TYPE_STRING && subject->type != LV_SUBJECT_TYPE_POINTER &&
|
||||
subject->type != LV_SUBJECT_TYPE_INT && subject->type != LV_SUBJECT_TYPE_FLOAT) {
|
||||
LV_LOG_WARN("Incompatible subject type: %d", subject->type);
|
||||
return NULL;
|
||||
}
|
||||
}
|
||||
|
||||
bind_element_string_t * user_data = lv_zalloc(sizeof(bind_element_string_t));
|
||||
if(user_data == NULL) {
|
||||
LV_LOG_WARN("Couldn't allocate user_data");
|
||||
LV_ASSERT_MALLOC(user_data);
|
||||
return NULL;
|
||||
}
|
||||
|
||||
user_data->subject = subject;
|
||||
user_data->element = span;
|
||||
user_data->fmt = fmt;
|
||||
|
||||
lv_observer_t * observer = lv_subject_add_observer_obj(subject, span_text_observer_cb, obj, user_data);
|
||||
observer->auto_free_user_data = 1;
|
||||
|
||||
return observer;
|
||||
}
|
||||
#endif /*LV_USE_OBSERVER*/
|
||||
|
||||
|
||||
/**********************
|
||||
* STATIC FUNCTIONS
|
||||
**********************/
|
||||
@@ -1398,4 +1455,36 @@ static lv_span_coords_t make_span_coords(const lv_span_t * prev_span, const lv_s
|
||||
return coords;
|
||||
}
|
||||
|
||||
#if LV_USE_OBSERVER
|
||||
|
||||
static void span_text_observer_cb(lv_observer_t * observer, lv_subject_t * subject)
|
||||
{
|
||||
bind_element_string_t * user_data = observer->user_data;
|
||||
|
||||
if(user_data->fmt == NULL) {
|
||||
lv_spangroup_set_span_text(observer->target, user_data->element, subject->value.pointer);
|
||||
}
|
||||
else {
|
||||
switch(subject->type) {
|
||||
|
||||
case LV_SUBJECT_TYPE_INT:
|
||||
lv_spangroup_set_span_text_fmt(observer->target, user_data->element, user_data->fmt, subject->value.num);
|
||||
break;
|
||||
#if LV_USE_FLOAT
|
||||
case LV_SUBJECT_TYPE_FLOAT:
|
||||
lv_spangroup_set_span_text_fmt(observer->target, user_data->element, user_data->fmt, subject->value.float_v);
|
||||
break;
|
||||
#endif
|
||||
case LV_SUBJECT_TYPE_STRING:
|
||||
case LV_SUBJECT_TYPE_POINTER:
|
||||
lv_spangroup_set_span_text_fmt(observer->target, user_data->element, user_data->fmt, subject->value.pointer);
|
||||
break;
|
||||
default:
|
||||
return;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
#endif /*LV_USE_OBSERVER*/
|
||||
|
||||
#endif
|
||||
|
||||
@@ -15,6 +15,7 @@ extern "C" {
|
||||
*********************/
|
||||
#include "../../lv_conf_internal.h"
|
||||
#include "../../core/lv_obj.h"
|
||||
#include "../../others/observer/lv_observer.h"
|
||||
|
||||
#if LV_USE_SPAN != 0
|
||||
|
||||
@@ -334,6 +335,24 @@ lv_span_t * lv_spangroup_get_span_by_point(lv_obj_t * obj, const lv_point_t * po
|
||||
*/
|
||||
void lv_spangroup_refresh(lv_obj_t * obj);
|
||||
|
||||
#if LV_USE_OBSERVER
|
||||
|
||||
/**
|
||||
* Bind an integer, string, or pointer Subject to a Spangroup's Span.
|
||||
* @param obj pointer to Spangroup
|
||||
* @param span pointer to Span
|
||||
* @param subject pointer to Subject
|
||||
* @param fmt optional printf-like format string with 1 format specifier (e.g. "%d °C")
|
||||
* or NULL to bind to the value directly.
|
||||
* @return pointer to newly-created Observer
|
||||
* @note `fmt == NULL` can be used only with string and pointer Subjects.
|
||||
* @note If `fmt == NULL` strings and pointers (`\0` terminated string) will be shown
|
||||
* as text as they are, integers as %d, floats as %0.1f
|
||||
*/
|
||||
lv_observer_t * lv_spangroup_bind_span_text(lv_obj_t * obj, lv_span_t * span, lv_subject_t * subject, const char * fmt);
|
||||
|
||||
#endif
|
||||
|
||||
/**********************
|
||||
* MACROS
|
||||
**********************/
|
||||
|
||||
Reference in New Issue
Block a user