2006-03-30  Alexander Larsson  <alexl@redhat.com>

	* gtk/gtk.symbols:
	Update

	* gtk/gtkprintbackend.[ch]:
	Add dnotify to gtk_print_backend_print_stream

	* gtk/gtkprinter-private.h:
	Declare gtk_print_job_set_status

	* gtk/gtkprinter.[ch]:
	Remove gtk_printer_prepare_job.

	* gtk/gtkprintjob.[ch]:
	Now you create print job directly with gtk_print_job_new() and
	they'll be prepared automatically.
	Add status_changed signal and get_status.
	Add gtk_print_job_set_source_file to allow sending a file.

	* gtk/gtkprintoperation-private.h:
	Add destroy notify for platform_data.
	Declare _gtk_print_operation_set_status.

	* gtk/gtkprintoperation-unix.c:
	Hook up status change handling.
	Use the new way to get a print job.

	* gtk/gtkprintoperation.[ch]:
	Add status_changed signal and get_status/is_finished.


	* modules/printbackends/cups/gtkprintbackendcups.c:
	* modules/printbackends/lpr/gtkprintbackendlpr.c:
	* modules/printbackends/pdf/gtkprintbackendpdf.c:
	Update to use new APIs and set status on the job.
	Cups polls for the status.

	* tests/print-editor.c:
	Track the print operations in the status bar.
This commit is contained in:
Alexander Larsson
2006-03-30 16:02:30 +00:00
committed by Alexander Larsson
parent d489c6835d
commit e36e4e0670
19 changed files with 698 additions and 192 deletions

View File

@@ -1,3 +1,44 @@
2006-03-30 Alexander Larsson <alexl@redhat.com>
* gtk/gtk.symbols:
Update
* gtk/gtkprintbackend.[ch]:
Add dnotify to gtk_print_backend_print_stream
* gtk/gtkprinter-private.h:
Declare gtk_print_job_set_status
* gtk/gtkprinter.[ch]:
Remove gtk_printer_prepare_job.
* gtk/gtkprintjob.[ch]:
Now you create print job directly with gtk_print_job_new() and
they'll be prepared automatically.
Add status_changed signal and get_status.
Add gtk_print_job_set_source_file to allow sending a file.
* gtk/gtkprintoperation-private.h:
Add destroy notify for platform_data.
Declare _gtk_print_operation_set_status.
* gtk/gtkprintoperation-unix.c:
Hook up status change handling.
Use the new way to get a print job.
* gtk/gtkprintoperation.[ch]:
Add status_changed signal and get_status/is_finished.
* modules/printbackends/cups/gtkprintbackendcups.c:
* modules/printbackends/lpr/gtkprintbackendlpr.c:
* modules/printbackends/pdf/gtkprintbackendpdf.c:
Update to use new APIs and set status on the job.
Cups polls for the status.
* tests/print-editor.c:
Track the print operations in the status bar.
2006-03-30 Alexander Larsson <alexl@redhat.com>
* gtk/Makefile.am:

View File

@@ -1,3 +1,44 @@
2006-03-30 Alexander Larsson <alexl@redhat.com>
* gtk/gtk.symbols:
Update
* gtk/gtkprintbackend.[ch]:
Add dnotify to gtk_print_backend_print_stream
* gtk/gtkprinter-private.h:
Declare gtk_print_job_set_status
* gtk/gtkprinter.[ch]:
Remove gtk_printer_prepare_job.
* gtk/gtkprintjob.[ch]:
Now you create print job directly with gtk_print_job_new() and
they'll be prepared automatically.
Add status_changed signal and get_status.
Add gtk_print_job_set_source_file to allow sending a file.
* gtk/gtkprintoperation-private.h:
Add destroy notify for platform_data.
Declare _gtk_print_operation_set_status.
* gtk/gtkprintoperation-unix.c:
Hook up status change handling.
Use the new way to get a print job.
* gtk/gtkprintoperation.[ch]:
Add status_changed signal and get_status/is_finished.
* modules/printbackends/cups/gtkprintbackendcups.c:
* modules/printbackends/lpr/gtkprintbackendlpr.c:
* modules/printbackends/pdf/gtkprintbackendpdf.c:
Update to use new APIs and set status on the job.
Cups polls for the status.
* tests/print-editor.c:
Track the print operations in the status bar.
2006-03-30 Alexander Larsson <alexl@redhat.com>
* gtk/Makefile.am:

View File

@@ -2,9 +2,8 @@ Temporary file with stuff left to do in the printing work:
Highlevel API:
* Add a way to make the cairo printing callbacks (optionally) happen in a thread
* Add API to EggPrintOperation to handle job status feedback while printing.
Needs something like "job_status_changed" and "job_finished" signals
Also during page generation. Should have progress bar?
* Do we want a progress bar during page generation?
At least a signal tracking the page generation progress.
* Add API to allow the app to add a custom tab with gtk+ widgets to the
print dialog. We can hopefully implement this on osx & win32.
* Want a print preview API.
@@ -13,6 +12,7 @@ Highlevel API:
Lowlevel API:
* Figure out the best way to configure module loading (textfile, gtkrc or
just frob the modules directory)
* Maybe we want gtk_print_job_cancel?
PDF backend:
* Change to using a GtkFileChooserEntry to get file names when we move to
@@ -41,7 +41,7 @@ General:
* use filechooserentry => J5
* get the right DPI from the printer into cairo
* gets errors on alex laptop
* general print to file (ps+pdf)
* general print to file module (ps+pdf)
Page setting dialog:
* insensitive margins-from-printer if list is empty

View File

@@ -2558,7 +2558,6 @@ gtk_printer_get_icon_name
gtk_printer_get_job_count
gtk_printer_is_active
gtk_printer_is_virtual
gtk_printer_prepare_job
#endif
#endif
@@ -2605,9 +2604,11 @@ gtk_print_job_get_type G_GNUC_CONST
gtk_print_job_new
gtk_print_job_get_settings
gtk_print_job_get_printer
gtk_print_job_get_title
gtk_print_job_get_status
gtk_print_job_set_source_file
gtk_print_job_get_surface
gtk_print_job_send
gtk_print_job_prepare
#endif
#endif
@@ -2628,6 +2629,8 @@ gtk_print_operation_set_unit
gtk_print_operation_set_show_dialog
gtk_print_operation_set_pdf_target
gtk_print_operation_run
gtk_print_operation_get_status
gtk_print_operation_is_finished
#endif
#endif

View File

