Skip to content

Commit

Permalink
Remove program logic from gtk_ui.c
Browse files Browse the repository at this point in the history
To be able to easily switch UI backends, the UI implementation
should contain as few "application logic" as possible.
  • Loading branch information
schaten committed Mar 5, 2024
1 parent 8b0c7fa commit 34141b0
Show file tree
Hide file tree
Showing 4 changed files with 78 additions and 109 deletions.
104 changes: 37 additions & 67 deletions src/gtk_ui.c
Original file line number Diff line number Diff line change
Expand Up @@ -10,6 +10,8 @@
#include <libgen.h>
#include <string.h>

#include <stdatomic.h>

#include "gtk_ui.h"
#include "view.h"

Expand Down Expand Up @@ -54,6 +56,8 @@ struct view_gtk_ui_s {
GtkWidget *dialog; // Save dialog
GtkFileChooser *chooser; // Save dialog
GtkWindow *window;

atomic_flag in_callback;
};


Expand Down Expand Up @@ -221,6 +225,19 @@ extern gboolean motion_callback(GtkWidget* /*widget*/, GdkEventMotion *event, gp
return FALSE;
}

extern gboolean click_callback(GtkWidget* /*widget*/, GdkEventButton *event, gpointer data)
{
struct view_s* v = data;

if (event->button == GDK_BUTTON_PRIMARY)
view_click(v, event->x, event->y, 1);

if (event->button == GDK_BUTTON_SECONDARY)
view_click(v, event->x, event->y, 2);

return FALSE;
}

extern gboolean show_hide_callback(GtkWidget *widget, GtkCheckButton* button)
{
gboolean flag = gtk_toggle_tool_button_get_active(GTK_TOGGLE_TOOL_BUTTON(button));
Expand Down Expand Up @@ -269,8 +286,6 @@ extern gboolean toggle_sync_callback(GtkToggleButton* /*button*/, gpointer data)
extern gboolean toggle_plot_callback(GtkToggleButton* /*button*/, gpointer data)
{
struct view_s* v = data;
v->settings.plot = !v->settings.plot;

view_toggle_plot(v);

return FALSE;
Expand All @@ -288,19 +303,6 @@ extern gboolean toogle_absolute_windowing_callback(GtkToggleToolButton* button,
return FALSE;
}

extern gboolean click_callback(GtkWidget* /*widget*/, GdkEventButton *event, gpointer data)
{
struct view_s* v = data;

if (event->button == GDK_BUTTON_PRIMARY)
view_click(v, event->x, event->y, 1);

if (event->button == GDK_BUTTON_SECONDARY)
view_click(v, event->x, event->y, 2);

return FALSE;
}



void ui_trigger_redraw(struct view_s* v)
Expand Down Expand Up @@ -330,23 +332,6 @@ void ui_pull_window(struct view_s* v)
window_callback(NULL, v);
}

void ui_set_limits(struct view_s* v)
{
gtk_adjustment_set_upper(v->ui->gtk_winhigh, v->win_high_max);
gtk_adjustment_set_upper(v->ui->gtk_winlow, v->win_low_max);
}

void ui_set_values(struct view_s* v)
{
gtk_adjustment_set_value(v->ui->gtk_winlow, v->settings.winlow);
gtk_adjustment_set_value(v->ui->gtk_winhigh, v->settings.winhigh);
}

void ui_set_mode(struct view_s* v)
{
gtk_combo_box_set_active(v->ui->gtk_mode, v->settings.mode);
}

void ui_set_msg(struct view_s* v, const char* msg)
{
gtk_entry_set_text(v->ui->gtk_entry, msg);
Expand All @@ -360,6 +345,8 @@ void ui_window_new(struct view_s* v, int N, const long dims[N])
for (int i = 0; i < DIMS; i++)
v->ui_params.selected[i] = (i == v->settings.xdim || i == v->settings.ydim) ? true : false;

atomic_flag_clear(&v->ui->in_callback);

v->ui->source = NULL;

GtkBuilder* builder = gtk_builder_new();
Expand Down Expand Up @@ -454,54 +441,37 @@ bool gtk_ui_save_png(struct view_s* v, const char* filename)
return false;
}

void ui_set_windowing(struct view_s* v, double max, double inc, int digits)
{
gtk_adjustment_configure(v->ui->gtk_winhigh, v->settings.winhigh, 0, max, inc, gtk_adjustment_get_page_increment(v->ui->gtk_winhigh), gtk_adjustment_get_page_size(v->ui->gtk_winhigh));
gtk_adjustment_configure(v->ui->gtk_winlow, v->settings.winlow, 0, max, inc, gtk_adjustment_get_page_increment(v->ui->gtk_winlow), gtk_adjustment_get_page_size(v->ui->gtk_winlow));
gtk_spin_button_set_digits(v->ui->gtk_button_winhigh, digits);
gtk_spin_button_set_digits(v->ui->gtk_button_winlow, digits);

gtk_widget_set_visible(GTK_WIDGET(v->ui->toolbar_scale1), v->settings.absolute_windowing ? FALSE : TRUE);
gtk_widget_set_visible(GTK_WIDGET(v->ui->toolbar_scale2), v->settings.absolute_windowing ? FALSE : TRUE);
gtk_widget_set_visible(GTK_WIDGET(v->ui->toolbar_button1), v->settings.absolute_windowing ? TRUE : FALSE);
gtk_widget_set_visible(GTK_WIDGET(v->ui->toolbar_button2), v->settings.absolute_windowing ? TRUE : FALSE);
}

void ui_set_position(struct view_s* v, unsigned int dim, unsigned int p)
{
v->settings.pos[dim] = p;

gtk_adjustment_set_value(v->ui->gtk_posall[dim], p);

for (struct view_s* v2 = v->next; v2 != v; v2 = v2->next)
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)
if (!atomic_flag_test_and_set(&v->ui->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);
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;
gtk_adjustment_set_value(v->ui->gtk_posall[j], v->settings.pos[j]);
}

gtk_widget_set_sensitive(GTK_WIDGET(v->ui->gtk_mode),
v->settings.plot ? FALSE : TRUE);

gtk_combo_box_set_active(v->ui->gtk_mode, v->settings.mode);

gtk_adjustment_configure(v->ui->gtk_winhigh, v->settings.winhigh, 0, v->ui_params.windowing_max, v->ui_params.windowing_inc, gtk_adjustment_get_page_increment(v->ui->gtk_winhigh), gtk_adjustment_get_page_size(v->ui->gtk_winhigh));
gtk_adjustment_configure(v->ui->gtk_winlow, v->settings.winlow, 0, v->ui_params.windowing_max, v->ui_params.windowing_inc, gtk_adjustment_get_page_increment(v->ui->gtk_winlow), gtk_adjustment_get_page_size(v->ui->gtk_winlow));
gtk_spin_button_set_digits(v->ui->gtk_button_winhigh, v->ui_params.windowing_digits);
gtk_spin_button_set_digits(v->ui->gtk_button_winlow, v->ui_params.windowing_digits);

gtk_widget_set_visible(GTK_WIDGET(v->ui->toolbar_scale1), v->settings.absolute_windowing ? FALSE : TRUE);
gtk_widget_set_visible(GTK_WIDGET(v->ui->toolbar_scale2), v->settings.absolute_windowing ? FALSE : TRUE);
gtk_widget_set_visible(GTK_WIDGET(v->ui->toolbar_button1), v->settings.absolute_windowing ? TRUE : FALSE);
gtk_widget_set_visible(GTK_WIDGET(v->ui->toolbar_button2), v->settings.absolute_windowing ? TRUE : FALSE);

atomic_flag_clear(&v->ui->in_callback);
}
10 changes: 1 addition & 9 deletions src/gtk_ui.h
Original file line number Diff line number Diff line change
Expand Up @@ -7,18 +7,10 @@ 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_position(struct view_s* v, unsigned int dim, unsigned int p);

