aboutsummaryrefslogtreecommitdiffstats
path: root/mail/mail-threads.c
diff options
context:
space:
mode:
authorPeter Williams <peterw@src.gnome.org>2000-06-23 04:31:01 +0800
committerPeter Williams <peterw@src.gnome.org>2000-06-23 04:31:01 +0800
commit855dff022c610063a9524c19386f9e2863b88ae7 (patch)
treefc6fc22da5559cd7596d1ccb95be193b12cd0489 /mail/mail-threads.c
parenta3a3ee2b1456314989686ed356108b7356c0a272 (diff)
downloadgsoc2013-evolution-855dff022c610063a9524c19386f9e2863b88ae7.tar.gz
gsoc2013-evolution-855dff022c610063a9524c19386f9e2863b88ae7.tar.zst
gsoc2013-evolution-855dff022c610063a9524c19386f9e2863b88ae7.zip
Make the async dialogs non-modal; add cleanup callbacks in the main thread.
svn path=/trunk/; revision=3694
Diffstat (limited to 'mail/mail-threads.c')
-rw-r--r--mail/mail-threads.c134
1 files changed, 88 insertions, 46 deletions
diff --git a/mail/mail-threads.c b/mail/mail-threads.c
index c54ebd67ae..8dc6ef2d48 100644
--- a/mail/mail-threads.c
+++ b/mail/mail-threads.c
@@ -41,7 +41,8 @@
**/
typedef struct closure_s {
- void (*func)( gpointer );
+ void (*callback)( gpointer );
+ void (*cleanup)( gpointer );
gpointer data;
gchar *prettyname;
@@ -56,7 +57,10 @@ typedef struct com_msg_s {
enum com_msg_type_e { STARTING, PERCENTAGE, HIDE_PBAR, SHOW_PBAR, MESSAGE, PASSWORD, ERROR, FINISHED } type;
gfloat percentage;
gchar *message;
-
+
+ void (*func)( gpointer );
+ gpointer userdata;
+
/* Password stuff */
gchar **reply;
gboolean secret;
@@ -145,8 +149,10 @@ static void check_compipe( void );
static gboolean read_msg( GIOChannel *source, GIOCondition condition, gpointer userdata );
static void remove_next_pending( void );
static void show_error( com_msg_t *msg );
+static void show_error_clicked( void );
static void get_password( com_msg_t *msg );
static void get_password_cb( gchar *string, gpointer data );
+static void get_password_clicked( GnomeDialog *dialog, gint button, gpointer user_data );
/* Pthread code */
/* FIXME: support other thread types!!!! */
@@ -177,6 +183,7 @@ choke on this: no thread type defined
* mail_operation_try:
* @description: A user-friendly string describing the operation.
* @callback: the function to call in another thread to start the operation
+ * @cleanup: the function to call in the main thread when the callback is finished
* @user_data: extra data passed to the callback
*
* Runs a mail operation asynchronously. If no other operation is running,
@@ -192,13 +199,15 @@ choke on this: no thread type defined
**/
gboolean
-mail_operation_try( const gchar *description, void (*callback)( gpointer ), gpointer user_data )
+mail_operation_try( const gchar *description, void (*callback)( gpointer ),
+ void (*cleanup)( gpointer ), gpointer user_data )
{
closure_t *clur;
g_assert( callback );
clur = g_new( closure_t, 1 );
- clur->func = callback;
+ clur->callback = callback;
+ clur->cleanup = cleanup;
clur->data = user_data;
clur->prettyname = g_strdup( description );
@@ -541,9 +550,11 @@ static void *dispatch_func( void *data )
msg.message = clur->prettyname;
write( WRITER, &msg, sizeof( msg ) );
- (clur->func)( clur->data );
+ (clur->callback)( clur->data );
msg.type = FINISHED;
+ msg.func = clur->cleanup; /* NULL is ok */
+ msg.userdata = clur->data;
write( WRITER, &msg, sizeof( msg ) );
g_free( clur->prettyname );
@@ -592,28 +603,35 @@ static gboolean read_msg( GIOChannel *source, GIOCondition condition, gpointer u
case STARTING:
gtk_label_set_text( GTK_LABEL( queue_window_message ), msg->message );
gtk_progress_bar_update( GTK_PROGRESS_BAR( queue_window_progress ), 0.0 );
+ g_free( msg );
break;
case PERCENTAGE:
gtk_progress_bar_update( GTK_PROGRESS_BAR( queue_window_progress ), msg->percentage );
+ g_free( msg );
break;
case HIDE_PBAR:
gtk_widget_hide( GTK_WIDGET( queue_window_progress ) );
+ g_free( msg );
break;
case SHOW_PBAR:
gtk_widget_show( GTK_WIDGET( queue_window_progress ) );
+ g_free( msg );
break;
case MESSAGE:
gtk_label_set_text( GTK_LABEL( queue_window_message ),
msg->message );
g_free( msg->message );
+ g_free( msg );
break;
case PASSWORD:
g_assert( msg->reply );
g_assert( msg->success );
get_password( msg );
+ /* don't free msg! done later */
break;
case ERROR:
show_error( msg );
+ g_free( msg );
break;
/* Don't fall through; dispatch_func does the FINISHED
@@ -621,6 +639,9 @@ static gboolean read_msg( GIOChannel *source, GIOCondition condition, gpointer u
*/
case FINISHED:
+ if( msg->func )
+ (msg->func)( msg->userdata );
+
if( op_queue == NULL ) {
/* All done! */
gtk_widget_hide( queue_window );
@@ -640,6 +661,7 @@ static gboolean read_msg( GIOChannel *source, GIOCondition condition, gpointer u
/* Run run run little process */
dispatch( clur );
}
+ g_free( msg );
break;
default:
g_warning( _("Corrupted message from dispatching thread?") );
@@ -647,34 +669,10 @@ static gboolean read_msg( GIOChannel *source, GIOCondition condition, gpointer u
}
GDK_THREADS_LEAVE();
- g_free( msg );
return TRUE;
}
/**
- * show_error:
- *
- * Show the error dialog and wait for user OK
- **/
-
-static void show_error( com_msg_t *msg )
-{
- GtkWidget *err_dialog;
-
- err_dialog = gnome_error_dialog( msg->message );
- g_free( msg->message );
-
- G_LOCK( modal_lock );
-
- modal_may_proceed = FALSE;
- gnome_dialog_run_and_close( GNOME_DIALOG( err_dialog ) );
- modal_may_proceed = TRUE;
-
- g_cond_signal( modal_cond );
- G_UNLOCK( modal_lock );
-}
-
-/**
* remove_next_pending:
*
* Remove an item from the list of pending items. If
@@ -702,6 +700,42 @@ static void remove_next_pending( void )
}
/**
+ * show_error:
+ *
+ * Show the error dialog and wait for user OK
+ **/
+
+static void show_error( com_msg_t *msg )
+{
+ GtkWidget *err_dialog;
+
+ err_dialog = gnome_error_dialog( msg->message );
+ gnome_dialog_set_close( GNOME_DIALOG(err_dialog), TRUE );
+ gtk_signal_connect( GTK_OBJECT( err_dialog ), "clicked", (GtkSignalFunc) show_error_clicked, NULL );
+ g_free( msg->message );
+
+ G_LOCK( modal_lock );
+
+ modal_may_proceed = FALSE;
+ /*gnome_dialog_run_and_close( GNOME_DIALOG( err_dialog ) );*/
+ gtk_widget_show( GTK_WIDGET( err_dialog ) );
+}
+
+/**
+ * show_error_clicked:
+ *
+ * Called when the user makes hits okay to the error dialog --
+ * the dispatch thread is allowed to continue.
+ **/
+
+static void show_error_clicked( void )
+{
+ modal_may_proceed = TRUE;
+ g_cond_signal( modal_cond );
+ G_UNLOCK( modal_lock );
+}
+
+/**
* get_password:
*
* Ask for a password and put the answer in *(msg->reply)
@@ -710,12 +744,12 @@ static void remove_next_pending( void )
static void get_password( com_msg_t *msg )
{
GtkWidget *dialog;
- gint ret;
dialog = gnome_request_dialog( msg->secret, msg->message, NULL,
0, get_password_cb, msg,
NULL );
-
+ gnome_dialog_set_close( GNOME_DIALOG(dialog), TRUE );
+ gtk_signal_connect( GTK_OBJECT( dialog ), "clicked", get_password_clicked, msg );
G_LOCK( modal_lock );
@@ -724,14 +758,31 @@ static void get_password( com_msg_t *msg )
if( dialog == NULL ) {
*(msg->success) = FALSE;
*(msg->reply) = g_strdup( _("Could not create dialog box.") );
- goto done;
+ modal_may_proceed = TRUE;
+ g_cond_signal( modal_cond );
+ G_UNLOCK( modal_lock );
+ } else {
+ *(msg->reply) = NULL;
+ /*ret = gnome_dialog_run_and_close( GNOME_DIALOG(dialog) );*/
+ gtk_widget_show( GTK_WIDGET( dialog ) );
}
+}
- *(msg->reply) = NULL;
- ret = gnome_dialog_run_and_close( GNOME_DIALOG(dialog) );
+static void get_password_cb( gchar *string, gpointer data )
+{
+ com_msg_t *msg = (com_msg_t *) data;
+
+ if (string)
+ *(msg->reply) = g_strdup( string );
+ else
+ *(msg->reply) = NULL;
+}
- /* The -1 check doesn't seem to work too well. */
- if( /*ret == -1 ||*/ *(msg->reply) == NULL ) {
+static void get_password_clicked( GnomeDialog *dialog, gint button, gpointer user_data )
+{
+ com_msg_t *msg = (com_msg_t *) user_data;
+
+ if( button == 1 || *(msg->reply) == NULL ) {
*(msg->success) = FALSE;
*(msg->reply) = g_strdup( _("User cancelled query.") );
goto done;
@@ -740,17 +791,8 @@ static void get_password( com_msg_t *msg )
*(msg->success) = TRUE;
done:
+ g_free( msg );
modal_may_proceed = TRUE;
g_cond_signal( modal_cond );
G_UNLOCK( modal_lock );
}
-
-static void get_password_cb( gchar *string, gpointer data )
-{
- com_msg_t *msg = (com_msg_t *) data;
-
- if (string)
- *(msg->reply) = g_strdup( string );
- else
- *(msg->reply) = NULL;
-}