Skip to content

Commit

Permalink
Remove implicit callback chains from gtk_ui
Browse files Browse the repository at this point in the history
Some program logic in view relies on callbacks triggering other
callbacks in the UI framework.
To allow swapping the UI framework, this commit splits up one such chain.
  • Loading branch information
schaten committed Mar 5, 2024
1 parent dca97bb commit 9a60208
Show file tree
Hide file tree
Showing 4 changed files with 70 additions and 59 deletions.
79 changes: 37 additions & 42 deletions src/gtk_ui.c
Original file line number Diff line number Diff line change
Expand Up @@ -66,18 +66,10 @@ extern gboolean fit_callback(GtkWidget* /*widget*/, gpointer data)
if (!flag)
return FALSE;

double aniso = gtk_adjustment_get_value(v->ui->gtk_aniso);

GtkAllocation alloc;
gtk_widget_get_allocation(v->ui->gtk_viewport, &alloc);
double xz = (double)(alloc.width - 5) / (double)view_get_dims(v)[v->settings.xdim];
double yz = (double)(alloc.height - 5) / (double)view_get_dims(v)[v->settings.ydim];


if (yz > xz / aniso)
yz = xz / aniso; // aniso

gtk_adjustment_set_value(v->ui->gtk_zoom, yz);
view_fit(v, alloc.width, alloc.height);

return FALSE;
}
Expand All @@ -91,27 +83,20 @@ extern gboolean geom_callback(GtkWidget* /*widget*/, gpointer data)
{
struct view_s* v = data;

struct view_ui_geom_params_s gp;

gp.N = DIMS;
gp.selected = malloc(sizeof(bool[DIMS]));

for (int j = 0; j < DIMS; j++) {

v->settings.pos[j] = gtk_adjustment_get_value(v->ui->gtk_posall[j]);
gp.selected[j] = gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(v->ui->gtk_checkall[j]));
v->ui_params.selected[j] = gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(v->ui->gtk_checkall[j]));
}

gp.zoom = gtk_adjustment_get_value(v->ui->gtk_zoom);
gp.aniso = gtk_adjustment_get_value(v->ui->gtk_aniso);
v->ui_params.zoom = gtk_adjustment_get_value(v->ui->gtk_zoom);
v->ui_params.aniso = gtk_adjustment_get_value(v->ui->gtk_aniso);

v->settings.flip = gtk_combo_box_get_active(v->ui->gtk_flip);
v->settings.interpolation = gtk_combo_box_get_active(v->ui->gtk_interp);
gp.transpose = gtk_toggle_tool_button_get_active(v->ui->gtk_transpose);

view_set_geom(v, gp);
v->ui_params.transpose = gtk_toggle_tool_button_get_active(v->ui->gtk_transpose);

free(gp.selected);
view_set_geom(v);

return FALSE;
}
Expand Down Expand Up @@ -252,6 +237,7 @@ extern gboolean window_close(GtkWidget* /*widget*/, GdkEvent* /*event*/, gpointe
{
struct view_s* v = data;

free(v->ui_params.selected);
view_window_close(v);

return FALSE;
Expand Down Expand Up @@ -342,27 +328,6 @@ void ui_rgbbuffer_connect(struct view_s* v, int rgbw, int rgbh, int rgbstr, unsi
v->ui->source = cairo_image_surface_create_for_data(buf, CAIRO_FORMAT_RGB24, rgbw, rgbh, rgbstr);
}

void ui_set_selected_dims(struct view_s* v, const bool* selected)
{
// Avoid calling this function from itself.
// Toggling the GTK_TOOGLE_BUTTONs below would normally lead to another call of this function.
static bool in_callback = false;
if (in_callback)
return;

in_callback = true;

for (int i = 0; i < DIMS; i++) {

if (selected[i])
gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(v->ui->gtk_checkall[i]), TRUE);
else
gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(v->ui->gtk_checkall[i]), FALSE);
}

in_callback = false;
}