extern void ui_set_limits(struct view_s* v);
extern void ui_set_values(struct view_s* v);
extern void ui_set_windowing(struct view_s* v, double max, double inc, int digits);

extern void ui_set_mode(struct view_s* v);
void ui_set_params(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]);

extern void ui_main();
Expand Down
52 changes: 30 additions & 22 deletions src/view.c
Original file line number Diff line number Diff line change
Expand Up @@ -105,7 +105,7 @@ void update_geom(struct view_s* v)
(*v->control->geom_current)[2][0], (*v->control->geom_current)[2][1], (*v->control->geom_current)[2][2]);
}

void view_sync_windowing(struct view_s* v)
void view_sync(struct view_s* v)
{

for (struct view_s* v2 = v->next; v2 != v; v2 = v2->next) {
Expand All @@ -115,8 +115,7 @@ void view_sync_windowing(struct view_s* v)
v2->settings.mode = v->settings.mode;
v2->settings.winlow = v->settings.winlow;
v2->settings.winhigh= v->settings.winhigh;
ui_set_values(v2);
ui_set_mode(v2);
ui_set_params(v2);
}
}
}
Expand Down Expand Up @@ -150,23 +149,16 @@ void view_refresh(struct view_s* v)

if (0 == v->control->max) {

v->win_high_max = max;
v->win_low_max = max;
v->settings.winhigh = max;
v->control->max = max;

ui_set_limits(v);
ui_set_values(v);
}

