From 057680fd0b25cc7bf90598f50bd2088ca4aa87ac Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?J=C3=BCrg=20Billeter?= Date: Sat, 23 Jul 2005 21:31:19 +0000 Subject: Use libgnomeprintui for the printing dialog and the paper part of the MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit 2005-07-22 Jürg Billeter * configure.ac: * data/glade/print.glade: * embed/mozilla/EphyUtils.cpp: * embed/mozilla/EphyUtils.h: * embed/mozilla/PrintingPromptService.cpp: * embed/mozilla/PrintingPromptService.h: * embed/print-dialog.c: (ephy_print_info_free), (ephy_print_load_config_from_file), (ephy_print_save_config_to_file), (ephy_print_get_print_info), (ephy_print_dialog_response_cb), (ephy_print_do_print_idle_cb), (ephy_print_do_print_and_free), (ephy_print_paper_selector_new), (ephy_print_dialog_construct_range_page), (ephy_print_dialog_new), (ephy_print_setup_dialog_new): * embed/print-dialog.h: Use libgnomeprintui for the printing dialog and the paper part of the printing setup dialog. Fixes bug #141241, bug #163255 and bug #301730. --- embed/mozilla/EphyUtils.cpp | 140 +++++++-- embed/mozilla/EphyUtils.h | 2 +- embed/mozilla/PrintingPromptService.cpp | 128 ++++++-- embed/mozilla/PrintingPromptService.h | 8 +- embed/print-dialog.c | 511 +++++++++++++++++--------------- embed/print-dialog.h | 31 +- 6 files changed, 510 insertions(+), 310 deletions(-) (limited to 'embed') diff --git a/embed/mozilla/EphyUtils.cpp b/embed/mozilla/EphyUtils.cpp index 3d43cf11e..55a392b44 100644 --- a/embed/mozilla/EphyUtils.cpp +++ b/embed/mozilla/EphyUtils.cpp @@ -26,6 +26,7 @@ #include "ephy-embed-shell.h" #include "ephy-embed-single.h" #include "print-dialog.h" +#include "ephy-file-helpers.h" #include #include @@ -124,10 +125,8 @@ EphyUtils::FindGtkParent (nsIDOMWindow *aDOMWindow) return gtk_widget_get_toplevel (GTK_WIDGET (embed)); } -#define MM_TO_INCH(x) (((double) x) / 25.4) - nsresult -EphyUtils::CollatePrintSettings (const EmbedPrintInfo *info, +EphyUtils::CollatePrintSettings (EmbedPrintInfo *info, nsIPrintSettings *options, gboolean preview) { @@ -137,25 +136,64 @@ EphyUtils::CollatePrintSettings (const EmbedPrintInfo *info, nsIPrintSettings::kEachFrameSep }; - switch (info->pages) + switch (info->range) { - case 0: + case GNOME_PRINT_RANGE_ALL: options->SetPrintRange (nsIPrintSettings::kRangeAllPages); break; - case 1: + case GNOME_PRINT_RANGE_RANGE: options->SetPrintRange (nsIPrintSettings::kRangeSpecifiedPageRange); options->SetStartPageRange (info->from_page); options->SetEndPageRange (info->to_page); break; - case 2: + case GNOME_PRINT_RANGE_SELECTION: options->SetPrintRange (nsIPrintSettings::kRangeSelection); break; } + + const GnomePrintUnit *unit, *inch, *mm; + double value; + + mm = gnome_print_unit_get_by_abbreviation ((const guchar *) "mm"); + inch = gnome_print_unit_get_by_abbreviation ((const guchar *) "in"); + g_assert (mm != NULL && inch != NULL); + + /* top margin */ + if (gnome_print_config_get_length (info->config, + (const guchar *) GNOME_PRINT_KEY_PAGE_MARGIN_TOP, + &value, &unit) + && gnome_print_convert_distance (&value, unit, inch)) + { + options->SetMarginTop (value); + } + + /* bottom margin */ + if (gnome_print_config_get_length (info->config, + (const guchar *) GNOME_PRINT_KEY_PAGE_MARGIN_BOTTOM, + &value, &unit) + && gnome_print_convert_distance (&value, unit, inch)) + { + options->SetMarginBottom (value); + } + + /* left margin */ + if (gnome_print_config_get_length (info->config, + (const guchar *) GNOME_PRINT_KEY_PAGE_MARGIN_LEFT, + &value, &unit) + && gnome_print_convert_distance (&value, unit, inch)) + { + options->SetMarginLeft (value); + } + + /* right margin */ + if (gnome_print_config_get_length (info->config, + (const guchar *) GNOME_PRINT_KEY_PAGE_MARGIN_RIGHT, + &value, &unit) + && gnome_print_convert_distance (&value, unit, inch)) + { + options->SetMarginRight (value); + } - options->SetMarginTop (MM_TO_INCH (info->top_margin)); - options->SetMarginBottom (MM_TO_INCH (info->bottom_margin)); - options->SetMarginLeft (MM_TO_INCH (info->left_margin)); - options->SetMarginRight (MM_TO_INCH (info->right_margin)); nsEmbedString tmp; @@ -183,38 +221,76 @@ EphyUtils::CollatePrintSettings (const EmbedPrintInfo *info, NS_CSTRING_ENCODING_UTF8, tmp); options->SetFooterStrRight(tmp.get()); - NS_CStringToUTF16 (nsEmbedCString(info->file), - NS_CSTRING_ENCODING_UTF8, tmp); - options->SetToFileName (tmp.get()); + options->SetPrintToFile (PR_FALSE); + + if (!preview) + { + char *cmd, *base; + const char *temp_dir; + + temp_dir = ephy_file_tmp_dir (); + base = g_build_filename (temp_dir, "printXXXXXX", NULL); + info->tempfile = ephy_file_tmp_filename (base, "ps"); + g_free (base); + + /* use cat instead of print to file to avoid fflush to ensure + * the file has been written completely and we don't need to + * select a printer (i.e. should be printing backend independent) + */ + + cmd = g_strconcat ("cat > ", info->tempfile, NULL); + NS_CStringToUTF16 (nsEmbedCString(cmd), + NS_CSTRING_ENCODING_UTF8, tmp); + options->SetPrintCommand (tmp.get()); + g_free (cmd); + } - NS_CStringToUTF16 (nsEmbedCString(info->printer), - NS_CSTRING_ENCODING_UTF8, tmp); - options->SetPrinterName (tmp.get()); + /* paper size */ + options->SetPaperSize (nsIPrintSettings::kPaperSizeDefined); + options->SetPaperSizeUnit (nsIPrintSettings::kPaperSizeMillimeters); - /** - * Work around a mozilla bug where paper size & orientation are ignored - * and the specified file is created (containing invalid postscript) - * in print preview mode if we set "print to file" to true. - * See epiphany bug #119818. - */ - if (preview) + if (gnome_print_config_get_length (info->config, + (const guchar *) GNOME_PRINT_KEY_PAPER_WIDTH, + &value, &unit) + && gnome_print_convert_distance (&value, unit, mm)) { - options->SetPrintToFile (PR_FALSE); + options->SetPaperWidth (value); } - else + + if (gnome_print_config_get_length (info->config, + (const guchar *) GNOME_PRINT_KEY_PAPER_HEIGHT, + &value, &unit) + && gnome_print_convert_distance (&value, unit, mm)) { - options->SetPrintToFile (info->print_to_file); + options->SetPaperHeight (value); } + + char *string; - /* native paper size formats. Our dialog does not support custom yet */ - options->SetPaperSize (nsIPrintSettings::kPaperSizeNativeData); - - NS_CStringToUTF16 (nsEmbedCString(info->paper), + /* paper name */ + string = (char *) gnome_print_config_get (info->config, + (const guchar *) GNOME_PRINT_KEY_PAPER_SIZE); + NS_CStringToUTF16 (nsEmbedCString(string), NS_CSTRING_ENCODING_UTF8, tmp); options->SetPaperName (tmp.get()); + g_free (string); + + /* paper orientation */ + string = (char *) gnome_print_config_get (info->config, + (const guchar *) GNOME_PRINT_KEY_ORIENTATION); + if (string == NULL) string = g_strdup ("R0"); + + if (strncmp (string, "R90", 3) == 0 || strncmp (string, "R270", 4) == 0) + { + options->SetOrientation (nsIPrintSettings::kLandscapeOrientation); + } + else + { + options->SetOrientation (nsIPrintSettings::kPortraitOrientation); + } + g_free (string); options->SetPrintInColor (info->print_color); - options->SetOrientation (info->orientation); options->SetPrintFrameType (frame_types[info->frame_type]); return NS_OK; diff --git a/embed/mozilla/EphyUtils.h b/embed/mozilla/EphyUtils.h index c518d4893..368e1e59f 100644 --- a/embed/mozilla/EphyUtils.h +++ b/embed/mozilla/EphyUtils.h @@ -50,7 +50,7 @@ namespace EphyUtils GtkWidget *FindGtkParent (nsIDOMWindow *aDOMWindow); - nsresult CollatePrintSettings (const _EmbedPrintInfo *info, + nsresult CollatePrintSettings (_EmbedPrintInfo *info, nsIPrintSettings *settings, gboolean preview); PRBool StringEquals (nsAString &s1, diff --git a/embed/mozilla/PrintingPromptService.cpp b/embed/mozilla/PrintingPromptService.cpp index 570b15774..2770f0d30 100644 --- a/embed/mozilla/PrintingPromptService.cpp +++ b/embed/mozilla/PrintingPromptService.cpp @@ -1,6 +1,7 @@ /* * Copyright (C) 2002 Philip Langdale * Copyright (C) 2003-2004 Christian Persch + * Copyright (C) 2005 Juerg Billeter * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -24,6 +25,8 @@ #include "config.h" #include + +#include #include "print-dialog.h" #include "ephy-embed.h" @@ -39,22 +42,30 @@ #include /* Implementation file */ -NS_IMPL_ISUPPORTS1(GPrintingPromptService, nsIPrintingPromptService) +NS_IMPL_ISUPPORTS3(GPrintingPromptService, nsIPrintingPromptService, nsIWebProgressListener, nsIPrintProgressParams) GPrintingPromptService::GPrintingPromptService() { LOG ("GPrintingPromptService ctor (%p)", this); + + mPrintInfo = NULL; } GPrintingPromptService::~GPrintingPromptService() { LOG ("GPrintingPromptService dtor (%p)", this); + + if (mPrintInfo != NULL) + { + ephy_print_info_free (mPrintInfo); + } } /* void showPrintDialog (in nsIDOMWindow parent, in nsIWebBrowserPrint webBrowserPrint, in nsIPrintSettings printSettings); */ NS_IMETHODIMP GPrintingPromptService::ShowPrintDialog(nsIDOMWindow *parent, nsIWebBrowserPrint *webBrowserPrint, nsIPrintSettings *printSettings) { - EphyDialog *dialog; + EmbedPrintInfo *info; + GtkWidget *dialog; if (eel_gconf_get_boolean (CONF_LOCKDOWN_DISABLE_PRINTING)) { @@ -64,38 +75,50 @@ NS_IMETHODIMP GPrintingPromptService::ShowPrintDialog(nsIDOMWindow *parent, nsIW EphyEmbed *embed = EPHY_EMBED (EphyUtils::FindEmbed (parent)); NS_ENSURE_TRUE (embed, NS_ERROR_FAILURE); + info = ephy_print_get_print_info (); + if (!eel_gconf_get_boolean (CONF_LOCKDOWN_DISABLE_PRINT_SETUP)) { GtkWidget *gtkParent = EphyUtils::FindGtkParent(parent); NS_ENSURE_TRUE (gtkParent, NS_ERROR_FAILURE); - dialog = ephy_print_dialog_new (gtkParent, embed); - ephy_dialog_set_modal (dialog, TRUE); + dialog = ephy_print_dialog_new (gtkParent, info); + gtk_window_set_modal (GTK_WINDOW (dialog), TRUE); - int ret = ephy_dialog_run (dialog); - - g_object_unref (dialog); + int ret; + + while (TRUE) + { + ret = gtk_dialog_run (GTK_DIALOG (dialog));; + + if (ret != GNOME_PRINT_DIALOG_RESPONSE_PRINT) + break; + + if (ephy_print_verify_postscript (GNOME_PRINT_DIALOG (dialog))) + break; + } + + gtk_widget_destroy (dialog); - if (ret != GTK_RESPONSE_OK) + if (ret != GNOME_PRINT_DIALOG_RESPONSE_PRINT) { + ephy_print_info_free (info); + return NS_ERROR_ABORT; } } - EmbedPrintInfo *info; - - info = ephy_print_get_print_info (); - /* work around mozilla bug which borks when printing selection without having one */ - if (info->pages == 2 && ephy_command_manager_can_do_command + if (info->range == GNOME_PRINT_RANGE_SELECTION && + ephy_command_manager_can_do_command (EPHY_COMMAND_MANAGER (embed), "cmd_copy") == FALSE) { - info->pages = 0; + info->range = GNOME_PRINT_RANGE_ALL; } EphyUtils::CollatePrintSettings (info, printSettings, FALSE); - - ephy_print_info_free (info); + + mPrintInfo = info; return NS_OK; } @@ -103,7 +126,13 @@ NS_IMETHODIMP GPrintingPromptService::ShowPrintDialog(nsIDOMWindow *parent, nsIW /* void showProgress (in nsIDOMWindow parent, in nsIWebBrowserPrint webBrowserPrint, in nsIPrintSettings printSettings, in nsIObserver openDialogObserver, in boolean isForPrinting, out nsIWebProgressListener webProgressListener, out nsIPrintProgressParams printProgressParams, out boolean notifyOnOpen); */ NS_IMETHODIMP GPrintingPromptService::ShowProgress(nsIDOMWindow *parent, nsIWebBrowserPrint *webBrowserPrint, nsIPrintSettings *printSettings, nsIObserver *openDialogObserver, PRBool isForPrinting, nsIWebProgressListener **webProgressListener, nsIPrintProgressParams **printProgressParams, PRBool *notifyOnOpen) { - return NS_ERROR_NOT_IMPLEMENTED; + *printProgressParams = NS_STATIC_CAST(nsIPrintProgressParams*, this); + NS_ADDREF(*printProgressParams); + + *webProgressListener = NS_STATIC_CAST(nsIWebProgressListener*, this); + NS_ADDREF(*webProgressListener); + + return NS_OK; } /* void showPageSetup (in nsIDOMWindow parent, in nsIPrintSettings printSettings, in nsIObserver printObserver); */ @@ -138,3 +167,68 @@ NS_IMETHODIMP GPrintingPromptService::ShowPrinterProperties(nsIDOMWindow *parent { return NS_ERROR_NOT_IMPLEMENTED; } + + +/* void onStateChange (in nsIWebProgress aWebProgress, in nsIRequest aRequest, in unsigned long aStateFlags, in nsresult aStatus); */ +NS_IMETHODIMP GPrintingPromptService::OnStateChange(nsIWebProgress *aWebProgress, nsIRequest *aRequest, PRUint32 aStateFlags, nsresult aStatus) +{ + if ((aStateFlags & STATE_STOP) && mPrintInfo) + { + if (NS_SUCCEEDED (aStatus)) + { + ephy_print_do_print_and_free (mPrintInfo); + } + else + { + ephy_print_info_free (mPrintInfo); + } + + mPrintInfo = NULL; + } + return NS_OK; +} + +/* void onProgressChange (in nsIWebProgress aWebProgress, in nsIRequest aRequest, in long aCurSelfProgress, in long aMaxSelfProgress, in long aCurTotalProgress, in long aMaxTotalProgress); */ +NS_IMETHODIMP GPrintingPromptService::OnProgressChange(nsIWebProgress *aWebProgress, nsIRequest *aRequest, PRInt32 aCurSelfProgress, PRInt32 aMaxSelfProgress, PRInt32 aCurTotalProgress, PRInt32 aMaxTotalProgress) +{ + return NS_ERROR_NOT_IMPLEMENTED; +} + +/* void onLocationChange (in nsIWebProgress aWebProgress, in nsIRequest aRequest, in nsIURI location); */ +NS_IMETHODIMP GPrintingPromptService::OnLocationChange(nsIWebProgress *aWebProgress, nsIRequest *aRequest, nsIURI *location) +{ + return NS_ERROR_NOT_IMPLEMENTED; +} + +/* void onStatusChange (in nsIWebProgress aWebProgress, in nsIRequest aRequest, in nsresult aStatus, in wstring aMessage); */ +NS_IMETHODIMP GPrintingPromptService::OnStatusChange(nsIWebProgress *aWebProgress, nsIRequest *aRequest, nsresult aStatus, const PRUnichar *aMessage) +{ + return NS_ERROR_NOT_IMPLEMENTED; +} + +/* void onSecurityChange (in nsIWebProgress aWebProgress, in nsIRequest aRequest, in unsigned long state); */ +NS_IMETHODIMP GPrintingPromptService::OnSecurityChange(nsIWebProgress *aWebProgress, nsIRequest *aRequest, PRUint32 state) +{ + return NS_ERROR_NOT_IMPLEMENTED; +} + +/* attribute wstring docTitle; */ +NS_IMETHODIMP GPrintingPromptService::GetDocTitle(PRUnichar * *aDocTitle) +{ + return NS_ERROR_NOT_IMPLEMENTED; +} +NS_IMETHODIMP GPrintingPromptService::SetDocTitle(const PRUnichar * aDocTitle) +{ + return NS_ERROR_NOT_IMPLEMENTED; +} + +/* attribute wstring docURL; */ +NS_IMETHODIMP GPrintingPromptService::GetDocURL(PRUnichar * *aDocURL) +{ + return NS_ERROR_NOT_IMPLEMENTED; +} +NS_IMETHODIMP GPrintingPromptService::SetDocURL(const PRUnichar * aDocURL) +{ + return NS_ERROR_NOT_IMPLEMENTED; +} + diff --git a/embed/mozilla/PrintingPromptService.h b/embed/mozilla/PrintingPromptService.h index 31df4be61..b0c1c004e 100644 --- a/embed/mozilla/PrintingPromptService.h +++ b/embed/mozilla/PrintingPromptService.h @@ -23,6 +23,7 @@ #include "nsError.h" #include "nsIPrintingPromptService.h" +#include "print-dialog.h" #define G_PRINTINGPROMPTSERVICE_CID \ { /* 5998a2d3-88ea-4c52-b4bb-4e7abd0d35e0 */ \ @@ -35,15 +36,20 @@ #define G_PRINTINGPROMPTSERVICE_CLASSNAME "Epiphany's Printing Prompt Service" #define G_PRINTINGPROMPTSERVICE_CONTRACTID "@mozilla.org/embedcomp/printingprompt-service;1" -class GPrintingPromptService : public nsIPrintingPromptService +class GPrintingPromptService : public nsIPrintingPromptService, nsIWebProgressListener, nsIPrintProgressParams { public: NS_DECL_ISUPPORTS NS_DECL_NSIPRINTINGPROMPTSERVICE + NS_DECL_NSIWEBPROGRESSLISTENER + NS_DECL_NSIPRINTPROGRESSPARAMS GPrintingPromptService(); virtual ~GPrintingPromptService(); /* additional members */ + +protected: + EmbedPrintInfo *mPrintInfo; }; #endif diff --git a/embed/print-dialog.c b/embed/print-dialog.c index 8a0fe264d..ba3dadca2 100755 --- a/embed/print-dialog.c +++ b/embed/print-dialog.c @@ -1,6 +1,7 @@ /* * Copyright (C) 2002 Jorn Baayen * Copyright (C) 2003, 2004 Christian Persch + * Copyright (C) 2005 Juerg Billeter * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -31,6 +32,8 @@ #include "ephy-debug.h" #include "ephy-gui.h" +#include +#include #include #include #include @@ -41,108 +44,44 @@ #include #include -#define CONF_PRINT_PRINTER "/apps/epiphany/dialogs/print_printer_name" -#define CONF_PRINT_FILE "/apps/epiphany/dialogs/print_file" -#define CONF_PRINT_DIR "/apps/epiphany/directories/print_to_file" -#define CONF_PRINT_PRINTON "/apps/epiphany/dialogs/print_on" -#define CONF_PRINT_ALL_PAGES "/apps/epiphany/dialogs/print_all_pages" -#define CONF_PRINT_FROM_PAGE "/apps/epiphany/dialogs/print_from_page" -#define CONF_PRINT_TO_PAGE "/apps/epiphany/dialogs/print_to_page" - -#define CONF_PRINT_BOTTOM_MARGIN "/apps/epiphany/dialogs/print_bottom_margin" -#define CONF_PRINT_TOP_MARGIN "/apps/epiphany/dialogs/print_top_margin" -#define CONF_PRINT_LEFT_MARGIN "/apps/epiphany/dialogs/print_left_margin" -#define CONF_PRINT_RIGHT_MARGIN "/apps/epiphany/dialogs/print_right_margin" +#include + #define CONF_PRINT_PAGE_TITLE "/apps/epiphany/dialogs/print_page_title" #define CONF_PRINT_PAGE_URL "/apps/epiphany/dialogs/print_page_url" #define CONF_PRINT_DATE "/apps/epiphany/dialogs/print_date" #define CONF_PRINT_PAGE_NUMBERS "/apps/epiphany/dialogs/print_page_numbers" -#define CONF_PRINT_PAPER "/apps/epiphany/dialogs/print_paper" #define CONF_PRINT_COLOR "/apps/epiphany/dialogs/print_color" -#define CONF_PRINT_ORIENTATION "/apps/epiphany/dialogs/print_orientation" - -enum -{ - WINDOW_PROP, - PRINTON_PROP, - PRINTER_PROP, - FILE_PROP, - BROWSE_PROP, - ALL_PAGES_PROP, - SELECTION_PROP, - TO_PROP, - FROM_PROP -}; - -enum -{ - COL_PRINTER_DISPLAY_NAME, - COL_PRINTER_NAME -}; - -static const -EphyDialogProperty print_props [] = -{ - { "print_dialog", NULL, PT_NORMAL, 0 }, - { "printer_radiobutton", CONF_PRINT_PRINTON, PT_AUTOAPPLY, 0 }, - { "printer_combobox", CONF_PRINT_PRINTER, PT_AUTOAPPLY, G_TYPE_STRING }, - { "file_entry", CONF_PRINT_FILE, PT_AUTOAPPLY, 0 }, - { "browse_button", NULL, PT_NORMAL, 0 }, - { "all_pages_radiobutton", CONF_PRINT_ALL_PAGES, PT_AUTOAPPLY, 0 }, - { "selection_radiobutton", NULL, PT_NORMAL, 0 }, - { "to_spinbutton", CONF_PRINT_FROM_PAGE, PT_AUTOAPPLY, G_TYPE_INT }, - { "from_spinbutton", CONF_PRINT_TO_PAGE, PT_AUTOAPPLY, G_TYPE_INT }, - { NULL } -}; +#define PRINT_CONFIG_FILENAME "ephy-print-config.xml" enum { SETUP_WINDOW_PROP, - PAPER_PROP, - TOP_PROP, - BOTTOM_PROP, - LEFT_PROP, - RIGHT_PROP, PAGE_TITLE_PROP, PAGE_URL_PROP, PAGE_NUMBERS_PROP, DATE_PROP, COLOR_PROP, - ORIENTATION_PROP, + PAPER_SELECTOR_PROP, }; static const EphyDialogProperty setup_props [] = { { "print_setup_dialog", NULL, PT_NORMAL, 0 }, - { "A4_radiobutton", CONF_PRINT_PAPER, PT_AUTOAPPLY, G_TYPE_STRING }, - { "top_spinbutton", CONF_PRINT_TOP_MARGIN, PT_AUTOAPPLY, G_TYPE_INT }, - { "bottom_spinbutton", CONF_PRINT_BOTTOM_MARGIN, PT_AUTOAPPLY, G_TYPE_INT }, - { "left_spinbutton", CONF_PRINT_LEFT_MARGIN, PT_AUTOAPPLY, G_TYPE_INT }, - { "right_spinbutton", CONF_PRINT_RIGHT_MARGIN, PT_AUTOAPPLY, G_TYPE_INT }, { "print_page_title_checkbutton", CONF_PRINT_PAGE_TITLE, PT_AUTOAPPLY, 0 }, { "print_page_url_checkbutton", CONF_PRINT_PAGE_URL, PT_AUTOAPPLY, 0 }, { "print_page_numbers_checkbutton", CONF_PRINT_PAGE_NUMBERS, PT_AUTOAPPLY, 0 }, { "print_date_checkbutton", CONF_PRINT_DATE, PT_AUTOAPPLY, 0 }, { "print_color_radiobutton", CONF_PRINT_COLOR, PT_AUTOAPPLY, 0 }, - { "orient_p_radiobutton", CONF_PRINT_ORIENTATION, PT_AUTOAPPLY, 0 }, + { "print_paper_selector_hbox", NULL, PT_NORMAL, 0 }, { NULL } }; -static const -char *paper_format_enum [] = -{ - "A4", "Letter", "Legal", "Executive" -}; -static guint n_paper_format_enum = G_N_ELEMENTS (paper_format_enum); - -void ephy_print_dialog_response_cb (GtkWidget *widget, +void ephy_print_dialog_response_cb (GtkDialog *dialog, int response, - EphyDialog *dialog); -void ephy_print_dialog_browse_button_cb (GtkWidget *widget, - EphyDialog *dialog); + EmbedPrintInfo *info); void ephy_print_setup_dialog_close_button_cb (GtkWidget *widget, EphyDialog *dialog); void ephy_print_setup_dialog_help_button_cb (GtkWidget *widget, @@ -152,10 +91,14 @@ void ephy_print_info_free (EmbedPrintInfo *info) { g_return_if_fail (info != NULL); + + g_object_unref (info->config); + + g_free (info->tempfile); + + if (info->cancel_print_id != 0) + g_signal_handler_disconnect (embed_shell, info->cancel_print_id); - g_free (info->printer); - g_free (info->file); - g_free (info->paper); g_free (info->header_left_string); g_free (info->header_center_string); g_free (info->header_right_string); @@ -165,98 +108,74 @@ ephy_print_info_free (EmbedPrintInfo *info) g_free (info); } -static char * -sanitize_filename (const char *input) +static GnomePrintConfig * +ephy_print_load_config_from_file (void) { - char *dir, *filename; - - if (input == NULL) return NULL; - - if (g_path_is_absolute (input) == FALSE) + gchar *file_name; + gboolean res; + gchar *contents; + GnomePrintConfig *ephy_print_config; + + file_name = g_build_filename (ephy_dot_dir (), PRINT_CONFIG_FILENAME, + NULL); + + res = g_file_get_contents (file_name, &contents, NULL, NULL); + g_free (file_name); + + if (res) { - dir = eel_gconf_get_string (CONF_PRINT_DIR); - /* Fallback */ - if (dir == NULL || g_path_is_absolute (dir) == FALSE) - { - g_free (dir); - dir = g_get_current_dir (); - } - /* Fallback */ - if (dir == NULL) - { - dir = g_strdup (g_get_home_dir ()); - } - - filename = g_build_filename (dir, input, NULL); - g_free (dir); + ephy_print_config = gnome_print_config_from_string (contents, 0); + g_free (contents); } else - { - filename = g_strdup (input); - } + ephy_print_config = gnome_print_config_default (); + + return ephy_print_config; +} - dir = g_path_get_dirname (filename); - if (dir == NULL || g_file_test (dir, G_FILE_TEST_IS_DIR) == FALSE) - { - g_free (filename); - filename = NULL; - } - g_free (dir); +static void +ephy_print_save_config_to_file (GnomePrintConfig *config) +{ + gchar *file_name; + gchar *str; + + g_return_if_fail (config != NULL); - return filename; + str = gnome_print_config_to_string (config, 0); + if (str == NULL) return; + + file_name = g_build_filename (ephy_dot_dir (), PRINT_CONFIG_FILENAME, + NULL); + + g_file_set_contents (file_name, str, -1, NULL); + + g_free (file_name); + g_free (str); +} + +static void +ephy_print_save_config_to_file_and_unref (GnomePrintConfig *config) +{ + ephy_print_save_config_to_file (config); + + g_object_unref (G_OBJECT (config)); } EmbedPrintInfo * ephy_print_get_print_info (void) { EmbedPrintInfo *info; - char *filename, *converted, *expanded, *fname = NULL; info = g_new0 (EmbedPrintInfo, 1); + + info->config = ephy_print_load_config_from_file (); + + info->range = GNOME_PRINT_RANGE_ALL; + info->from_page = 1; + info->to_page = 1; - info->print_to_file = eel_gconf_get_integer (print_props[PRINTON_PROP].pref) == 1; - - if (info->print_to_file) - { - filename = eel_gconf_get_string (print_props[FILE_PROP].pref); - if (filename != NULL) - { - converted = g_filename_from_utf8 (filename, -1, NULL, NULL, NULL); - if (converted != NULL) - { - expanded = gnome_vfs_expand_initial_tilde (filename); - fname = sanitize_filename (expanded); - g_free (expanded); - g_free (converted); - } - } - g_free (filename); - - /* fallback */ - if (fname == NULL) - { - fname = sanitize_filename ("output.ps"); - } - - info->file = g_filename_to_utf8 (fname, -1, NULL, NULL, NULL); - g_free (fname); - } - - info->printer = eel_gconf_get_string (print_props[PRINTER_PROP].pref); - - info->pages = eel_gconf_get_integer (print_props[ALL_PAGES_PROP].pref); - info->from_page = eel_gconf_get_integer (print_props[FROM_PROP].pref); - info->to_page = eel_gconf_get_integer (print_props[TO_PROP].pref); - - info->paper = eel_gconf_get_string (setup_props[PAPER_PROP].pref); - info->orientation = eel_gconf_get_integer (setup_props[ORIENTATION_PROP].pref); info->print_color = ! eel_gconf_get_integer (setup_props[COLOR_PROP].pref); - info->bottom_margin = eel_gconf_get_integer (setup_props[BOTTOM_PROP].pref); - info->top_margin = eel_gconf_get_integer (setup_props[TOP_PROP].pref); - info->left_margin = eel_gconf_get_integer (setup_props[LEFT_PROP].pref); - info->right_margin = eel_gconf_get_integer (setup_props[RIGHT_PROP].pref); - info->header_left_string = eel_gconf_get_boolean (setup_props[PAGE_TITLE_PROP].pref) ? g_strdup ("&T") : g_strdup (""); info->header_right_string = eel_gconf_get_boolean (setup_props[PAGE_URL_PROP].pref) ? @@ -274,76 +193,120 @@ ephy_print_get_print_info (void) } void -ephy_print_dialog_response_cb (GtkWidget *widget, +ephy_print_dialog_response_cb (GtkDialog *dialog, int response, - EphyDialog *dialog) + EmbedPrintInfo *info) { - switch (response) + if (response == GNOME_PRINT_DIALOG_RESPONSE_PRINT) { - case GTK_RESPONSE_HELP: - ephy_gui_help (GTK_WINDOW (widget), "epiphany", "to-print-page"); - return; - default: - break; + ephy_print_save_config_to_file (info->config); + + info->range = gnome_print_dialog_get_range_page (GNOME_PRINT_DIALOG (dialog), + &info->from_page, + &info->to_page); } } -static void -print_filechooser_response_cb (GtkDialog *fc, - int response, - EphyDialog *dialog) +static gboolean +using_postscript_printer (GnomePrintConfig *config) { - if (response == GTK_RESPONSE_ACCEPT) - { - char *filename; - - filename = gtk_file_chooser_get_filename (GTK_FILE_CHOOSER (fc)); - if (filename != NULL) - { - GtkWidget *entry; - char *converted; + const guchar *driver; + const guchar *transport; - converted = g_filename_to_utf8 (filename, -1, NULL, NULL, NULL); + driver = gnome_print_config_get ( + config, (const guchar *)"Settings.Engine.Backend.Driver"); - entry = ephy_dialog_get_control (dialog, print_props[FILE_PROP].id); - gtk_entry_set_text (GTK_ENTRY (entry), converted); + transport = gnome_print_config_get ( + config, (const guchar *)"Settings.Transport.Backend"); - g_free (converted); - g_free (filename); - } + if (driver) + { + if (strcmp ((const gchar *)driver, "gnome-print-ps") == 0) + return TRUE; + else + return FALSE; + } + else if (transport) + { + if (strcmp ((const gchar *)transport, "CUPS") == 0) + return TRUE; + else if (strcmp ((const gchar *)transport, "LPD") == 0) + return TRUE; } - gtk_widget_destroy (GTK_WIDGET (fc)); + return FALSE; } -void -ephy_print_dialog_browse_button_cb (GtkWidget *widget, - EphyDialog *dialog) +gboolean +ephy_print_verify_postscript (GnomePrintDialog *print_dialog) +{ + GnomePrintConfig *config; + GtkWidget *dialog; + + config = gnome_print_dialog_get_config (print_dialog); + + if (using_postscript_printer (config)) + return TRUE; + + dialog = gtk_message_dialog_new ( + GTK_WINDOW (print_dialog), GTK_DIALOG_MODAL, + GTK_MESSAGE_ERROR, GTK_BUTTONS_OK, + _("Printing is not supported on this printer.")); + gtk_message_dialog_format_secondary_text ( + GTK_MESSAGE_DIALOG (dialog), + _("You were trying to print to a printer using the \"%s\" driver. This program requires a PostScript printer driver."), + gnome_print_config_get ( + config, (guchar *)"Settings.Engine.Backend.Driver")); + + if (GTK_WINDOW (print_dialog)->group) + gtk_window_group_add_window (GTK_WINDOW (print_dialog)->group, + GTK_WINDOW (dialog)); + + gtk_dialog_run (GTK_DIALOG (dialog)); + gtk_widget_destroy (dialog); + + return FALSE; +} + +static void +cancel_print_cb (EphyEmbedShell *shell, EmbedPrintInfo *info) { - GtkWidget *parent; - EphyFileChooser *fc; - GtkFileFilter *filter; + g_source_remove (info->print_idle_id); + + ephy_print_info_free (info); +} - parent = ephy_dialog_get_control (dialog, print_props[WINDOW_PROP].id); +static gboolean +ephy_print_do_print_idle_cb (EmbedPrintInfo *info) +{ + GnomePrintJob *job; - fc = ephy_file_chooser_new (_("Print to"), - GTK_WIDGET (parent), - GTK_FILE_CHOOSER_ACTION_SAVE, - CONF_PRINT_DIR, EPHY_FILE_FILTER_NONE); + job = gnome_print_job_new (info->config); - filter = ephy_file_chooser_add_mime_filter (fc, _("Postscript files"), - "application/postscript", NULL); + gnome_print_job_set_file (job, info->tempfile); + gnome_print_job_print (job); - ephy_file_chooser_add_pattern_filter (fc, _("All files"), "*", NULL); + g_object_unref (job); + + unlink (info->tempfile); - gtk_file_chooser_set_filter (GTK_FILE_CHOOSER (fc), filter); + ephy_print_info_free (info); - g_signal_connect (GTK_DIALOG (fc), "response", - G_CALLBACK (print_filechooser_response_cb), - dialog); + return FALSE; +} - gtk_window_set_modal (GTK_WINDOW (fc), TRUE); - gtk_widget_show (GTK_WIDGET (fc)); +void +ephy_print_do_print_and_free (EmbedPrintInfo *info) +{ + /* mozilla printing system hasn't really sent the data + * to the printer when reporting that printing is done, it's + * just ready to do it now + */ + info->print_idle_id = g_idle_add ((GSourceFunc) ephy_print_do_print_idle_cb, + info); + info->cancel_print_id = g_signal_connect (embed_shell, "prepare-close", + G_CALLBACK (cancel_print_cb), + info); } void @@ -360,58 +323,108 @@ ephy_print_setup_dialog_help_button_cb (GtkWidget *widget, ephy_gui_help (GTK_WINDOW (dialog), "epiphany", "using-print-setup"); } -EphyDialog * -ephy_print_dialog_new (GtkWidget *parent, - EphyEmbed *embed) +static GtkWidget * +ephy_print_paper_selector_new () { - EphyDialog *dialog; - GtkWidget *widget; - GList *printers, *l; - GtkListStore *store; - GtkTreeIter iter; - GtkCellRenderer *renderer; - EphyEmbedSingle *single; - - dialog = ephy_dialog_new_with_parent (parent); - - ephy_dialog_construct (dialog, - print_props, - ephy_file ("print.glade"), - "print_dialog", - NULL); - - widget = ephy_dialog_get_control (dialog, print_props[WINDOW_PROP].id); - gtk_window_set_icon_name (GTK_WINDOW (widget), GTK_STOCK_PRINT); - - widget = ephy_dialog_get_control (dialog, print_props[BROWSE_PROP].id); - gtk_widget_set_sensitive (widget, eel_gconf_key_is_writable (CONF_PRINT_FILE)); - - widget = ephy_dialog_get_control (dialog, print_props[PRINTER_PROP].id); - single = EPHY_EMBED_SINGLE (ephy_embed_shell_get_embed_single (embed_shell)); - store = gtk_list_store_new (2, G_TYPE_STRING, G_TYPE_STRING); + GtkWidget *paper_selector; + GnomePrintConfig *config; + + config = ephy_print_load_config_from_file (); + + paper_selector = gnome_paper_selector_new_with_flags (config, + GNOME_PAPER_SELECTOR_MARGINS); + + g_object_set_data_full (G_OBJECT (paper_selector), "config", config, + (GDestroyNotify) ephy_print_save_config_to_file_and_unref); + + return paper_selector; +} - printers = ephy_embed_single_get_printer_list (single); - for (l = printers; l != NULL; l = l->next) - { - gtk_list_store_append (store, &iter); - gtk_list_store_set (store, &iter, - COL_PRINTER_DISPLAY_NAME, l->data, - COL_PRINTER_NAME, l->data, - -1); +/* + * A variant of gnome_print_dialog_construct_range_page that can be used when + * the total page count is unknown. It defaults to 1-1 + */ +static void +ephy_print_dialog_construct_range_page (GnomePrintDialog *gpd, gint flags, + const guchar *currentlabel, const guchar *rangelabel) +{ + GtkWidget *hbox; + + hbox = NULL; + + if (flags & GNOME_PRINT_RANGE_RANGE) { + GtkWidget *l, *sb; + GtkObject *a; + AtkObject *atko; + + hbox = gtk_hbox_new (FALSE, 3); + gtk_widget_show (hbox); + + l = gtk_label_new_with_mnemonic (_("_From:")); + gtk_widget_show (l); + gtk_box_pack_start (GTK_BOX (hbox), l, FALSE, FALSE, 0); + + a = gtk_adjustment_new (1, 1, 9999, 1, 10, 10); + g_object_set_data (G_OBJECT (hbox), "from", a); + sb = gtk_spin_button_new (GTK_ADJUSTMENT (a), 1, 0.0); + gtk_spin_button_set_numeric (GTK_SPIN_BUTTON (sb), TRUE); + gtk_widget_show (sb); + gtk_box_pack_start (GTK_BOX (hbox), sb, FALSE, FALSE, 0); + gtk_label_set_mnemonic_widget ((GtkLabel *) l, sb); + + atko = gtk_widget_get_accessible (sb); + atk_object_set_description (atko, _("Sets the start of the range of pages to be printed")); + + l = gtk_label_new_with_mnemonic (_("_To:")); + gtk_widget_show (l); + gtk_box_pack_start (GTK_BOX (hbox), l, FALSE, FALSE, 0); + + a = gtk_adjustment_new (1, 1, 9999, 1, 10, 10); + g_object_set_data (G_OBJECT (hbox), "to", a); + sb = gtk_spin_button_new (GTK_ADJUSTMENT (a), 1, 0.0); + gtk_spin_button_set_numeric (GTK_SPIN_BUTTON (sb), TRUE); + gtk_widget_show (sb); + gtk_box_pack_start (GTK_BOX (hbox), sb, FALSE, FALSE, 0); + gtk_label_set_mnemonic_widget ((GtkLabel *) l, sb); + + atko = gtk_widget_get_accessible (sb); + atk_object_set_description (atko, _("Sets the end of the range of pages to be printed")); } - g_list_foreach (printers, (GFunc)g_free, NULL); - g_list_free (printers); - gtk_combo_box_set_model (GTK_COMBO_BOX (widget), GTK_TREE_MODEL (store)); - g_object_unref (store); + gnome_print_dialog_construct_range_any (gpd, flags, hbox, currentlabel, rangelabel); +} - renderer = gtk_cell_renderer_text_new (); - gtk_cell_layout_pack_start (GTK_CELL_LAYOUT (widget), renderer, TRUE); - gtk_cell_layout_set_attributes (GTK_CELL_LAYOUT (widget), renderer, - "text", COL_PRINTER_DISPLAY_NAME, - NULL); - ephy_dialog_set_data_column (dialog, print_props[PRINTER_PROP].id, - COL_PRINTER_NAME); +GtkWidget * +ephy_print_dialog_new (GtkWidget *parent, + EmbedPrintInfo *info) +{ + GtkWidget *dialog; + + dialog = g_object_new (GNOME_TYPE_PRINT_DIALOG, "print_config", + info->config, NULL); + + gnome_print_dialog_construct (GNOME_PRINT_DIALOG (dialog), (const guchar *) _("Print"), + GNOME_PRINT_DIALOG_RANGE | + GNOME_PRINT_DIALOG_COPIES); + + ephy_print_dialog_construct_range_page (GNOME_PRINT_DIALOG (dialog), + GNOME_PRINT_RANGE_ALL | + GNOME_PRINT_RANGE_RANGE | + GNOME_PRINT_RANGE_SELECTION, + NULL, (const guchar *) _("Pages")); + + gtk_dialog_set_response_sensitive (GTK_DIALOG (dialog), + GNOME_PRINT_DIALOG_RESPONSE_PREVIEW, + FALSE); + + g_signal_connect (G_OBJECT (dialog), "response", + G_CALLBACK (ephy_print_dialog_response_cb), info); + + gtk_window_set_transient_for (GTK_WINDOW (dialog), GTK_WINDOW (parent)); + + if (GTK_WINDOW (parent)->group) + gtk_window_group_add_window (GTK_WINDOW (parent)->group, + GTK_WINDOW (dialog)); return dialog; } @@ -421,6 +434,7 @@ ephy_print_setup_dialog_new (void) { EphyDialog *dialog; GtkWidget *window; + GtkWidget *paper_selector_hbox; dialog = EPHY_DIALOG (g_object_new (EPHY_TYPE_DIALOG, NULL)); @@ -430,11 +444,14 @@ ephy_print_setup_dialog_new (void) "print_setup_dialog", NULL); - ephy_dialog_add_enum (dialog, setup_props[PAPER_PROP].id, - n_paper_format_enum, paper_format_enum); - window = ephy_dialog_get_control (dialog, setup_props[SETUP_WINDOW_PROP].id); gtk_window_set_icon_name (GTK_WINDOW (window), STOCK_PRINT_SETUP); + + paper_selector_hbox = ephy_dialog_get_control (dialog, + setup_props[PAPER_SELECTOR_PROP].id); + gtk_box_pack_start_defaults (GTK_BOX (paper_selector_hbox), + ephy_print_paper_selector_new ()); + gtk_widget_show_all (paper_selector_hbox); return dialog; } diff --git a/embed/print-dialog.h b/embed/print-dialog.h index 1ca09db8b..34452581d 100644 --- a/embed/print-dialog.h +++ b/embed/print-dialog.h @@ -1,6 +1,7 @@ /* * Copyright (C) 2002 Jorn Baayen * Copyright (C) 2003 Christian Persch + * Copyright (C) 2005 Juerg Billeter * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -29,23 +30,25 @@ #include #include +/* for gnome_print_job_set_file */ +#define GNOME_PRINT_UNSTABLE_API +#include +#include + G_BEGIN_DECLS typedef struct _EmbedPrintInfo { - gboolean print_to_file; - char *printer; - char *file; - char *paper; - int top_margin; - int bottom_margin; - int left_margin; - int right_margin; - int pages; + GnomePrintConfig *config; + + char *tempfile; + guint print_idle_id; + gulong cancel_print_id; + + GnomePrintDialogRangeFlags range; int from_page; int to_page; int frame_type; - int orientation; gboolean print_color; /* @@ -67,8 +70,8 @@ typedef struct _EmbedPrintInfo } EmbedPrintInfo; -EphyDialog *ephy_print_dialog_new (GtkWidget *parent, - EphyEmbed *embed); +GtkWidget *ephy_print_dialog_new (GtkWidget *parent, + EmbedPrintInfo *info); EphyDialog *ephy_print_setup_dialog_new (void); @@ -76,6 +79,10 @@ EmbedPrintInfo *ephy_print_get_print_info (void); void ephy_print_info_free (EmbedPrintInfo *info); +void ephy_print_do_print_and_free (EmbedPrintInfo *info); + +gboolean ephy_print_verify_postscript (GnomePrintDialog *print_dialog); + G_END_DECLS #endif -- cgit v1.2.3