@@ -358,19 +358,19 @@ gtk_print_backend_find_printer (GtkPrintBackend *print_backend,
void
gtk_print_backend_print_stream (GtkPrintBackend *print_backend,
GtkPrintJob *job,
const gchar *title,
gint data_fd,
GtkPrintJobCompleteFunc callback,
gpointer user_data)
gpointer user_data,
GDestroyNotify dnotify)
{
g_return_if_fail (GTK_IS_PRINT_BACKEND (print_backend));
return GTK_PRINT_BACKEND_GET_IFACE (print_backend)->print_stream (print_backend,
job,
title,
data_fd,
callback,
user_data);
GTK_PRINT_BACKEND_GET_IFACE (print_backend)->print_stream (print_backend,
job,
data_fd,
callback,
user_data,
dnotify);
}
#define __GTK_PRINT_BACKEND_C__

View File

@@ -67,10 +67,10 @@ struct _GtkPrintBackendIface
const gchar *printer_name);
void (*print_stream) (GtkPrintBackend *print_backend,
GtkPrintJob *job,
const gchar *title,
gint data_fd,
GtkPrintJobCompleteFunc callback,
gpointer user_data);
gpointer user_data,
GDestroyNotify dnotify);
/* Printer methods: */
void (*printer_request_details) (GtkPrinter *printer);
@@ -112,10 +112,10 @@ GtkPrinter *gtk_print_backend_find_printer (GtkPrintBackend *print_b
const gchar *printer_name);
void gtk_print_backend_print_stream (GtkPrintBackend *print_backend,
GtkPrintJob *job,
const gchar *title,
gint data_fd,
GtkPrintJobCompleteFunc callback,
gpointer user_data);
gpointer user_data,
GDestroyNotify dnotify);
GList * gtk_print_backend_load_modules (void);

View File

@@ -23,7 +23,7 @@
#include <glib.h>
#include "gtkprinter.h"
#include "gtkprintsettings.h"
#include "gtkprintoperation.h"
#include "gtkprinteroptionset.h"
#include "gtkpagesetup.h"
@@ -73,5 +73,10 @@ void _gtk_printer_get_hard_margins (GtkPrinter
double *right);
GHashTable * _gtk_printer_get_custom_widgets (GtkPrinter *printer);
/* GtkPrintJob private methods: */
void gtk_print_job_set_status (GtkPrintJob *job,
GtkPrintStatus status);
G_END_DECLS
#endif /* __GTK_PRINT_OPERATION_PRIVATE_H__ */

View File