if (v->control->max < max) {

v->win_high_max = max;
v->win_low_max = max;
if (v->control->max < max)
v->control->max = max;

ui_set_limits(v);
}
v->ui_params.windowing_max = v->control->max;
ui_set_params(v);

} else {

long size = md_calc_size(DIMS, v->control->dims);
Expand Down Expand Up @@ -266,7 +258,7 @@ void view_geom(struct view_s* v)

void view_window(struct view_s* v)
{
view_sync_windowing(v);
view_sync(v);
v->rgb_invalid = true;

ui_trigger_redraw(v);
Expand Down Expand Up @@ -485,7 +477,9 @@ struct view_s* create_view(const char* name, const long pos[DIMS], const long di
v->control = xmalloc(sizeof(struct view_control_s));
v->ui = NULL;
v->ui_params.selected = NULL;
v->ui_params.windowing_max = v->control->max;
v->settings.pos = NULL;
v->settings.mode = 0;

v->next = v->prev = v;
v->sync = true;
Expand Down Expand Up @@ -552,9 +546,11 @@ static void view_set_windowing(struct view_s* v)
{
double max = v->settings.absolute_windowing ? v->control->max : 1;
max = MIN(1.e10, max);
double inc = exp(log(10) * round(log(max) / log(10.))) * 0.001;
int digits = MAX(3, 3 - (int)round(log(max) / log(10.)));
ui_set_windowing(v, max, inc, digits);
v->ui_params.windowing_max = max;
v->ui_params.windowing_inc = exp(log(10) * round(log(max) / log(10.))) * 0.001;
v->ui_params.windowing_digits = MAX(3, 3 - (int)round(log(max) / log(10.)));

ui_set_params(v);
}

void view_toggle_absolute_windowing(struct view_s* v)
Expand Down Expand Up @@ -588,6 +584,17 @@ void view_toggle_absolute_windowing(struct view_s* v)
view_set_windowing(v);
}

static void view_set_position(struct view_s* v, float pos[DIMS])
{
v->settings.pos[v->settings.xdim] = pos[v->settings.xdim];
v->settings.pos[v->settings.ydim] = pos[v->settings.ydim];
for (int i = 0; i < DIMS; i++)
printf("%ld ", v->settings.pos[i]);
printf("\n");
ui_set_params(v);
view_sync(v);
}

void view_click(struct view_s* v, int x, int y, int button)
{
struct xy_s xy = { x, y };
Expand All @@ -610,8 +617,7 @@ void view_click(struct view_s* v, int x, int y, int button)
v->settings.cross_hair = true;
v->control->status_bar = true;

ui_set_position(v, v->settings.xdim, pos[v->settings.xdim]);
ui_set_position(v, v->settings.ydim, pos[v->settings.ydim]);
view_set_position(v, pos);
}
}

Expand All @@ -638,8 +644,8 @@ void view_motion(struct view_s* v, int x, int y, double inc_low, double inc_high

v->settings.winlow = low;
v->settings.winhigh = high;
ui_set_values(v);
view_sync_windowing(v);
ui_set_params(v);
view_sync(v);
}
}

Expand Down Expand Up @@ -714,6 +720,8 @@ void view_fit(struct view_s* v, int width, int height)

void view_toggle_plot(struct view_s* v)
{
v->settings.plot = !v->settings.plot;

v->invalid = true;
ui_set_params(v);
ui_trigger_redraw(v);
Expand Down
21 changes: 10 additions & 11 deletions src/view.h
Original file line number Diff line number Diff line change
Expand Up @@ -44,6 +44,11 @@ struct view_ui_params_s {
double aniso;

bool transpose;

int windowing_digits;
double windowing_max;
double windowing_inc;

};


Expand All @@ -62,10 +67,6 @@ struct view_s {
struct view_s* next;
struct view_s* prev;
bool sync;

// shared state (owned by controller)
double win_high_max;
double win_low_max;
};


Expand All @@ -82,23 +83,21 @@ extern void view_geom(struct view_s* v);
extern void view_refresh(struct view_s* v);
extern void view_window(struct view_s* v);

extern void view_draw(struct view_s* v);

extern bool view_save_png(struct view_s* v, const char *filename);
extern bool view_save_pngmovie(struct view_s* v, const char *folder);

extern void view_motion(struct view_s* v, int x, int y, double inc_low, double inc_high, int button);

extern struct view_s* view_window_clone(struct view_s* v, const long pos[DIMS]);

extern void view_draw(struct view_s* v);
extern void view_click(struct view_s* v, int x, int y, int button);

extern void view_toggle_plot(struct view_s* v);
extern void view_toggle_absolute_windowing(struct view_s* v);

extern void view_add_geometry(struct view_s* v, unsigned long flags, const float (*geom)[3][3]);

extern void view_click(struct view_s* v, int x, int y, int button);


extern void view_toggle_absolute_windowing(struct view_s* v);
extern struct view_s* view_window_clone(struct view_s* v, const long pos[DIMS]);

extern void view_window_close(struct view_s* v);

Expand Down

0 comments on commit 34141b0

Please sign in to comment.