access gtk throbber frames through an interface

This changes the gtk throbber frames to be accessed through an API
  This removes teh nsgtk_throbber global and hides the implementation
  details from the rest of the code.
This commit is contained in:
Vincent Sanders 2019-08-18 14:41:31 +01:00
parent 01f3879b64
commit c0e27bd0da
4 changed files with 92 additions and 39 deletions

View File

@ -349,16 +349,20 @@ static void scaffolding_update_context(struct nsgtk_scaffolding *g)
*/
static void nsgtk_throb(void *p)
{
nserror res;
GdkPixbuf *pixbuf;
struct nsgtk_scaffolding *g = p;
if (g->throb_frame >= (nsgtk_throbber->nframes - 1)) {
g->throb_frame++; /* advance to next frame */
res = nsgtk_throbber_get_frame(g->throb_frame, &pixbuf);
if (res == NSERROR_BAD_SIZE) {
g->throb_frame = 1;
} else {
g->throb_frame++;
res = nsgtk_throbber_get_frame(g->throb_frame, &pixbuf);
}
gtk_image_set_from_pixbuf(g->throbber,
nsgtk_throbber->framedata[g->throb_frame]);
if (res == NSERROR_OK) {
gtk_image_set_from_pixbuf(g->throbber, pixbuf);
}
nsgtk_schedule(100, nsgtk_throb, p);
}
@ -2358,11 +2362,19 @@ void gui_window_start_throbber(struct gui_window* _g)
void gui_window_stop_throbber(struct gui_window* _g)
{
nserror res;
GdkPixbuf *pixbuf;
struct nsgtk_scaffolding *g = nsgtk_get_scaffold(_g);
if (g == NULL)
if (g == NULL) {
return;
}
scaffolding_update_context(g);
nsgtk_schedule(-1, nsgtk_throb, g);
g->throb_frame = 0;
if (g->buttons[STOP_BUTTON] != NULL)
g->buttons[STOP_BUTTON]->sensitivity = false;
if (g->buttons[RELOAD_BUTTON] != NULL)
@ -2370,11 +2382,11 @@ void gui_window_stop_throbber(struct gui_window* _g)
nsgtk_scaffolding_set_sensitivity(g);
if ((g->throbber == NULL) || (nsgtk_throbber == NULL) ||
(nsgtk_throbber->framedata == NULL) ||
(nsgtk_throbber->framedata[0] == NULL))
return;
gtk_image_set_from_pixbuf(g->throbber, nsgtk_throbber->framedata[0]);
res = nsgtk_throbber_get_frame(g->throb_frame, &pixbuf);
if ((res == NSERROR_OK) &&
(g->throbber != NULL)) {
gtk_image_set_from_pixbuf(g->throbber, pixbuf);
}
}

View File

@ -28,7 +28,16 @@
#include "gtk/resources.h"
#include "gtk/throbber.h"
struct nsgtk_throbber *nsgtk_throbber = NULL;
/**
* Throbber images context
*/
struct nsgtk_throbber
{
int nframes; /**< Number of frames in the throbber */
GdkPixbuf **framedata; /* pixbuf data for the frames */
};
static struct nsgtk_throbber *nsgtk_throbber = NULL;
#define THROBBER_FRAMES 9
#define THROBBER_FMT "throbber/throbber%d.png"
@ -36,10 +45,10 @@ struct nsgtk_throbber *nsgtk_throbber = NULL;
/* exported interface documented in gtk/throbber.h */
nserror nsgtk_throbber_init(void)
{
struct nsgtk_throbber *throb; /**< structure we generate */
nserror res = NSERROR_OK;
struct nsgtk_throbber *throb;
int frame;
char resname[] = THROBBER_FMT;
nserror res = NSERROR_OK;
throb = malloc(sizeof(*throb));
if (throb == NULL) {
@ -49,7 +58,7 @@ nserror nsgtk_throbber_init(void)
throb->framedata = malloc(sizeof(GdkPixbuf *) * THROBBER_FRAMES);
if (throb->framedata == NULL) {
free(throb);
return false;
return NSERROR_NOMEM;
}
for (frame = 0; frame < THROBBER_FRAMES; frame++) {
@ -73,11 +82,9 @@ nserror nsgtk_throbber_init(void)
throb->nframes = frame;
nsgtk_throbber = throb;
return res;
}
/* exported interface documented in gtk/throbber.h */
void nsgtk_throbber_finalise(void)
{
int i;
@ -91,3 +98,30 @@ void nsgtk_throbber_finalise(void)
nsgtk_throbber = NULL;
}
/* exported interface documented in gtk/throbber.h */
nserror nsgtk_throbber_get_frame(int frame, GdkPixbuf **pixbuf)
{
nserror res = NSERROR_OK;
/* ensure initialisation */
if (nsgtk_throbber == NULL) {
res = nsgtk_throbber_init();
}
if (res != NSERROR_OK) {
return res;
}
/* ensure frame in range */
if ((frame < 0) || (frame >= nsgtk_throbber->nframes)) {
return NSERROR_BAD_SIZE;
}
/* ensure there is frame data */
if (nsgtk_throbber->framedata[frame] == NULL) {
return NSERROR_INVALID;
}
*pixbuf = nsgtk_throbber->framedata[frame];
return NSERROR_OK;
}

View File

@ -16,20 +16,27 @@
* along with this program. If not, see <http://www.gnu.org/licenses/>.
*/
#ifndef __GTK_THROBBER_H__
#define __GTK_THROBBER_H__
#include <gtk/gtk.h>
struct nsgtk_throbber
{
int nframes; /**< Number of frames in the throbber */
GdkPixbuf **framedata;
};
extern struct nsgtk_throbber *nsgtk_throbber;
#ifndef NETSURF_GTK_THROBBER_H
#define NETSURF_GTK_THROBBER_H
/**
* Initialise global throbber context
*/
nserror nsgtk_throbber_init(void);
/**
* release global throbber context
*/
void nsgtk_throbber_finalise(void);
#endif /* __GTK_THROBBER_H__ */
/**
* get the pixbuf of a given frame of the throbber
*
* \param frame The frame number starting at 0 for stopped frame
* \param pixbuf updated on success
* \return NSERROR_OK and pixbuf updated on success, NSERROR_BAD_SIZE if frame
* is out of range else error code.
*/
nserror nsgtk_throbber_get_frame(int frame, GdkPixbuf **pixbuf);
#endif /* NETSURF_GTK_THROBBER_H */

View File

@ -478,23 +478,23 @@ nsgtk_toolbar_make_widget(struct nsgtk_scaffolding *g,
}
case THROBBER_ITEM: {
if ((nsgtk_throbber == NULL) ||
(nsgtk_throbber->framedata == NULL) ||
(nsgtk_throbber->framedata[0] == NULL)) {
nserror res;
GdkPixbuf *pixbuf;
res = nsgtk_throbber_get_frame(0, &pixbuf);
if (res != NSERROR_OK) {
return NULL;
}
if (edit_mode) {
w = GTK_WIDGET(gtk_tool_button_new(GTK_WIDGET(
gtk_image_new_from_pixbuf(
nsgtk_throbber->framedata[0])),
"[throbber]"));
w = GTK_WIDGET(gtk_tool_button_new(
GTK_WIDGET(gtk_image_new_from_pixbuf(pixbuf)),
"[throbber]"));
} else {
GtkWidget *image;
w = GTK_WIDGET(gtk_tool_item_new());
image = gtk_image_new_from_pixbuf(nsgtk_throbber->framedata[0]);
image = gtk_image_new_from_pixbuf(pixbuf);
if (image != NULL) {
nsgtk_widget_set_alignment(image,
GTK_ALIGN_CENTER,