void ui_pull_geom(struct view_s* v)
{
geom_callback(NULL, v);
Expand Down Expand Up @@ -398,6 +363,11 @@ void ui_set_msg(struct view_s* v, const char* msg)
void ui_window_new(struct view_s* v, int N, const long dims[N])
{
v->ui = xmalloc(sizeof(struct view_gtk_ui_s));
v->ui_params.selected = xmalloc(sizeof(bool[DIMS]));

for (int i = 0; i < DIMS; i++)
v->ui_params.selected[i] = (i == v->settings.xdim || i == v->settings.ydim) ? true : false;

v->ui->source = NULL;

GtkBuilder* builder = gtk_builder_new();
Expand Down Expand Up @@ -515,3 +485,28 @@ void ui_set_position(struct view_s* v, unsigned int dim, unsigned int p)
if (v->sync && v2->sync)
gtk_adjustment_set_value(v2->ui->gtk_posall[dim], p);
}

void ui_set_params(struct view_s* v)
{
// Avoid calling this function from itself.
// Toggling the GTK_TOOGLE_BUTTONs below would normally lead to another call of this function.
static bool in_callback = false;
if (in_callback)
return;

in_callback = true;

double zoom = gtk_adjustment_get_value(v->ui->gtk_zoom);
if (zoom != v->ui_params.zoom)
gtk_adjustment_set_value(v->ui->gtk_zoom, v->ui_params.zoom);

for (int j = 0; j < DIMS; j++) {

bool selected = gtk_toggle_button_get_active(GTK_TOGGLE_BUTTON(v->ui->gtk_checkall[j]));

if (selected != v->ui_params.selected[j])
gtk_toggle_button_set_active(GTK_TOGGLE_BUTTON(v->ui->gtk_checkall[j]), v->ui_params.selected[j] ? TRUE : FALSE);
}

in_callback = false;
}
3 changes: 1 addition & 2 deletions src/gtk_ui.h
Original file line number Diff line number Diff line change
Expand Up @@ -7,8 +7,6 @@ struct view_s;
extern void ui_rgbbuffer_disconnect(struct view_s* v);
extern void ui_rgbbuffer_connect(struct view_s* v, int rgbw, int rgbh, int rgbstr, unsigned char* buf);

extern void ui_set_selected_dims(struct view_s* v, const bool* selected);

extern void ui_set_position(struct view_s* v, unsigned int dim, unsigned int p);

extern void ui_set_limits(struct view_s* v);
Expand All @@ -19,6 +17,7 @@ extern void ui_set_mode(struct view_s* v);

extern void ui_set_msg(struct view_s* v, const char* msg);

void ui_set_params(struct view_s* v);

extern void ui_window_new(struct view_s* v, int N, const long dims[N]);

Expand Down
37 changes: 26 additions & 11 deletions src/view.c
Original file line number Diff line number Diff line change
Expand Up @@ -198,29 +198,29 @@ void view_add_geometry(struct view_s* v, unsigned long flags, const float (*geom
}


void view_set_geom(struct view_s* v, struct view_ui_geom_params_s gp)
void view_set_geom(struct view_s* v)
{
for (int j = 0; j < DIMS; j++) {
if (!gp.selected[j])
if (!v->ui_params.selected[j])
continue;

if (1 == v->control->dims[j]) {

gp.selected[j] = false;
v->ui_params.selected[j] = false;
} else if ((j != v->settings.xdim) && (j != v->settings.ydim)) {

for (int i = 0; i < DIMS; i++) {

if (v->settings.xdim == (DIMS + j - i) % DIMS) {

gp.selected[v->settings.xdim] = false;
v->ui_params.selected[v->settings.xdim] = false;
v->settings.xdim = j;
break;
}

if (v->settings.ydim == (DIMS + j - i) % DIMS) {

gp.selected[v->settings.ydim] = false;
v->ui_params.selected[v->settings.ydim] = false;
v->settings.ydim = j;
break;
}
Expand All @@ -229,15 +229,15 @@ void view_set_geom(struct view_s* v, struct view_ui_geom_params_s gp)
}
}

gp.selected[v->settings.xdim] = true;
gp.selected[v->settings.ydim] = true;
v->ui_params.selected[v->settings.xdim] = true;
v->ui_params.selected[v->settings.ydim] = true;

ui_set_selected_dims(v, gp.selected);
ui_set_params(v);

v->settings.xzoom = gp.zoom * gp.aniso;
v->settings.yzoom = gp.zoom;
v->settings.xzoom = v->ui_params.zoom * v->ui_params.aniso;
v->settings.yzoom = v->ui_params.zoom;

if (gp.transpose) {
if (v->ui_params.transpose) {

if (v->settings.xdim < v->settings.ydim) {

Expand Down Expand Up @@ -484,6 +484,8 @@ struct view_s* create_view(const char* name, const long pos[DIMS], const long di
struct view_s* v = xmalloc(sizeof(struct view_s));
v->control = xmalloc(sizeof(struct view_control_s));
v->ui = NULL;
v->ui_params.selected = NULL;
v->settings.pos = NULL;

v->next = v->prev = v;
v->sync = true;
Expand Down Expand Up @@ -698,3 +700,16 @@ const long *view_get_dims(struct view_s* v)
{
return v->control->dims;
}

void view_fit(struct view_s* v, int width, int height)
{
double xz = (double)(width - 5) / (double)v->control->dims[v->settings.xdim];
double yz = (double)(height - 5) / (double)v->control->dims[v->settings.ydim];

if (yz > xz / v->ui_params.aniso)
yz = xz / v->ui_params.aniso; // aniso

v->ui_params.zoom = yz;

view_set_geom(v);
}
10 changes: 6 additions & 4 deletions src/view.h
Original file line number Diff line number Diff line change
Expand Up @@ -37,20 +37,20 @@ struct view_settings_s {
enum interp_t interpolation;
};

struct view_ui_geom_params_s {
int N;
struct view_ui_params_s {
bool* selected;

double zoom;
double aniso;

bool transpose;

};


struct view_s {
const char* name;
struct view_settings_s settings;
struct view_ui_params_s ui_params;
struct view_control_s* control;
struct view_gtk_ui_s* ui;

Expand Down Expand Up @@ -93,8 +93,10 @@ extern void view_toggle_absolute_windowing(struct view_s* v);

extern void view_window_close(struct view_s* v);

extern void view_fit(struct view_s* v, int width, int height);

//
extern void view_set_geom(struct view_s* v, struct view_ui_geom_params_s gp);
extern void view_set_geom(struct view_s* v);

extern void view_refresh(struct view_s* v);
extern void view_redraw(struct view_s* v);
Expand Down

0 comments on commit 9a60208

Please sign in to comment.