I have a Raspberry Pi3 board and I have some sensors. I wanted to make a GUI and the shortest was gtk+ and C++. For example I got continuous ECG data. That function what gave me the data is on an infinite loop. I would like to update in real time the GTK labels. Could somebody solve the problem? This the code:
#include <gtk/gtk.h>
#include "eHealth.h"
#include <stdio.h>
#include <stdlib.h>
//g++ -lpthread -lrt a.cpp arduPi.o eHealth.o -o a `pkg-config gtkmm-2.4 --cflags --libs`
char c[256];
float ECG;
int i=0;
float looop(){
//here is the infinite loop
while(1){
ECG=eHealth.getECG();
}
return ECG;
}
static void button_clicked10(GtkWidget *widget, gpointer data){
gtk_label_set_text(GTK_LABEL(data), "u clicked10");
}
static void button_clicked11(GtkWidget *widget, gpointer data){
gtk_label_set_text(GTK_LABEL(data), "u clicked11");
}
int main(int argc, char* argv[])
{
gtk_init(&argc, &argv);
GtkWidget *window, *label, *button, *table, *label10;
window = gtk_window_new(GTK_WINDOW_TOPLEVEL);
g_signal_connect(window, "delete-event", G_CALLBACK(gtk_main_quit), NULL);
table = gtk_table_new(8, 3, 10); //rows, columns, honogenous
button = gtk_button_new_with_mnemonic("_Button");
ECG=eHealth.getECG();
sprintf(c,"%f", looop());
//in this label I want to print the ECG data
label = gtk_label_new(c); ///(!!!)
gtk_table_attach(GTK_TABLE(table), label, 0,1,0,1, GTK_FILL, GTK_FILL, 0,0);
gtk_table_attach(GTK_TABLE(table), button, 1,2,0,1, GTK_FILL, GTK_FILL, 0,0);
button = gtk_button_new_with_mnemonic("_Button 2");
label = gtk_label_new("Hello World 2");
gtk_table_attach(GTK_TABLE(table), label, 0,1,1,2, GTK_FILL, GTK_FILL, 0,0);
gtk_table_attach(GTK_TABLE(table), button, 1,2,1,2, GTK_FILL, GTK_FILL, 0,0);
button = gtk_button_new_with_mnemonic("_Button 3");
label = gtk_label_new("Hello World 3");
gtk_table_attach(GTK_TABLE(table), label, 0,1,2,3, GTK_FILL, GTK_FILL, 0,0);
gtk_table_attach(GTK_TABLE(table), button, 1,2,2,3, GTK_FILL, GTK_FILL, 0,0);
button = gtk_button_new_with_mnemonic("_Button 4");
label = gtk_label_new("Hello World 4");
gtk_table_attach(GTK_TABLE(table), label, 0,1,3,4, GTK_FILL, GTK_FILL, 0,0);
gtk_table_attach(GTK_TABLE(table), button, 1,2,3,4, GTK_FILL, GTK_FILL, 0,0);
button = gtk_button_new_with_mnemonic("_Button 5");
label = gtk_label_new("Hello World 5");
gtk_table_attach(GTK_TABLE(table), label, 2,3,0,1, GTK_FILL, GTK_FILL, 0,0);
gtk_table_attach(GTK_TABLE(table), button, 3,4,0,1, GTK_FILL, GTK_FILL, 0,0);
button = gtk_button_new_with_mnemonic("_Button 6");
label = gtk_label_new("Hello World 6");
gtk_table_attach(GTK_TABLE(table), label, 2,3,1,2, GTK_FILL, GTK_FILL, 0,0);
gtk_table_attach(GTK_TABLE(table), button, 3,4,1,2, GTK_FILL, GTK_FILL, 0,0);
button = gtk_button_new_with_mnemonic("_Button 7");
label10 = gtk_label_new("Hello World 7");
gtk_table_attach(GTK_TABLE(table), label10, 2,3,2,3, GTK_FILL, GTK_FILL, 0,0);
gtk_table_attach(GTK_TABLE(table), button, 3,4,2,3, GTK_FILL, GTK_FILL, 0,0);
g_signal_connect(button, "clicked", G_CALLBACK(button_clicked10), (gpointer)label10);
button = gtk_button_new_with_mnemonic("_Button 8");
label = gtk_label_new("Hello World 8");
gtk_table_attach(GTK_TABLE(table), label, 2,3,3,4, GTK_FILL, GTK_FILL, 0,0);
gtk_table_attach(GTK_TABLE(table), button, 3,4,3,4, GTK_FILL, GTK_FILL, 0,0);
button = gtk_button_new_with_mnemonic("_Button 9");
gtk_table_attach(GTK_TABLE(table), button, 0,4,4,5, GTK_FILL, GTK_FILL, 0,0);
button = gtk_button_new_with_mnemonic("_Button 10");
gtk_table_attach(GTK_TABLE(table), button, 0,4,5,6, GTK_FILL, GTK_FILL, 0,0);
button = gtk_button_new_with_mnemonic("_Button 11");
gtk_table_attach(GTK_TABLE(table), button, 0,4,6,7, GTK_FILL, GTK_FILL, 0,0);
g_signal_connect(button, "clicked", G_CALLBACK(button_clicked11), (gpointer)label);
button = gtk_button_new_with_mnemonic("_Button 10");
gtk_table_attach(GTK_TABLE(table), button, 0,4,7,8, GTK_FILL, GTK_FILL, 0,0);
g_signal_connect(button, "clicked", G_CALLBACK(button_clicked10), (gpointer)label);
gtk_container_add(GTK_CONTAINER(window), table);
gtk_widget_set_size_request(window, 500, 500);
gtk_widget_show_all(window);
gtk_main();
return 0;
}
GTK+ and its underlying libraries like GLib require to run their own main event loop. Any code of yours that alters GTK+/GLib stuff needs to then return, so that GTK+/GLib can deal with what you've asked them to do. If you block them using your own while
or other loop, they can't do anything.
I won't dwell on this further as it's basic stuff; see, for example:
You can resolve your question by using a GLib timeout source, to run the function that updates your label, on a desired schedule. There are g_timeout_add()
, g_timeout_add_seconds()
, and others documented at that page.
Here's a toy example:
#include <gtk/gtk.h>
static gboolean
on_timeout (gpointer user_data)
{
static unsigned f_times = 0;
GtkLabel *label = GTK_LABEL (user_data);
++f_times;
gchar *text = g_strdup_printf ("I have been updated %u times", f_times);
gtk_label_set_label (label, text);
g_free (text);
return G_SOURCE_CONTINUE; /* or G_SOURCE_REMOVE when you want to stop */
}
int
main (int argc,
char **argv)
{
gtk_init (&argc, &argv);
GtkWidget *label = gtk_label_new ("not updated yet...");
g_timeout_add (1000 /* milliseconds */, on_timeout, label);
GtkWidget *window = gtk_window_new (GTK_WINDOW_TOPLEVEL);
gtk_container_add (GTK_CONTAINER (window), label);
g_signal_connect (window, "destroy", G_CALLBACK (gtk_main_quit), NULL);
gtk_widget_show_all (window);
gtk_main ();
return 0;
}
Some other points:
GtkTable
is deprecated in GTK+ 3 and gone in GTK+ 4; you should be using GtkGrid
instead. See Migrating from other containers to GtkGrid gtkmm
, the official C++ bindings for GTK+, yet you have written all your code to call the C library directly. That seems a bit odd. gtkmm
is great, so I can recommend it, but if you don't want it, then you should state your intent by using C and linking against GTK+. But obviously, my code assumes you really want C. I achieve this using GTK2, check https://www.linuxtopia.org/online_books/gui_toolkit_guides/gtk+_gnome_application_development/sec-mainloop.html
You can use gtk_main_iteration();
#include <gtkmm/main.h>
#include <gtkmm/window.h>
#include <gtkmm.h>
int main(int argc, char** argv)
{
Gtk::Main kit(argc, argv);
Gtk::Window win;
Gtk::Frame m_Frame;
m_Frame.set_label("Gtk::Frame Widget");
win.add(m_Frame);
win.set_default_size(900,600);
win.set_title("Loop App");
win.set_border_width(10);
win.show_all_children();
```win.show();
while(1){
while (gtk_events_pending())
gtk_main_iteration();
/*Do your work*/
/*Do your work 2*/
}
}
The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.