@@ -305,29 +305,6 @@ gtk_printer_is_virtual (GtkPrinter *printer)
return printer->priv->is_virtual;
}
GtkPrintJob *
gtk_printer_prepare_job (GtkPrinter *printer,
GtkPrintSettings *settings,
GtkPageSetup *page_setup,
const gchar *title,
GError **error)
{
GtkPrintJob *job;
job = gtk_print_job_new (title,
settings,
page_setup,
printer);
if (!gtk_print_job_prepare (job, error))
{
g_object_unref (G_OBJECT (job));
job = NULL;
}
return job;
}
void
_gtk_printer_request_details (GtkPrinter *printer)
{

View File

@@ -21,8 +21,8 @@
#include <glib-object.h>
#include <cairo.h>
#include "gtkprintsettings.h"
#include "gtkpagesetup.h"
#include <gtk/gtkprintsettings.h>
#include <gtk/gtkpagesetup.h>
G_BEGIN_DECLS
@@ -78,12 +78,6 @@ gint gtk_printer_get_job_count (GtkPrinter *printer);
gboolean gtk_printer_is_active (GtkPrinter *printer);
gboolean gtk_printer_is_virtual (GtkPrinter *printer);
GtkPrintJob *gtk_printer_prepare_job (GtkPrinter *printer,
GtkPrintSettings *settings,
GtkPageSetup *page_setup,
const gchar *title,
GError **error);
G_END_DECLS
#endif /* __GTK_PRINTER_H__ */

View File

@@ -21,12 +21,15 @@
#include <stdlib.h>
#include <string.h>
#include <stdio.h>
#include <fcntl.h>
#include <errno.h>
#ifdef HAVE_UNISTD_H
#include <unistd.h>
#endif
#include <sys/types.h>
#include <sys/stat.h>
#include <glib/gstdio.h>
#include "gtkintl.h"
#include "gtkprivate.h"
@@ -35,37 +38,49 @@
#include "gtkprintbackend.h"
#include "gtkalias.h"
#ifndef O_BINARY
#define O_BINARY 0
#endif
struct _GtkPrintJobPrivate
{
gchar *title;
gint cache_fd;
int spool_file_fd;
cairo_surface_t *surface;
GtkPrintSettings *settings;
GtkPageSetup *page_setup;
GtkPrintStatus status;
GtkPrintBackend *backend;
GtkPrinter *printer;
GtkPrintSettings *settings;
GtkPageSetup *page_setup;
gint printer_set : 1;
gint page_setup_set : 1;
gint settings_set : 1;
gint prepped : 1;
};
#define GTK_PRINT_JOB_GET_PRIVATE(o) \
(G_TYPE_INSTANCE_GET_PRIVATE ((o), GTK_TYPE_PRINT_JOB, GtkPrintJobPrivate))
static void gtk_print_job_finalize (GObject *object);
static void gtk_print_job_set_property (GObject *object,
guint prop_id,
const GValue *value,
GParamSpec *pspec);
static void gtk_print_job_get_property (GObject *object,
guint prop_id,
GValue *value,
GParamSpec *pspec);
static void gtk_print_job_finalize (GObject *object);
static void gtk_print_job_set_property (GObject *object,
guint prop_id,
const GValue *value,
GParamSpec *pspec);
static void gtk_print_job_get_property (GObject *object,
guint prop_id,
GValue *value,
GParamSpec *pspec);
static GObject* gtk_print_job_constructor (GType type,
guint n_construct_properties,
GObjectConstructParam *construct_params);
enum {
STATUS_CHANGED,
LAST_SIGNAL
};
enum {
PROP_0,
@@ -75,6 +90,8 @@ enum {
GTK_PRINT_JOB_PROP_SETTINGS
};
static guint signals[LAST_SIGNAL] = { 0 };
G_DEFINE_TYPE (GtkPrintJob, gtk_print_job, G_TYPE_OBJECT);
static void
@@ -84,6 +101,7 @@ gtk_print_job_class_init (GtkPrintJobClass *class)
object_class = (GObjectClass *) class;
object_class->finalize = gtk_print_job_finalize;
object_class->constructor = gtk_print_job_constructor;
object_class->set_property = gtk_print_job_set_property;
object_class->get_property = gtk_print_job_get_property;
@@ -95,7 +113,7 @@ gtk_print_job_class_init (GtkPrintJobClass *class)
P_("Title"),
P_("Title of the print job"),
NULL,
GTK_PARAM_WRITABLE |
GTK_PARAM_READWRITE |
G_PARAM_CONSTRUCT_ONLY));
g_object_class_install_property (G_OBJECT_CLASS (class),
@@ -124,15 +142,24 @@ gtk_print_job_class_init (GtkPrintJobClass *class)
GTK_TYPE_PAGE_SETUP,
GTK_PARAM_READWRITE |
G_PARAM_CONSTRUCT_ONLY));
signals[STATUS_CHANGED] =
g_signal_new ("status-changed",
G_TYPE_FROM_CLASS (class),
G_SIGNAL_RUN_LAST,
G_STRUCT_OFFSET (GtkPrintJobClass, status_changed),
NULL, NULL,
g_cclosure_marshal_VOID__VOID,
G_TYPE_NONE, 0);
}
static void
gtk_print_job_init (GtkPrintJob *print_job)
{
print_job->priv = GTK_PRINT_JOB_GET_PRIVATE (print_job);
print_job->priv->cache_fd = 0;
print_job->priv->spool_file_fd = -1;
print_job->priv->title = NULL;
print_job->priv->title = g_strdup ("");
print_job->priv->surface = NULL;
print_job->priv->backend = NULL;
print_job->priv->printer = NULL;
@@ -140,7 +167,7 @@ gtk_print_job_init (GtkPrintJob *print_job)
print_job->priv->printer_set = FALSE;
print_job->priv->settings_set = FALSE;
print_job->priv->page_setup_set = FALSE;
print_job->priv->status = GTK_PRINT_STATUS_INITIAL;
print_job->print_pages = GTK_PRINT_PAGES_ALL;
print_job->page_ranges = NULL;
@@ -153,15 +180,49 @@ gtk_print_job_init (GtkPrintJob *print_job)
print_job->rotate_to_orientation = FALSE;
}
static GObject*
gtk_print_job_constructor (GType type,
guint n_construct_properties,
GObjectConstructParam *construct_params)
{
GtkPrintJob *job;
GObject *object;
object =
G_OBJECT_CLASS (gtk_print_job_parent_class)->constructor (type,
n_construct_properties,
construct_params);
job = GTK_PRINT_JOB (object);
g_assert (job->priv->printer_set &&
job->priv->settings_set &&
job->priv->page_setup_set);
_gtk_printer_prepare_for_print (job->priv->printer,
job,
job->priv->settings,
job->priv->page_setup);
return object;
}
static void
gtk_print_job_finalize (GObject *object)
{
GtkPrintJob *print_job;
g_return_if_fail (object != NULL);
GtkPrintJob *print_job = GTK_PRINT_JOB (object);
print_job = GTK_PRINT_JOB (object);
if (print_job->priv->cache_fd != 0)
close (print_job->priv->cache_fd);
if (print_job->priv->spool_file_fd > 0)
{
close (print_job->priv->spool_file_fd);
print_job->priv->spool_file_fd = -1;
}
if (print_job->priv->backend)
g_object_unref (G_OBJECT (print_job->priv->backend));
@@ -181,6 +242,9 @@ gtk_print_job_finalize (GObject *object)
g_free (print_job->page_ranges);
print_job->page_ranges = NULL;
g_free (print_job->priv->title);
print_job->priv->title = NULL;
if (G_OBJECT_CLASS (gtk_print_job_parent_class)->finalize)
G_OBJECT_CLASS (gtk_print_job_parent_class)->finalize (object);
}
@@ -196,30 +260,28 @@ gtk_print_job_finalize (GObject *object)
**/
GtkPrintJob *
gtk_print_job_new (const gchar *title,
GtkPrinter *printer,
GtkPrintSettings *settings,
GtkPageSetup *page_setup,
GtkPrinter *printer)
GtkPageSetup *page_setup)
{
GObject *result;
result = g_object_new (GTK_TYPE_PRINT_JOB,
"title", title,
"printer", printer,
"settings", settings,
"page-setup", page_setup,
NULL);
return (GtkPrintJob *) result;
}
GtkPrintSettings *
gtk_print_job_get_settings (GtkPrintJob *print_job)
{
g_assert (GTK_IS_PRINT_SETTINGS (print_job->priv->settings));
g_return_val_if_fail (GTK_IS_PRINT_JOB (print_job), NULL);
return print_job->priv->settings;
}
GtkPrinter *
gtk_print_job_get_printer (GtkPrintJob *print_job)
{
@@ -228,53 +290,91 @@ gtk_print_job_get_printer (GtkPrintJob *print_job)
return print_job->priv->printer;
}
cairo_surface_t *
gtk_print_job_get_surface (GtkPrintJob *print_job)
const char *
gtk_print_job_get_title (GtkPrintJob *print_job)
{
g_return_val_if_fail (GTK_IS_PRINT_JOB (print_job), NULL);
return print_job->priv->surface;
return print_job->priv->title;
}
gboolean
gtk_print_job_prepare (GtkPrintJob *job,
GError **error)
GtkPrintStatus
gtk_print_job_get_status (GtkPrintJob *print_job)
{
g_return_val_if_fail (GTK_IS_PRINT_JOB (print_job), GTK_PRINT_STATUS_FINISHED);
return print_job->priv->status;
}
void
gtk_print_job_set_status (GtkPrintJob *job,
GtkPrintStatus status)
{
if (job->priv->status == status)
return;
job->priv->status = status;
g_signal_emit (job, signals[STATUS_CHANGED], 0);
}
gboolean
gtk_print_job_set_source_file (GtkPrintJob *job,
const char *filename,
GError **error)
{
g_return_val_if_fail (GTK_IS_PRINT_JOB (job), FALSE);
job->priv->spool_file_fd = g_open (filename, O_RDONLY|O_BINARY);
if (job->priv->spool_file_fd < 0)
{
gchar *display_filename = g_filename_display_name (filename);
int save_errno = errno;
g_set_error (error,
G_FILE_ERROR,
g_file_error_from_errno (save_errno),
_("Failed to open file '%s': %s"),
display_filename,
g_strerror (save_errno));
g_free (display_filename);
return FALSE;
}
return TRUE;
}
cairo_surface_t *
gtk_print_job_get_surface (GtkPrintJob *job,
GError **error)
{
char *filename;
double width, height;
GtkPaperSize *paper_size;
/* TODO: populate GError */
if (!(job->priv->printer_set &&
job->priv->settings_set &&
job->priv->page_setup_set))
return FALSE;
g_return_val_if_fail (GTK_IS_PRINT_JOB (job), NULL);
job->priv->prepped = TRUE;
job->priv->cache_fd = g_file_open_tmp ("gtkprint_XXXXXX",
&filename,
error);
fchmod (job->priv->cache_fd, S_IRUSR | S_IWUSR);
if (job->priv->surface)
return job->priv->surface;
job->priv->spool_file_fd = g_file_open_tmp ("gtkprint_XXXXXX",
&filename,
error);
if (job->priv->spool_file_fd == -1)
return NULL;
fchmod (job->priv->spool_file_fd, S_IRUSR | S_IWUSR);
unlink (filename);
if (error != NULL && *error != NULL)
return FALSE;
paper_size = gtk_page_setup_get_paper_size (job->priv->page_setup);
width = gtk_paper_size_get_width (paper_size, GTK_UNIT_POINTS);
height = gtk_paper_size_get_height (paper_size, GTK_UNIT_POINTS);
job->priv->surface = _gtk_printer_create_cairo_surface (job->priv->printer,
width, height,
job->priv->cache_fd);
_gtk_printer_prepare_for_print (job->priv->printer,
job,
job->priv->settings,
job->priv->page_setup);
return TRUE;
job->priv->spool_file_fd);
return job->priv->surface;
}
static void
@@ -285,6 +385,7 @@ gtk_print_job_set_property (GObject *object,
{
GtkPrintJob *job = GTK_PRINT_JOB (object);
GtkPrintSettings *settings;
switch (prop_id)
{
@@ -304,7 +405,10 @@ gtk_print_job_set_property (GObject *object,
break;
case GTK_PRINT_JOB_PROP_SETTINGS:
job->priv->settings = GTK_PRINT_SETTINGS (g_value_dup_object (value));
/* We save a copy of the settings since we modify
* if when preparing the printer job. */
settings = GTK_PRINT_SETTINGS (g_value_get_object (value));
job->priv->settings = gtk_print_settings_copy (settings);
job->priv->settings_set = TRUE;
break;
@@ -324,6 +428,9 @@ gtk_print_job_get_property (GObject *object,
switch (prop_id)
{
case GTK_PRINT_JOB_PROP_TITLE:
g_value_set_string (value, job->priv->title);
break;
case GTK_PRINT_JOB_PROP_PRINTER:
g_value_set_object (value, job->priv->printer);
break;
@@ -343,23 +450,23 @@ gboolean
gtk_print_job_send (GtkPrintJob *print_job,
GtkPrintJobCompleteFunc callback,
gpointer user_data,
GDestroyNotify dnotify,
GError **error)
{
/* TODO: set gerror */
if (!print_job->priv->prepped)
return FALSE;
g_return_val_if_fail (GTK_IS_PRINT_JOB (print_job), FALSE);
g_return_val_if_fail (print_job->priv->spool_file_fd > 0, FALSE);
lseek (print_job->priv->cache_fd, 0, SEEK_SET);
gtk_print_job_set_status (print_job, GTK_PRINT_STATUS_SENDING_DATA);
lseek (print_job->priv->spool_file_fd, 0, SEEK_SET);
gtk_print_backend_print_stream (print_job->priv->backend,
print_job,
print_job->priv->title,
print_job->priv->cache_fd,
print_job->priv->spool_file_fd,
callback,
user_data);
user_data,
dnotify);
return TRUE;
}
#define __GTK_PRINT_JOB_C__
#include "gtkaliasdef.c"

View File

@@ -22,8 +22,8 @@
#include <glib-object.h>
#include <cairo.h>
#include "gtkprinter.h"
#include "gtkprintsettings.h"
#include <gtk/gtkprinter.h>
#include <gtk/gtkprintoperation.h>
G_BEGIN_DECLS
@@ -40,7 +40,7 @@ typedef struct _GtkPrintJobPrivate GtkPrintJobPrivate;
typedef void (*GtkPrintJobCompleteFunc) (GtkPrintJob *print_job,
void *user_data,
GError **error);
GError *error);
struct _GtkPrinter;
@@ -50,7 +50,9 @@ struct _GtkPrintJob
GtkPrintJobPrivate *priv;
/* These are read-only, set by prepare */
/* Settings the client has to implement:
* (These are read-only, set at initialization)
*/
GtkPrintPages print_pages;
GtkPageRange *page_ranges;
int num_page_ranges;
@@ -66,6 +68,7 @@ struct _GtkPrintJobClass
{
GObjectClass parent_class;
void (*status_changed) (GtkPrintJob *job);
/* Padding for future expansion */
void (*_gtk_reserved1) (void);
@@ -79,20 +82,24 @@ struct _GtkPrintJobClass
GType gtk_print_job_get_type (void) G_GNUC_CONST;
GtkPrintJob *gtk_print_job_new (const gchar *title,
GtkPrinter *printer,
GtkPrintSettings *settings,
GtkPageSetup *page_setup,
GtkPrinter *printer);
GtkPageSetup *page_setup);
GtkPrintSettings *gtk_print_job_get_settings (GtkPrintJob *print_job);
GtkPrinter *gtk_print_job_get_printer (GtkPrintJob *print_job);
cairo_surface_t *gtk_print_job_get_surface (GtkPrintJob *print_job);
gboolean gtk_print_job_send (GtkPrintJob *print_job,
GtkPrintJobCompleteFunc callback,
gpointer user_data,
GError **error);
gboolean gtk_print_job_prepare (GtkPrintJob *job,
GError **error);
const char *gtk_print_job_get_title (GtkPrintJob *print_job);
GtkPrintStatus gtk_print_job_get_status (GtkPrintJob *print_job);
gboolean gtk_print_job_set_source_file (GtkPrintJob *print_job,
const char *filename,
GError **error);
cairo_surface_t *gtk_print_job_get_surface (GtkPrintJob *print_job,
GError **error);
gboolean gtk_print_job_send (GtkPrintJob *print_job,
GtkPrintJobCompleteFunc callback,
gpointer user_data,
GDestroyNotify dnotify,
GError **error);
G_END_DECLS

View File

@@ -27,6 +27,7 @@ G_BEGIN_DECLS
struct _GtkPrintOperationPrivate
{
GtkPrintStatus status;
GtkPageSetup *default_page_setup;
GtkPrintSettings *print_settings;
char *job_name;
@@ -60,6 +61,7 @@ struct _GtkPrintOperationPrivate
void (*end_page) (GtkPrintOperation *operation,
GtkPrintContext *print_context);
void (*end_run) (GtkPrintOperation *operation);
GDestroyNotify free_platform_data;
};
GtkPrintOperationResult _gtk_print_operation_platform_backend_run_dialog (GtkPrintOperation *operation,
@@ -67,7 +69,8 @@ GtkPrintOperationResult _gtk_print_operation_platform_backend_run_dialog (GtkPri
gboolean *do_print,
GError **error);
void _gtk_print_operation_set_status (GtkPrintOperation *op,
GtkPrintStatus status);
/* GtkPrintContext private functions: */

View File

@@ -39,6 +39,7 @@
typedef struct {
GtkPrintJob *job; /* the job we are sending to the printer */
gulong job_status_changed_tag;
GtkWindow *parent; /* parent window just in case we need to throw error dialogs */
} GtkPrintOperationUnix;
@@ -64,7 +65,11 @@ static void
op_unix_free (GtkPrintOperationUnix *op_unix)
{
if (op_unix->job)
g_object_unref (G_OBJECT (op_unix->job));
{
g_signal_handler_disconnect (op_unix->job,
op_unix->job_status_changed_tag);
g_object_unref (op_unix->job);
}
g_free (op_unix);
}
@@ -72,7 +77,7 @@ op_unix_free (GtkPrintOperationUnix *op_unix)
static void
unix_finish_send (GtkPrintJob *job,
void *user_data,
GError **error)
GError *error)
{
GtkPrintOperationUnix *op_unix;
GtkWindow *parent;
@@ -81,19 +86,15 @@ unix_finish_send (GtkPrintJob *job,
parent = op_unix->parent;
op_unix_free (op_unix);
if (error != NULL && *error != NULL)
if (error != NULL)
{
GtkWidget *edialog;
GError *err = *error;
edialog = gtk_message_dialog_new (parent,
GTK_DIALOG_DESTROY_WITH_PARENT,
GTK_MESSAGE_ERROR,
GTK_BUTTONS_CLOSE,
"Error printing: %s",
err->message);
error->message);
gtk_dialog_run (GTK_DIALOG (edialog));
gtk_widget_destroy (edialog);
@@ -106,11 +107,16 @@ unix_end_run (GtkPrintOperation *op)
GtkPrintOperationUnix *op_unix = op->priv->platform_data;
/* TODO: Check for error */
gtk_print_job_send (g_object_ref (op_unix->job),
gtk_print_job_send (op_unix->job,
unix_finish_send,
op_unix, NULL);
op_unix, NULL,
NULL);
}
op->priv->platform_data = NULL;
static void
job_status_changed_cb (GtkPrintJob *job, GtkPrintOperation *op)
{
_gtk_print_operation_set_status (op, gtk_print_job_get_status (job));
}
GtkPrintOperationResult
@@ -143,7 +149,7 @@ _gtk_print_operation_platform_backend_run_dialog (GtkPrintOperation *op,
{
GtkPrintOperationUnix *op_unix;
GtkPrinter *printer;
GtkPrintSettings *settings, *settings_copy;
GtkPrintSettings *settings;
result = GTK_PRINT_OPERATION_RESULT_APPLY;
@@ -154,22 +160,17 @@ _gtk_print_operation_platform_backend_run_dialog (GtkPrintOperation *op,
*do_print = TRUE;
settings = gtk_print_unix_dialog_get_settings (GTK_PRINT_UNIX_DIALOG (pd));
gtk_print_operation_set_print_settings (op, settings);
/* We save a copy to return to the user to avoid exposing
the extra settings preparint the printer job adds. */
settings_copy = gtk_print_settings_copy (settings);
gtk_print_operation_set_print_settings (op, settings_copy);
g_object_unref (settings_copy);
op_unix = g_new (GtkPrintOperationUnix, 1);
op_unix->job = gtk_printer_prepare_job (printer,
settings,
page_setup,
"Title",
error);
op_unix = g_new0 (GtkPrintOperationUnix, 1);
op_unix->job = gtk_print_job_new (op->priv->job_name,
printer,
settings,
page_setup);
g_object_unref (settings);
if (error != NULL && *error != NULL)
op->priv->surface = gtk_print_job_get_surface (op_unix->job, error);
if (op->priv->surface == NULL)
{
*do_print = FALSE;
op_unix_free (op_unix);
@@ -177,14 +178,18 @@ _gtk_print_operation_platform_backend_run_dialog (GtkPrintOperation *op,
goto out;
}
_gtk_print_operation_set_status (op, gtk_print_job_get_status (op_unix->job));
op_unix->job_status_changed_tag =
g_signal_connect (op_unix->job, "status_changed",
G_CALLBACK (job_status_changed_cb), op);
op_unix->parent = parent;
op->priv->surface = gtk_print_job_get_surface (op_unix->job);
op->priv->dpi_x = 72;
op->priv->dpi_y = 72;
op->priv->platform_data = op_unix;
op->priv->free_platform_data = (GDestroyNotify) op_unix_free;
op->priv->print_pages = op_unix->job->print_pages;
op->priv->page_ranges = op_unix->job->page_ranges;

View File

@@ -31,6 +31,7 @@ enum {
REQUEST_PAGE_SETUP,
DRAW_PAGE,
END_PRINT,
STATUS_CHANGED,
LAST_SIGNAL
};
@@ -53,6 +54,13 @@ gtk_print_operation_finalize (GObject *object)
{
GtkPrintOperation *print_operation = GTK_PRINT_OPERATION (object);
if (print_operation->priv->free_platform_data &&
print_operation->priv->platform_data)
{
print_operation->priv->free_platform_data (print_operation->priv->platform_data);
print_operation->priv->free_platform_data = NULL;
}
if (print_operation->priv->default_page_setup)
g_object_unref (print_operation->priv->default_page_setup);
@@ -61,6 +69,7 @@ gtk_print_operation_finalize (GObject *object)
g_free (print_operation->priv->pdf_target);
g_free (print_operation->priv->job_name);
G_OBJECT_CLASS (gtk_print_operation_parent_class)->finalize (object);
}
@@ -71,6 +80,7 @@ gtk_print_operation_init (GtkPrintOperation *operation)
operation->priv = GTK_PRINT_OPERATION_GET_PRIVATE (operation);
operation->priv->status = GTK_PRINT_STATUS_INITIAL;
operation->priv->default_page_setup = NULL;
operation->priv->print_settings = NULL;
operation->priv->nr_of_pages = -1;
@@ -132,6 +142,15 @@ gtk_print_operation_class_init (GtkPrintOperationClass *class)
NULL, NULL,
g_cclosure_marshal_VOID__OBJECT,
G_TYPE_NONE, 1, GTK_TYPE_PRINT_CONTEXT);
signals[STATUS_CHANGED] =
g_signal_new ("status-changed",
G_TYPE_FROM_CLASS (class),
G_SIGNAL_RUN_LAST,
G_STRUCT_OFFSET (GtkPrintOperationClass, status_changed),
NULL, NULL,
g_cclosure_marshal_VOID__VOID,
G_TYPE_NONE, 0);
}
GtkPrintOperation *
@@ -238,6 +257,37 @@ gtk_print_operation_set_unit (GtkPrintOperation *op,
op->priv->unit = unit;
}
void
_gtk_print_operation_set_status (GtkPrintOperation *op,
GtkPrintStatus status)
{
if (op->priv->status == status)
return;
op->priv->status = status;
g_signal_emit (op, signals[STATUS_CHANGED], 0);
}
GtkPrintStatus
gtk_print_operation_get_status (GtkPrintOperation *op)
{
g_return_val_if_fail (GTK_IS_PRINT_OPERATION (op), GTK_PRINT_STATUS_FINISHED_ABORTED);
return op->priv->status;
}
gboolean
gtk_print_operation_is_finished (GtkPrintOperation *op)
{
g_return_val_if_fail (GTK_IS_PRINT_OPERATION (op), TRUE);
return
op->priv->status == GTK_PRINT_STATUS_FINISHED_ABORTED ||
op->priv->status == GTK_PRINT_STATUS_FINISHED;
}
void
gtk_print_operation_set_show_dialog (GtkPrintOperation *op,
gboolean show_dialog)
@@ -404,7 +454,10 @@ gtk_print_operation_run (GtkPrintOperation *op,
result = run_print_dialog (op, parent, &do_print, error);
if (!do_print)
return result;
{
_gtk_print_operation_set_status (op, GTK_PRINT_STATUS_FINISHED_ABORTED);
return result;
}
if (op->priv->manual_collation)
{
@@ -422,6 +475,7 @@ gtk_print_operation_run (GtkPrintOperation *op,
initial_page_setup = create_page_setup (op);
_gtk_print_context_set_page_setup (print_context, initial_page_setup);
_gtk_print_operation_set_status (op, GTK_PRINT_STATUS_PREPARING);
g_signal_emit (op, signals[BEGIN_PRINT], 0, print_context);
g_return_val_if_fail (op->priv->nr_of_pages != -1, FALSE);
@@ -447,6 +501,8 @@ gtk_print_operation_run (GtkPrintOperation *op,
ranges[0].end = op->priv->nr_of_pages - 1;
}
_gtk_print_operation_set_status (op, GTK_PRINT_STATUS_GENERATING_DATA);
for (i = 0; i < uncollated_copies; i++)
{
for (range = 0; range < num_ranges; range ++)

View File

@@ -23,6 +23,7 @@
#include <glib-object.h>
#include <cairo.h>
#include "gtkmain.h"
#include "gtkenums.h"
#include "gtkwindow.h"
#include "gtkpagesetup.h"
@@ -39,6 +40,17 @@ typedef struct _GtkPrintOperationClass GtkPrintOperationClass;
typedef struct _GtkPrintOperationPrivate GtkPrintOperationPrivate;
typedef struct _GtkPrintOperation GtkPrintOperation;
typedef enum {
GTK_PRINT_STATUS_INITIAL,
GTK_PRINT_STATUS_PREPARING,
GTK_PRINT_STATUS_GENERATING_DATA,
GTK_PRINT_STATUS_SENDING_DATA,
GTK_PRINT_STATUS_PENDING,
GTK_PRINT_STATUS_PROCESSING,
GTK_PRINT_STATUS_FINISHED,
GTK_PRINT_STATUS_FINISHED_ABORTED
} GtkPrintStatus;
struct _GtkPrintOperation
{
GObject parent_instance;
@@ -61,6 +73,8 @@ struct _GtkPrintOperationClass
void (*end_print) (GtkPrintOperation *operation,
GtkPrintContext *context);
void (*status_changed) (GtkPrintOperation *operation);
/* Padding for future expansion */
void (*_gtk_reserved1) (void);
void (*_gtk_reserved2) (void);
@@ -113,6 +127,8 @@ void gtk_print_operation_set_pdf_target (GtkPrintOper
GtkPrintOperationResult gtk_print_operation_run (GtkPrintOperation *op,
GtkWindow *parent,
GError **error);
GtkPrintStatus gtk_print_operation_get_status (GtkPrintOperation *op);
gboolean gtk_print_operation_is_finished (GtkPrintOperation *op);
GtkPageSetup *gtk_print_run_page_setup_dialog (GtkWindow *parent,
GtkPageSetup *page_setup,

View File

@@ -138,6 +138,10 @@ static void cups_printer_get_hard_margins (GtkPrinter
double *right);
static void set_option_from_settings (GtkPrinterOption *option,
GtkPrintSettings *setting);
static void cups_begin_polling_info (GtkPrintBackendCups *print_backend,
GtkPrintJob *job,
int job_id);
static gboolean cups_job_info_poll_timeout (gpointer user_data);
static void
gtk_print_backend_cups_register_type (GTypeModule *module)
@@ -281,7 +285,17 @@ typedef struct {
GtkPrintJobCompleteFunc callback;
GtkPrintJob *job;
gpointer user_data;
} _PrintStreamData;
GDestroyNotify dnotify;
} CupsPrintStreamData;
static void
cups_free_print_stream_data (CupsPrintStreamData *data)
{
if (data->dnotify)
data->dnotify (data->user_data);
g_object_unref (data->job);
g_free (data);
}
static void
cups_print_cb (GtkPrintBackendCups *print_backend,
@@ -289,8 +303,7 @@ cups_print_cb (GtkPrintBackendCups *print_backend,
gpointer user_data)
{
GError *error = NULL;
_PrintStreamData *ps = (_PrintStreamData *) user_data;
CupsPrintStreamData *ps = user_data;
if (gtk_cups_result_is_error (result))
error = g_error_new_literal (gtk_print_error_quark (),
@@ -298,9 +311,33 @@ cups_print_cb (GtkPrintBackendCups *print_backend,
gtk_cups_result_get_error_string (result));
if (ps->callback)
ps->callback (ps->job, ps->user_data, &error);
ps->callback (ps->job, ps->user_data, error);
g_free (ps);
if (error == NULL)
{
int job_id = 0;
ipp_attribute_t *attr; /* IPP job-id attribute */
ipp_t *response = gtk_cups_result_get_response (result);
if ((attr = ippFindAttribute(response, "job-id", IPP_TAG_INTEGER)) != NULL)
job_id = attr->values[0].integer;
if (job_id == 0)
gtk_print_job_set_status (ps->job, GTK_PRINT_STATUS_FINISHED);
else
{
gtk_print_job_set_status (ps->job, GTK_PRINT_STATUS_PENDING);
cups_begin_polling_info (print_backend, ps->job, job_id);
}
}
else
gtk_print_job_set_status (ps->job, GTK_PRINT_STATUS_FINISHED_ABORTED);
if (error)
g_error_free (error);
}
static void
@@ -324,16 +361,17 @@ add_cups_options (const char *key,
static void
gtk_print_backend_cups_print_stream (GtkPrintBackend *print_backend,
GtkPrintJob *job,
const gchar *title,
gint data_fd,
GtkPrintJobCompleteFunc callback,
gpointer user_data)
gpointer user_data,
GDestroyNotify dnotify)
{
GError *error;
GtkPrinterCups *cups_printer;
_PrintStreamData *ps;
CupsPrintStreamData *ps;
GtkCupsRequest *request;
GtkPrintSettings *settings;
const gchar *title;
cups_printer = GTK_PRINTER_CUPS (gtk_print_job_get_printer (job));
settings = gtk_print_job_get_settings (job);
@@ -353,22 +391,24 @@ gtk_print_backend_cups_print_stream (GtkPrintBackend *print_backend,
gtk_cups_request_ipp_add_string (request, IPP_TAG_OPERATION, IPP_TAG_NAME, "requesting-user-name",
NULL, cupsUser());
title = gtk_print_job_get_title (job);
if (title)
gtk_cups_request_ipp_add_string (request, IPP_TAG_OPERATION, IPP_TAG_NAME, "job-name", NULL,
title);
gtk_print_settings_foreach (settings, add_cups_options, request);
ps = g_new0 (_PrintStreamData, 1);
ps = g_new0 (CupsPrintStreamData, 1);
ps->callback = callback;
ps->user_data = user_data;
ps->job = job;
ps->dnotify = dnotify;
ps->job = g_object_ref (job);
cups_request_execute (GTK_PRINT_BACKEND_CUPS (print_backend),
request,
(GtkPrintCupsResponseCallbackFunc) cups_print_cb,
ps,
NULL,
(GDestroyNotify)cups_free_print_stream_data,
&error);
}
@@ -634,6 +674,9 @@ cups_request_printer_info_cb (GtkPrintBackendCups *print_backend,
cups_printer->device_uri = g_strdup_printf ("/printers/%s", printer_name);
state_msg = "";
loc = "";
desc = "";
for (attr = response->attrs; attr != NULL; attr = attr->next)
{
if (!attr->name)
@@ -732,6 +775,167 @@ cups_request_printer_info (GtkPrintBackendCups *print_backend,
}
typedef struct {
GtkPrintBackendCups *print_backend;
GtkPrintJob *job;
int job_id;
int counter;
} CupsJobPollData;
static void
job_object_died (gpointer user_data,
GObject *where_the_object_was)
{
CupsJobPollData *data = user_data;
data->job = NULL;
}
static void
cups_job_poll_data_free (CupsJobPollData *data)
{
if (data->job)
g_object_weak_unref (G_OBJECT (data->job), job_object_died, data);
g_free (data);
}
static void
cups_request_job_info_cb (GtkPrintBackendCups *print_backend,
GtkCupsResult *result,
gpointer user_data)
{
CupsJobPollData *data = user_data;
ipp_attribute_t *attr;
ipp_t *response;
int state;
gboolean done;
if (data->job == NULL)
{
cups_job_poll_data_free (data);
return;
}
data->counter++;
response = gtk_cups_result_get_response (result);
state = 0;
for (attr = response->attrs; attr != NULL; attr = attr->next)
{
if (!attr->name)
continue;
_CUPS_MAP_ATTR_INT (attr, state, "job-state");
}
done = FALSE;
switch (state)
{
case IPP_JOB_PENDING:
case IPP_JOB_HELD:
case IPP_JOB_STOPPED:
gtk_print_job_set_status (data->job,
GTK_PRINT_STATUS_PENDING);
break;
case IPP_JOB_PROCESSING:
gtk_print_job_set_status (data->job,
GTK_PRINT_STATUS_PROCESSING);
break;
default:
case IPP_JOB_CANCELLED:
case IPP_JOB_ABORTED:
gtk_print_job_set_status (data->job,
GTK_PRINT_STATUS_FINISHED_ABORTED);
done = TRUE;
break;
case 0:
case IPP_JOB_COMPLETED:
gtk_print_job_set_status (data->job,
GTK_PRINT_STATUS_FINISHED);
done = TRUE;
break;
}
if (!done && data->job != NULL)
{
guint32 timeout;
if (data->counter < 5)
timeout = 100;
else if (data->counter < 10)
timeout = 500;
else
timeout = 1000;
g_timeout_add (timeout, cups_job_info_poll_timeout, data);
}
else
cups_job_poll_data_free (data);
}
static void
cups_request_job_info (CupsJobPollData *data)
{
GError *error;
GtkCupsRequest *request;
gchar *printer_uri;
error = NULL;
request = gtk_cups_request_new (NULL,
GTK_CUPS_POST,
IPP_GET_JOB_ATTRIBUTES,
0,
NULL,
NULL);
printer_uri = g_strdup_printf ("ipp://localhost/jobs/%d", data->job_id);
gtk_cups_request_ipp_add_string (request, IPP_TAG_OPERATION, IPP_TAG_URI,
"job-uri", NULL, printer_uri);
g_free (printer_uri);
cups_request_execute (data->print_backend,
request,
(GtkPrintCupsResponseCallbackFunc) cups_request_job_info_cb,
data,
NULL,
&error);
}
static gboolean
cups_job_info_poll_timeout (gpointer user_data)
{
CupsJobPollData *data = user_data;
if (data->job == NULL)
cups_job_poll_data_free (data);
else
cups_request_job_info (data);
return FALSE;
}
static void
cups_begin_polling_info (GtkPrintBackendCups *print_backend,
GtkPrintJob *job,
int job_id)
{
CupsJobPollData *data;
data = g_new0 (CupsJobPollData, 1);
data->print_backend = print_backend;
data->job = job;
data->job_id = job_id;
data->counter = 0;
g_object_weak_ref (G_OBJECT (job), job_object_died, data);
cups_request_job_info (data);
}
static gint
printer_cmp (GtkPrinter *a, GtkPrinter *b)
{

View File

@@ -241,6 +241,7 @@ typedef struct {
GtkPrintJobCompleteFunc callback;
GtkPrintJob *job;
gpointer user_data;
GDestroyNotify dnotify;
gint in;
gint out;
@@ -250,7 +251,7 @@ typedef struct {
static void
lpr_print_cb (GtkPrintBackendLpr *print_backend,
GError **error,
GError *error,
gpointer user_data)
{
_PrintStreamData *ps = (_PrintStreamData *) user_data;
@@ -267,6 +268,15 @@ lpr_print_cb (GtkPrintBackendLpr *print_backend,
if (ps->callback)
ps->callback (ps->job, ps->user_data, error);
if (ps->dnotify)
ps->dnotify (ps->user_data);
gtk_print_job_set_status (ps->job,
(error != NULL)?GTK_PRINT_STATUS_FINISHED_ABORTED:GTK_PRINT_STATUS_FINISHED);
if (ps->job)
g_object_unref (ps->job);
g_free (ps);
}
@@ -307,7 +317,7 @@ lpr_write (GIOChannel *source,
if (bytes_read == 0 || error != NULL)
{
lpr_print_cb (GTK_PRINT_BACKEND_LPR (ps->backend), &error, user_data);
lpr_print_cb (GTK_PRINT_BACKEND_LPR (ps->backend), error, user_data);
return FALSE;
}
@@ -319,11 +329,11 @@ lpr_write (GIOChannel *source,
static void
gtk_print_backend_lpr_print_stream (GtkPrintBackend *print_backend,
GtkPrintJob *job,
const gchar *title,
gint data_fd,
GtkPrintJobCompleteFunc callback,
gpointer user_data)
GtkPrintJob *job,
gint data_fd,
GtkPrintJobCompleteFunc callback,
gpointer user_data,
GDestroyNotify dnotify)
{
GError *error;
GtkPrinterLpr *lpr_printer;
@@ -344,7 +354,8 @@ gtk_print_backend_lpr_print_stream (GtkPrintBackend *print_backend,
ps = g_new0 (_PrintStreamData, 1);
ps->callback = callback;
ps->user_data = user_data;
ps->job = job;
ps->dnotify = dnotify;
ps->job = g_object_ref (job);
ps->in = 0;
ps->out = 0;
ps->err = 0;
@@ -360,8 +371,7 @@ gtk_print_backend_lpr_print_stream (GtkPrintBackend *print_backend,
&error))
{
lpr_print_cb (GTK_PRINT_BACKEND_LPR (print_backend),
&error,
ps);
error, ps);
g_free (cmd_line);
return;
@@ -382,8 +392,7 @@ gtk_print_backend_lpr_print_stream (GtkPrintBackend *print_backend,
&error))
{
lpr_print_cb (GTK_PRINT_BACKEND_LPR (print_backend),
&error,
ps);
error, ps);
goto out;

View File

@@ -242,11 +242,12 @@ typedef struct {
GtkPrintJob *job;
gint target_fd;
gpointer user_data;
GDestroyNotify dnotify;
} _PrintStreamData;
static void
pdf_print_cb (GtkPrintBackendPdf *print_backend,
GError **error,
GError *error,
gpointer user_data)
{
_PrintStreamData *ps = (_PrintStreamData *) user_data;
@@ -257,6 +258,15 @@ pdf_print_cb (GtkPrintBackendPdf *print_backend,
if (ps->callback)
ps->callback (ps->job, ps->user_data, error);
if (ps->dnotify)
ps->dnotify (ps->user_data);
gtk_print_job_set_status (ps->job,
(error != NULL)?GTK_PRINT_STATUS_FINISHED_ABORTED:GTK_PRINT_STATUS_FINISHED);
if (ps->job)
g_object_unref (ps->job);
g_free (ps);
}
@@ -299,7 +309,7 @@ pdf_write (GIOChannel *source,
if (bytes_read == 0 || error != NULL)
{
pdf_print_cb (GTK_PRINT_BACKEND_PDF (ps->backend), &error, user_data);
pdf_print_cb (GTK_PRINT_BACKEND_PDF (ps->backend), error, user_data);
return FALSE;
}
@@ -309,11 +319,11 @@ pdf_write (GIOChannel *source,
static void
gtk_print_backend_pdf_print_stream (GtkPrintBackend *print_backend,
GtkPrintJob *job,
const gchar *title,
gint data_fd,
GtkPrintJobCompleteFunc callback,
gpointer user_data)
GtkPrintJob *job,
gint data_fd,
GtkPrintJobCompleteFunc callback,
gpointer user_data,
GDestroyNotify dnotify)
{
GError *error;
GtkPrinterPdf *pdf_printer;
@@ -335,7 +345,7 @@ gtk_print_backend_pdf_print_stream (GtkPrintBackend *print_backend,
ps = g_new0 (_PrintStreamData, 1);
ps->callback = callback;
ps->user_data = user_data;
ps->job = job;
ps->job = g_object_ref (job);
filename = pdf_printer->file_option->value;
@@ -349,7 +359,7 @@ gtk_print_backend_pdf_print_stream (GtkPrintBackend *print_backend,
g_strerror (errno));
pdf_print_cb (GTK_PRINT_BACKEND_PDF (print_backend),
&error,
error,
ps);
return;

View File

@@ -9,6 +9,7 @@ static GtkPrintSettings *settings = NULL;
static gboolean file_changed = FALSE;
static GtkTextBuffer *buffer;
static GtkWidget *statusbar;
static int printing_count = 0;
static void
update_title (void)
@@ -44,8 +45,10 @@ update_statusbar (void)
row = gtk_text_iter_get_line (&iter);
col = gtk_text_iter_get_line_offset (&iter);
msg = g_strdup_printf ("%d, %d%s",
row, col, file_changed?" - Modified":"");
msg = g_strdup_printf ("%d, %d%s%s",
row, col,
file_changed?" - Modified":"",
(printing_count > 0)?" printing...":"");
gtk_statusbar_push (GTK_STATUSBAR (statusbar), 0, msg);
@@ -368,6 +371,17 @@ do_page_setup (GtkAction *action)
page_setup = new_page_setup;
}
static void
status_changed_cb (GtkPrintOperation *op,
gpointer user_data)
{
if (gtk_print_operation_is_finished (op))
{
g_object_unref (op);
printing_count--;
update_statusbar ();
}
}
static void
do_print (GtkAction *action)
@@ -382,6 +396,7 @@ do_print (GtkAction *action)
print = gtk_print_operation_new ();
if (settings != NULL)
gtk_print_operation_set_print_settings (print, settings);
@@ -412,6 +427,19 @@ do_print (GtkAction *action)
g_object_unref (settings);
settings = g_object_ref (gtk_print_operation_get_print_settings (print));
}
if (!gtk_print_operation_is_finished (print))
{
printing_count++;
update_statusbar ();
/* This ref is unref:ed when we get the final state change */
g_object_ref (print);
g_signal_connect (print, "status_changed",
G_CALLBACK (status_changed_cb), NULL);
}
g_object_unref (print);
}
static void