1/* GtkPrinter
2 * Copyright (C) 2006 John (J5) Palmieri <johnp@redhat.com>
3 *
4 * This library is free software; you can redistribute it and/or
5 * modify it under the terms of the GNU Lesser General Public
6 * License as published by the Free Software Foundation; either
7 * version 2 of the License, or (at your option) any later version.
8 *
9 * This library is distributed in the hope that it will be useful,
10 * but WITHOUT ANY WARRANTY; without even the implied warranty of
11 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
12 * Lesser General Public License for more details.
13 *
14 * You should have received a copy of the GNU Lesser General Public
15 * License along with this library. If not, see <http://www.gnu.org/licenses/>.
16 */
17
18#include "config.h"
19#include <stdlib.h>
20#include <string.h>
21#include <stdio.h>
22
23#include "gtkintl.h"
24#include "gtkprivate.h"
25
26#include "gtkprinter.h"
27#include "gtkprinterprivate.h"
28#include "gtkprintbackendprivate.h"
29#include "gtkprintjob.h"
30
31/**
32 * GtkPrinter:
33 *
34 * A `GtkPrinter` object represents a printer.
35 *
36 * You only need to deal directly with printers if you use the
37 * non-portable [class@Gtk.PrintUnixDialog] API.
38 *
39 * A `GtkPrinter` allows to get status information about the printer,
40 * such as its description, its location, the number of queued jobs,
41 * etc. Most importantly, a `GtkPrinter` object can be used to create
42 * a [class@Gtk.PrintJob] object, which lets you print to the printer.
43 */
44
45
46static void gtk_printer_finalize (GObject *object);
47
48struct _GtkPrinterPrivate
49{
50 char *name;
51 char *location;
52 char *description;
53 char *icon_name;
54
55 guint is_active : 1;
56 guint is_paused : 1;
57 guint is_accepting_jobs : 1;
58 guint is_new : 1;
59 guint is_virtual : 1;
60 guint is_default : 1;
61 guint has_details : 1;
62 guint accepts_pdf : 1;
63 guint accepts_ps : 1;
64
65 char *state_message;
66 int job_count;
67
68 GtkPrintBackend *backend;
69};
70
71enum {
72 DETAILS_ACQUIRED,
73 LAST_SIGNAL
74};
75
76enum {
77 PROP_0,
78 PROP_NAME,
79 PROP_BACKEND,
80 PROP_IS_VIRTUAL,
81 PROP_STATE_MESSAGE,
82 PROP_LOCATION,
83 PROP_ICON_NAME,
84 PROP_JOB_COUNT,
85 PROP_ACCEPTS_PDF,
86 PROP_ACCEPTS_PS,
87 PROP_PAUSED,
88 PROP_ACCEPTING_JOBS
89};
90
91static guint signals[LAST_SIGNAL] = { 0 };
92
93static void gtk_printer_set_property (GObject *object,
94 guint prop_id,
95 const GValue *value,
96 GParamSpec *pspec);
97static void gtk_printer_get_property (GObject *object,
98 guint prop_id,
99 GValue *value,
100 GParamSpec *pspec);
101
102G_DEFINE_TYPE_WITH_PRIVATE (GtkPrinter, gtk_printer, G_TYPE_OBJECT)
103
104static void
105gtk_printer_class_init (GtkPrinterClass *class)
106{
107 GObjectClass *object_class;
108 object_class = (GObjectClass *) class;
109
110 object_class->finalize = gtk_printer_finalize;
111
112 object_class->set_property = gtk_printer_set_property;
113 object_class->get_property = gtk_printer_get_property;
114
115 /**
116 * GtkPrinter:name: (attributes org.gtk.Property.get=gtk_printer_get_name)
117 *
118 * The name of the printer.
119 */
120 g_object_class_install_property (G_OBJECT_CLASS (class),
121 property_id: PROP_NAME,
122 pspec: g_param_spec_string (name: "name",
123 P_("Name"),
124 P_("Name of the printer"),
125 default_value: "",
126 GTK_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY));
127
128 /**
129 * GtkPrinter:backend: (attributes org.gtk.Property.get=gtk_printer_get_backend)
130 *
131 * The backend for the printer.
132 */
133 g_object_class_install_property (G_OBJECT_CLASS (class),
134 property_id: PROP_BACKEND,
135 pspec: g_param_spec_object (name: "backend",
136 P_("Backend"),
137 P_("Backend for the printer"),
138 GTK_TYPE_PRINT_BACKEND,
139 GTK_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY));
140
141 /**
142 * GtkPrinter:is-virtual: (attributes org.gtk.Property.get=gtk_printer_is_virtual)
143 *
144 * %FALSE if this represents a real hardware device.
145 */
146 g_object_class_install_property (G_OBJECT_CLASS (class),
147 property_id: PROP_IS_VIRTUAL,
148 pspec: g_param_spec_boolean (name: "is-virtual",
149 P_("Is Virtual"),
150 P_("FALSE if this represents a real hardware printer"),
151 FALSE,
152 GTK_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY));
153
154 /**
155 * GtkPrinter:accepts-pdf: (attributes org.gtk.Property.get=gtk_printer_accepts_pdf)
156 *
157 * %TRUE if this printer can accept PDF.
158 */
159 g_object_class_install_property (G_OBJECT_CLASS (class),
160 property_id: PROP_ACCEPTS_PDF,
161 pspec: g_param_spec_boolean (name: "accepts-pdf",
162 P_("Accepts PDF"),
163 P_("TRUE if this printer can accept PDF"),
164 FALSE,
165 GTK_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY));
166
167 /**
168 * GtkPrinter:accepts-ps: (attributes org.gtk.Property.get=gtk_printer_accepts_ps)
169 *
170 * %TRUE if this printer can accept PostScript.
171 */
172 g_object_class_install_property (G_OBJECT_CLASS (class),
173 property_id: PROP_ACCEPTS_PS,
174 pspec: g_param_spec_boolean (name: "accepts-ps",
175 P_("Accepts PostScript"),
176 P_("TRUE if this printer can accept PostScript"),
177 TRUE,
178 GTK_PARAM_READWRITE | G_PARAM_CONSTRUCT_ONLY));
179
180 /**
181 * GtkPrinter:state-message: (attributes org.gtk.Property.get=gtk_printer_get_state_message)
182 *
183 * String giving the current status of the printer.
184 */
185 g_object_class_install_property (G_OBJECT_CLASS (class),
186 property_id: PROP_STATE_MESSAGE,
187 pspec: g_param_spec_string (name: "state-message",
188 P_("State Message"),
189 P_("String giving the current state of the printer"),
190 default_value: "",
191 GTK_PARAM_READABLE));
192
193 /**
194 * GtkPrinter:location: (attributes org.gtk.Property.get=gtk_printer_get_location)
195 *
196 * Information about the location of the printer.
197 */
198 g_object_class_install_property (G_OBJECT_CLASS (class),
199 property_id: PROP_LOCATION,
200 pspec: g_param_spec_string (name: "location",
201 P_("Location"),
202 P_("The location of the printer"),
203 default_value: "",
204 GTK_PARAM_READABLE));
205
206 /**
207 * GtkPrinter:icon-name: (attributes org.gtk.Property.get=gtk_printer_get_icon_name)
208 *
209 * Icon name to use for the printer.
210 */
211 g_object_class_install_property (G_OBJECT_CLASS (class),
212 property_id: PROP_ICON_NAME,
213 pspec: g_param_spec_string (name: "icon-name",
214 P_("Icon Name"),
215 P_("The icon name to use for the printer"),
216 default_value: "printer",
217 GTK_PARAM_READABLE));
218
219 /**
220 * GtkPrinter:job-count: (attributes org.gtk.Property.get=gtk_printer_get_job_count)
221 *
222 * Number of jobs queued in the printer.
223 */
224 g_object_class_install_property (G_OBJECT_CLASS (class),
225 property_id: PROP_JOB_COUNT,
226 pspec: g_param_spec_int (name: "job-count",
227 P_("Job Count"),
228 P_("Number of jobs queued in the printer"),
229 minimum: 0,
230 G_MAXINT,
231 default_value: 0,
232 GTK_PARAM_READABLE));
233
234 /**
235 * GtkPrinter:paused: (attributes org.gtk.Property.get=gtk_printer_is_paused)
236 *
237 * %TRUE if this printer is paused.
238 *
239 * A paused printer still accepts jobs, but it does
240 * not print them.
241 */
242 g_object_class_install_property (G_OBJECT_CLASS (class),
243 property_id: PROP_PAUSED,
244 pspec: g_param_spec_boolean (name: "paused",
245 P_("Paused Printer"),
246 P_("TRUE if this printer is paused"),
247 FALSE,
248 GTK_PARAM_READABLE));
249
250 /**
251 * GtkPrinter:accepting-jobs: (attributes org.gtk.Property.get=gtk_printer_is_accepting_jobs)
252 *
253 * %TRUE if the printer is accepting jobs.
254 */
255 g_object_class_install_property (G_OBJECT_CLASS (class),
256 property_id: PROP_ACCEPTING_JOBS,
257 pspec: g_param_spec_boolean (name: "accepting-jobs",
258 P_("Accepting Jobs"),
259 P_("TRUE if this printer is accepting new jobs"),
260 TRUE,
261 GTK_PARAM_READABLE));
262
263 /**
264 * GtkPrinter::details-acquired:
265 * @printer: the `GtkPrinter` on which the signal is emitted
266 * @success: %TRUE if the details were successfully acquired
267 *
268 * Emitted in response to a request for detailed information
269 * about a printer from the print backend.
270 *
271 * The @success parameter indicates if the information was
272 * actually obtained.
273 */
274 signals[DETAILS_ACQUIRED] =
275 g_signal_new (I_("details-acquired"),
276 G_TYPE_FROM_CLASS (class),
277 signal_flags: G_SIGNAL_RUN_LAST,
278 G_STRUCT_OFFSET (GtkPrinterClass, details_acquired),
279 NULL, NULL,
280 NULL,
281 G_TYPE_NONE, n_params: 1, G_TYPE_BOOLEAN);
282}
283
284static void
285gtk_printer_init (GtkPrinter *printer)
286{
287 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
288
289 priv->name = NULL;
290 priv->location = NULL;
291 priv->description = NULL;
292 priv->icon_name = g_strdup (str: "printer");
293
294 priv->is_active = TRUE;
295 priv->is_paused = FALSE;
296 priv->is_accepting_jobs = TRUE;
297 priv->is_new = TRUE;
298 priv->has_details = FALSE;
299 priv->accepts_pdf = FALSE;
300 priv->accepts_ps = TRUE;
301
302 priv->state_message = NULL;
303 priv->job_count = 0;
304}
305
306static void
307gtk_printer_finalize (GObject *object)
308{
309 GtkPrinter *printer = GTK_PRINTER (object);
310 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
311
312 g_free (mem: priv->name);
313 g_free (mem: priv->location);
314 g_free (mem: priv->description);
315 g_free (mem: priv->state_message);
316 g_free (mem: priv->icon_name);
317
318 if (priv->backend)
319 g_object_unref (object: priv->backend);
320
321 G_OBJECT_CLASS (gtk_printer_parent_class)->finalize (object);
322}
323
324static void
325gtk_printer_set_property (GObject *object,
326 guint prop_id,
327 const GValue *value,
328 GParamSpec *pspec)
329{
330 GtkPrinter *printer = GTK_PRINTER (object);
331 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
332
333 switch (prop_id)
334 {
335 case PROP_NAME:
336 priv->name = g_value_dup_string (value);
337 break;
338
339 case PROP_BACKEND:
340 priv->backend = GTK_PRINT_BACKEND (g_value_dup_object (value));
341 break;
342
343 case PROP_IS_VIRTUAL:
344 priv->is_virtual = g_value_get_boolean (value);
345 break;
346
347 case PROP_ACCEPTS_PDF:
348 priv->accepts_pdf = g_value_get_boolean (value);
349 break;
350
351 case PROP_ACCEPTS_PS:
352 priv->accepts_ps = g_value_get_boolean (value);
353 break;
354
355 default:
356 G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
357 break;
358 }
359}
360
361static void
362gtk_printer_get_property (GObject *object,
363 guint prop_id,
364 GValue *value,
365 GParamSpec *pspec)
366{
367 GtkPrinter *printer = GTK_PRINTER (object);
368 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
369
370 switch (prop_id)
371 {
372 case PROP_NAME:
373 if (priv->name)
374 g_value_set_string (value, v_string: priv->name);
375 else
376 g_value_set_static_string (value, v_string: "");
377 break;
378 case PROP_BACKEND:
379 g_value_set_object (value, v_object: priv->backend);
380 break;
381 case PROP_STATE_MESSAGE:
382 if (priv->state_message)
383 g_value_set_string (value, v_string: priv->state_message);
384 else
385 g_value_set_static_string (value, v_string: "");
386 break;
387 case PROP_LOCATION:
388 if (priv->location)
389 g_value_set_string (value, v_string: priv->location);
390 else
391 g_value_set_static_string (value, v_string: "");
392 break;
393 case PROP_ICON_NAME:
394 if (priv->icon_name)
395 g_value_set_string (value, v_string: priv->icon_name);
396 else
397 g_value_set_static_string (value, v_string: "printer");
398 break;
399 case PROP_JOB_COUNT:
400 g_value_set_int (value, v_int: priv->job_count);
401 break;
402 case PROP_IS_VIRTUAL:
403 g_value_set_boolean (value, v_boolean: priv->is_virtual);
404 break;
405 case PROP_ACCEPTS_PDF:
406 g_value_set_boolean (value, v_boolean: priv->accepts_pdf);
407 break;
408 case PROP_ACCEPTS_PS:
409 g_value_set_boolean (value, v_boolean: priv->accepts_ps);
410 break;
411 case PROP_PAUSED:
412 g_value_set_boolean (value, v_boolean: priv->is_paused);
413 break;
414 case PROP_ACCEPTING_JOBS:
415 g_value_set_boolean (value, v_boolean: priv->is_accepting_jobs);
416 break;
417 default:
418 G_OBJECT_WARN_INVALID_PROPERTY_ID (object, prop_id, pspec);
419 break;
420 }
421}
422
423/**
424 * gtk_printer_new:
425 * @name: the name of the printer
426 * @backend: a `GtkPrintBackend`
427 * @virtual_: whether the printer is virtual
428 *
429 * Creates a new `GtkPrinter`.
430 *
431 * Returns: a new `GtkPrinter`
432 */
433GtkPrinter *
434gtk_printer_new (const char *name,
435 GtkPrintBackend *backend,
436 gboolean virtual_)
437{
438 GObject *result;
439
440 result = g_object_new (GTK_TYPE_PRINTER,
441 first_property_name: "name", name,
442 "backend", backend,
443 "is-virtual", virtual_,
444 NULL);
445
446 return (GtkPrinter *) result;
447}
448
449/**
450 * gtk_printer_get_backend: (attributes org.gtk.Method.get_property=backend)
451 * @printer: a `GtkPrinter`
452 *
453 * Returns the backend of the printer.
454 *
455 * Returns: (transfer none): the backend of @printer
456 */
457GtkPrintBackend *
458gtk_printer_get_backend (GtkPrinter *printer)
459{
460 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
461
462 g_return_val_if_fail (GTK_IS_PRINTER (printer), NULL);
463
464 return priv->backend;
465}
466
467/**
468 * gtk_printer_get_name: (attributes org.gtk.Method.get_property=name)
469 * @printer: a `GtkPrinter`
470 *
471 * Returns the name of the printer.
472 *
473 * Returns: the name of @printer
474 */
475const char *
476gtk_printer_get_name (GtkPrinter *printer)
477{
478 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
479
480 g_return_val_if_fail (GTK_IS_PRINTER (printer), NULL);
481
482 return priv->name;
483}
484
485/**
486 * gtk_printer_get_description:
487 * @printer: a `GtkPrinter`
488 *
489 * Gets the description of the printer.
490 *
491 * Returns: the description of @printer
492 */
493const char *
494gtk_printer_get_description (GtkPrinter *printer)
495{
496 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
497
498 g_return_val_if_fail (GTK_IS_PRINTER (printer), NULL);
499
500 return priv->description;
501}
502
503gboolean
504gtk_printer_set_description (GtkPrinter *printer,
505 const char *description)
506{
507 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
508
509 g_return_val_if_fail (GTK_IS_PRINTER (printer), FALSE);
510
511 if (g_strcmp0 (str1: priv->description, str2: description) == 0)
512 return FALSE;
513
514 g_free (mem: priv->description);
515 priv->description = g_strdup (str: description);
516
517 return TRUE;
518}
519
520/**
521 * gtk_printer_get_state_message: (attributes org.gtk.Method.get_property=state-message)
522 * @printer: a `GtkPrinter`
523 *
524 * Returns the state message describing the current state
525 * of the printer.
526 *
527 * Returns: the state message of @printer
528 */
529const char *
530gtk_printer_get_state_message (GtkPrinter *printer)
531{
532 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
533
534 g_return_val_if_fail (GTK_IS_PRINTER (printer), NULL);
535
536 return priv->state_message;
537}
538
539gboolean
540gtk_printer_set_state_message (GtkPrinter *printer,
541 const char *message)
542{
543 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
544
545 g_return_val_if_fail (GTK_IS_PRINTER (printer), FALSE);
546
547 if (g_strcmp0 (str1: priv->state_message, str2: message) == 0)
548 return FALSE;
549
550 g_free (mem: priv->state_message);
551 priv->state_message = g_strdup (str: message);
552 g_object_notify (G_OBJECT (printer), property_name: "state-message");
553
554 return TRUE;
555}
556
557/**
558 * gtk_printer_get_location: (attributes org.gtk.Method.get_property=location)
559 * @printer: a `GtkPrinter`
560 *
561 * Returns a description of the location of the printer.
562 *
563 * Returns: the location of @printer
564 */
565const char *
566gtk_printer_get_location (GtkPrinter *printer)
567{
568 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
569
570 g_return_val_if_fail (GTK_IS_PRINTER (printer), NULL);
571
572 return priv->location;
573}
574
575gboolean
576gtk_printer_set_location (GtkPrinter *printer,
577 const char *location)
578{
579 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
580
581 g_return_val_if_fail (GTK_IS_PRINTER (printer), FALSE);
582
583 if (g_strcmp0 (str1: priv->location, str2: location) == 0)
584 return FALSE;
585
586 g_free (mem: priv->location);
587 priv->location = g_strdup (str: location);
588 g_object_notify (G_OBJECT (printer), property_name: "location");
589
590 return TRUE;
591}
592
593/**
594 * gtk_printer_get_icon_name: (attributes org.gtk.Method.get_property=icon-name)
595 * @printer: a `GtkPrinter`
596 *
597 * Gets the name of the icon to use for the printer.
598 *
599 * Returns: the icon name for @printer
600 */
601const char *
602gtk_printer_get_icon_name (GtkPrinter *printer)
603{
604 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
605
606 g_return_val_if_fail (GTK_IS_PRINTER (printer), NULL);
607
608 return priv->icon_name;
609}
610
611void
612gtk_printer_set_icon_name (GtkPrinter *printer,
613 const char *icon)
614{
615 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
616
617 g_return_if_fail (GTK_IS_PRINTER (printer));
618
619 g_free (mem: priv->icon_name);
620 priv->icon_name = g_strdup (str: icon);
621 g_object_notify (G_OBJECT (printer), property_name: "icon-name");
622}
623
624/**
625 * gtk_printer_get_job_count: (attributes org.gtk.Method.get_property=job-count)
626 * @printer: a `GtkPrinter`
627 *
628 * Gets the number of jobs currently queued on the printer.
629 *
630 * Returns: the number of jobs on @printer
631 */
632int
633gtk_printer_get_job_count (GtkPrinter *printer)
634{
635 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
636
637 g_return_val_if_fail (GTK_IS_PRINTER (printer), 0);
638
639 return priv->job_count;
640}
641
642gboolean
643gtk_printer_set_job_count (GtkPrinter *printer,
644 int count)
645{
646 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
647
648 g_return_val_if_fail (GTK_IS_PRINTER (printer), FALSE);
649
650 if (priv->job_count == count)
651 return FALSE;
652
653 priv->job_count = count;
654
655 g_object_notify (G_OBJECT (printer), property_name: "job-count");
656
657 return TRUE;
658}
659
660/**
661 * gtk_printer_has_details:
662 * @printer: a `GtkPrinter`
663 *
664 * Returns whether the printer details are available.
665 *
666 * Returns: %TRUE if @printer details are available
667 */
668gboolean
669gtk_printer_has_details (GtkPrinter *printer)
670{
671 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
672
673 g_return_val_if_fail (GTK_IS_PRINTER (printer), FALSE);
674
675 return priv->has_details;
676}
677
678void
679gtk_printer_set_has_details (GtkPrinter *printer,
680 gboolean val)
681{
682 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
683
684 priv->has_details = val;
685}
686
687/**
688 * gtk_printer_is_active:
689 * @printer: a `GtkPrinter`
690 *
691 * Returns whether the printer is currently active (i.e.
692 * accepts new jobs).
693 *
694 * Returns: %TRUE if @printer is active
695 */
696gboolean
697gtk_printer_is_active (GtkPrinter *printer)
698{
699 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
700
701 g_return_val_if_fail (GTK_IS_PRINTER (printer), TRUE);
702
703 return priv->is_active;
704}
705
706void
707gtk_printer_set_is_active (GtkPrinter *printer,
708 gboolean val)
709{
710 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
711
712 g_return_if_fail (GTK_IS_PRINTER (printer));
713
714 priv->is_active = val;
715}
716
717/**
718 * gtk_printer_is_paused: (attributes org.gtk.Method.get_property=paused)
719 * @printer: a `GtkPrinter`
720 *
721 * Returns whether the printer is currently paused.
722 *
723 * A paused printer still accepts jobs, but it is not
724 * printing them.
725 *
726 * Returns: %TRUE if @printer is paused
727 */
728gboolean
729gtk_printer_is_paused (GtkPrinter *printer)
730{
731 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
732
733 g_return_val_if_fail (GTK_IS_PRINTER (printer), TRUE);
734
735 return priv->is_paused;
736}
737
738gboolean
739gtk_printer_set_is_paused (GtkPrinter *printer,
740 gboolean val)
741{
742 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
743
744 g_return_val_if_fail (GTK_IS_PRINTER (printer), FALSE);
745
746 if (val == priv->is_paused)
747 return FALSE;
748
749 priv->is_paused = val;
750
751 return TRUE;
752}
753
754/**
755 * gtk_printer_is_accepting_jobs: (attributes org.gtk.Method.get_property=accepting-jobs)
756 * @printer: a `GtkPrinter`
757 *
758 * Returns whether the printer is accepting jobs
759 *
760 * Returns: %TRUE if @printer is accepting jobs
761 */
762gboolean
763gtk_printer_is_accepting_jobs (GtkPrinter *printer)
764{
765 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
766
767 g_return_val_if_fail (GTK_IS_PRINTER (printer), TRUE);
768
769 return priv->is_accepting_jobs;
770}
771
772gboolean
773gtk_printer_set_is_accepting_jobs (GtkPrinter *printer,
774 gboolean val)
775{
776 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
777
778 g_return_val_if_fail (GTK_IS_PRINTER (printer), FALSE);
779
780 if (val == priv->is_accepting_jobs)
781 return FALSE;
782
783 priv->is_accepting_jobs = val;
784
785 return TRUE;
786}
787
788/**
789 * gtk_printer_is_virtual: (attributes org.gtk.Method.get_property=is-virtual)
790 * @printer: a `GtkPrinter`
791 *
792 * Returns whether the printer is virtual (i.e. does not
793 * represent actual printer hardware, but something like
794 * a CUPS class).
795 *
796 * Returns: %TRUE if @printer is virtual
797 */
798gboolean
799gtk_printer_is_virtual (GtkPrinter *printer)
800{
801 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
802
803 g_return_val_if_fail (GTK_IS_PRINTER (printer), TRUE);
804
805 return priv->is_virtual;
806}
807
808/**
809 * gtk_printer_accepts_pdf: (attributes org.gtk.Method.get_property=accepts-pdf)
810 * @printer: a `GtkPrinter`
811 *
812 * Returns whether the printer accepts input in
813 * PDF format.
814 *
815 * Returns: %TRUE if @printer accepts PDF
816 */
817gboolean
818gtk_printer_accepts_pdf (GtkPrinter *printer)
819{
820 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
821
822 g_return_val_if_fail (GTK_IS_PRINTER (printer), TRUE);
823
824 return priv->accepts_pdf;
825}
826
827void
828gtk_printer_set_accepts_pdf (GtkPrinter *printer,
829 gboolean val)
830{
831 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
832
833 g_return_if_fail (GTK_IS_PRINTER (printer));
834
835 priv->accepts_pdf = val;
836}
837
838/**
839 * gtk_printer_accepts_ps: (attributes org.gtk.Method.get_property=accepts-ps)
840 * @printer: a `GtkPrinter`
841 *
842 * Returns whether the printer accepts input in
843 * PostScript format.
844 *
845 * Returns: %TRUE if @printer accepts PostScript
846 */
847gboolean
848gtk_printer_accepts_ps (GtkPrinter *printer)
849{
850 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
851
852 g_return_val_if_fail (GTK_IS_PRINTER (printer), TRUE);
853
854 return priv->accepts_ps;
855}
856
857void
858gtk_printer_set_accepts_ps (GtkPrinter *printer,
859 gboolean val)
860{
861 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
862
863 g_return_if_fail (GTK_IS_PRINTER (printer));
864
865 priv->accepts_ps = val;
866}
867
868gboolean
869gtk_printer_is_new (GtkPrinter *printer)
870{
871 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
872
873 g_return_val_if_fail (GTK_IS_PRINTER (printer), FALSE);
874
875 return priv->is_new;
876}
877
878void
879gtk_printer_set_is_new (GtkPrinter *printer,
880 gboolean val)
881{
882 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
883
884 g_return_if_fail (GTK_IS_PRINTER (printer));
885
886 priv->is_new = val;
887}
888
889
890/**
891 * gtk_printer_is_default:
892 * @printer: a `GtkPrinter`
893 *
894 * Returns whether the printer is the default printer.
895 *
896 * Returns: %TRUE if @printer is the default
897 */
898gboolean
899gtk_printer_is_default (GtkPrinter *printer)
900{
901 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
902
903 g_return_val_if_fail (GTK_IS_PRINTER (printer), FALSE);
904
905 return priv->is_default;
906}
907
908void
909gtk_printer_set_is_default (GtkPrinter *printer,
910 gboolean val)
911{
912 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
913
914 g_return_if_fail (GTK_IS_PRINTER (printer));
915
916 priv->is_default = val;
917}
918
919/**
920 * gtk_printer_request_details:
921 * @printer: a `GtkPrinter`
922 *
923 * Requests the printer details.
924 *
925 * When the details are available, the
926 * [signal@Gtk.Printer::details-acquired] signal
927 * will be emitted on @printer.
928 */
929void
930gtk_printer_request_details (GtkPrinter *printer)
931{
932 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
933 GtkPrintBackendClass *backend_class;
934
935 g_return_if_fail (GTK_IS_PRINTER (printer));
936
937 backend_class = GTK_PRINT_BACKEND_GET_CLASS (priv->backend);
938 backend_class->printer_request_details (printer);
939}
940
941GtkPrinterOptionSet *
942_gtk_printer_get_options (GtkPrinter *printer,
943 GtkPrintSettings *settings,
944 GtkPageSetup *page_setup,
945 GtkPrintCapabilities capabilities)
946{
947 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
948 GtkPrintBackendClass *backend_class = GTK_PRINT_BACKEND_GET_CLASS (priv->backend);
949
950 return backend_class->printer_get_options (printer, settings, page_setup, capabilities);
951}
952
953gboolean
954_gtk_printer_mark_conflicts (GtkPrinter *printer,
955 GtkPrinterOptionSet *options)
956{
957 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
958 GtkPrintBackendClass *backend_class = GTK_PRINT_BACKEND_GET_CLASS (priv->backend);
959
960 return backend_class->printer_mark_conflicts (printer, options);
961}
962
963void
964_gtk_printer_get_settings_from_options (GtkPrinter *printer,
965 GtkPrinterOptionSet *options,
966 GtkPrintSettings *settings)
967{
968 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
969 GtkPrintBackendClass *backend_class = GTK_PRINT_BACKEND_GET_CLASS (priv->backend);
970
971 backend_class->printer_get_settings_from_options (printer, options, settings);
972}
973
974void
975_gtk_printer_prepare_for_print (GtkPrinter *printer,
976 GtkPrintJob *print_job,
977 GtkPrintSettings *settings,
978 GtkPageSetup *page_setup)
979{
980 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
981 GtkPrintBackendClass *backend_class = GTK_PRINT_BACKEND_GET_CLASS (priv->backend);
982
983 backend_class->printer_prepare_for_print (printer, print_job, settings, page_setup);
984}
985
986cairo_surface_t *
987_gtk_printer_create_cairo_surface (GtkPrinter *printer,
988 GtkPrintSettings *settings,
989 double width,
990 double height,
991 GIOChannel *cache_io)
992{
993 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
994 GtkPrintBackendClass *backend_class = GTK_PRINT_BACKEND_GET_CLASS (priv->backend);
995
996 return backend_class->printer_create_cairo_surface (printer, settings,
997 width, height, cache_io);
998}
999
1000/**
1001 * gtk_printer_list_papers:
1002 * @printer: a `GtkPrinter`
1003 *
1004 * Lists all the paper sizes @printer supports.
1005 *
1006 * This will return and empty list unless the printer’s details
1007 * are available, see [method@Gtk.Printer.has_details] and
1008 * [method@Gtk.Printer.request_details].
1009 *
1010 * Returns: (element-type GtkPageSetup) (transfer full): a newly
1011 * allocated list of newly allocated `GtkPageSetup`s.
1012 */
1013GList *
1014gtk_printer_list_papers (GtkPrinter *printer)
1015{
1016 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
1017 GtkPrintBackendClass *backend_class;
1018
1019 g_return_val_if_fail (GTK_IS_PRINTER (printer), NULL);
1020
1021 backend_class = GTK_PRINT_BACKEND_GET_CLASS (priv->backend);
1022 return backend_class->printer_list_papers (printer);
1023}
1024
1025/**
1026 * gtk_printer_get_default_page_size:
1027 * @printer: a `GtkPrinter`
1028 *
1029 * Returns default page size of @printer.
1030 *
1031 * Returns: (transfer full): a newly allocated `GtkPageSetup` with default page size
1032 * of the printer.
1033 */
1034GtkPageSetup *
1035gtk_printer_get_default_page_size (GtkPrinter *printer)
1036{
1037 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
1038 GtkPrintBackendClass *backend_class;
1039
1040 g_return_val_if_fail (GTK_IS_PRINTER (printer), NULL);
1041
1042 backend_class = GTK_PRINT_BACKEND_GET_CLASS (priv->backend);
1043
1044 return backend_class->printer_get_default_page_size (printer);
1045}
1046
1047/**
1048 * gtk_printer_get_hard_margins:
1049 * @printer: a `GtkPrinter`
1050 * @top: (out): a location to store the top margin in
1051 * @bottom: (out): a location to store the bottom margin in
1052 * @left: (out): a location to store the left margin in
1053 * @right: (out): a location to store the right margin in
1054 *
1055 * Retrieve the hard margins of @printer.
1056 *
1057 * These are the margins that define the area at the borders
1058 * of the paper that the printer cannot print to.
1059 *
1060 * Note: This will not succeed unless the printer’s details are
1061 * available, see [method@Gtk.Printer.has_details] and
1062 * [method@Gtk.Printer.request_details].
1063 *
1064 * Returns: %TRUE iff the hard margins were retrieved
1065 */
1066gboolean
1067gtk_printer_get_hard_margins (GtkPrinter *printer,
1068 double *top,
1069 double *bottom,
1070 double *left,
1071 double *right)
1072{
1073 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
1074 GtkPrintBackendClass *backend_class = GTK_PRINT_BACKEND_GET_CLASS (priv->backend);
1075
1076 return backend_class->printer_get_hard_margins (printer, top, bottom, left, right);
1077}
1078
1079/**
1080 * gtk_printer_get_hard_margins_for_paper_size:
1081 * @printer: a `GtkPrinter`
1082 * @paper_size: a `GtkPaperSize`
1083 * @top: (out): a location to store the top margin in
1084 * @bottom: (out): a location to store the bottom margin in
1085 * @left: (out): a location to store the left margin in
1086 * @right: (out): a location to store the right margin in
1087 *
1088 * Retrieve the hard margins of @printer for @paper_size.
1089 *
1090 * These are the margins that define the area at the borders
1091 * of the paper that the printer cannot print to.
1092 *
1093 * Note: This will not succeed unless the printer’s details are
1094 * available, see [method@Gtk.Printer.has_details] and
1095 * [method@Gtk.Printer.request_details].
1096 *
1097 * Return value: %TRUE iff the hard margins were retrieved
1098 */
1099gboolean
1100gtk_printer_get_hard_margins_for_paper_size (GtkPrinter *printer,
1101 GtkPaperSize *paper_size,
1102 double *top,
1103 double *bottom,
1104 double *left,
1105 double *right)
1106{
1107 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
1108 GtkPrintBackendClass *backend_class = GTK_PRINT_BACKEND_GET_CLASS (priv->backend);
1109
1110 return backend_class->printer_get_hard_margins_for_paper_size (printer, paper_size, top, bottom, left, right);
1111}
1112
1113/**
1114 * gtk_printer_get_capabilities:
1115 * @printer: a `GtkPrinter`
1116 *
1117 * Returns the printer’s capabilities.
1118 *
1119 * This is useful when you’re using `GtkPrintUnixDialog`’s
1120 * manual-capabilities setting and need to know which settings
1121 * the printer can handle and which you must handle yourself.
1122 *
1123 * This will return 0 unless the printer’s details are
1124 * available, see [method@Gtk.Printer.has_details] and
1125 * [method@Gtk.Printer.request_details].
1126 *
1127 * Returns: the printer’s capabilities
1128 */
1129GtkPrintCapabilities
1130gtk_printer_get_capabilities (GtkPrinter *printer)
1131{
1132 GtkPrinterPrivate *priv = gtk_printer_get_instance_private (self: printer);
1133 GtkPrintBackendClass *backend_class;
1134
1135 g_return_val_if_fail (GTK_IS_PRINTER (printer), 0);
1136
1137 backend_class = GTK_PRINT_BACKEND_GET_CLASS (priv->backend);
1138 return backend_class->printer_get_capabilities (printer);
1139}
1140
1141/**
1142 * gtk_printer_compare:
1143 * @a: a `GtkPrinter`
1144 * @b: another `GtkPrinter`
1145 *
1146 * Compares two printers.
1147 *
1148 * Returns: 0 if the printer match, a negative value if @a < @b,
1149 * or a positive value if @a > @b
1150 */
1151int
1152gtk_printer_compare (GtkPrinter *a,
1153 GtkPrinter *b)
1154{
1155 const char *name_a, *name_b;
1156
1157 g_assert (GTK_IS_PRINTER (a) && GTK_IS_PRINTER (b));
1158
1159 name_a = gtk_printer_get_name (printer: a);
1160 name_b = gtk_printer_get_name (printer: b);
1161 if (name_a == NULL && name_b == NULL)
1162 return 0;
1163 else if (name_a == NULL)
1164 return G_MAXINT;
1165 else if (name_b == NULL)
1166 return G_MININT;
1167 else
1168 return g_ascii_strcasecmp (s1: name_a, s2: name_b);
1169}
1170
1171
1172typedef struct
1173{
1174 GList *backends;
1175 GtkPrinterFunc func;
1176 gpointer data;
1177 GDestroyNotify destroy;
1178 GMainLoop *loop;
1179} PrinterList;
1180
1181static void list_done_cb (GtkPrintBackend *backend,
1182 PrinterList *printer_list);
1183
1184static void
1185stop_enumeration (PrinterList *printer_list)
1186{
1187 GList *list, *next;
1188 GtkPrintBackend *backend;
1189
1190 for (list = printer_list->backends; list; list = next)
1191 {
1192 next = list->next;
1193 backend = GTK_PRINT_BACKEND (list->data);
1194 list_done_cb (backend, printer_list);
1195 }
1196}
1197
1198static void
1199free_printer_list (PrinterList *printer_list)
1200{
1201 if (printer_list->destroy)
1202 printer_list->destroy (printer_list->data);
1203
1204 if (printer_list->loop)
1205 {
1206 g_main_loop_quit (loop: printer_list->loop);
1207 g_main_loop_unref (loop: printer_list->loop);
1208 }
1209
1210 g_free (mem: printer_list);
1211}
1212
1213static gboolean
1214list_added_cb (GtkPrintBackend *backend,
1215 GtkPrinter *printer,
1216 PrinterList *printer_list)
1217{
1218 if (printer_list->func (printer, printer_list->data))
1219 {
1220 stop_enumeration (printer_list);
1221 return TRUE;
1222 }
1223
1224 return FALSE;
1225}
1226
1227static void
1228backend_status_changed (GObject *object,
1229 GParamSpec *pspec,
1230 gpointer data)
1231{
1232 GtkPrintBackend *backend = GTK_PRINT_BACKEND (object);
1233 PrinterList *printer_list = data;
1234 GtkPrintBackendStatus status;
1235
1236 g_object_get (object: backend, first_property_name: "status", &status, NULL);
1237
1238 if (status == GTK_PRINT_BACKEND_STATUS_UNAVAILABLE)
1239 list_done_cb (backend, printer_list);
1240}
1241
1242static gboolean
1243list_printers_remove_backend (PrinterList *printer_list,
1244 GtkPrintBackend *backend)
1245{
1246 printer_list->backends = g_list_remove (list: printer_list->backends, data: backend);
1247 gtk_print_backend_destroy (print_backend: backend);
1248 g_object_unref (object: backend);
1249
1250 if (printer_list->backends == NULL)
1251 {
1252 free_printer_list (printer_list);
1253 return TRUE;
1254 }
1255
1256 return FALSE;
1257}
1258
1259static void
1260list_done_cb (GtkPrintBackend *backend,
1261 PrinterList *printer_list)
1262{
1263 g_signal_handlers_disconnect_by_func (backend, list_added_cb, printer_list);
1264 g_signal_handlers_disconnect_by_func (backend, list_done_cb, printer_list);
1265 g_signal_handlers_disconnect_by_func (backend, backend_status_changed, printer_list);
1266
1267 list_printers_remove_backend(printer_list, backend);
1268}
1269
1270static gboolean
1271list_printers_init (PrinterList *printer_list,
1272 GtkPrintBackend *backend)
1273{
1274 GList *list, *node;
1275 GtkPrintBackendStatus status;
1276
1277 list = gtk_print_backend_get_printer_list (print_backend: backend);
1278
1279 for (node = list; node != NULL; node = node->next)
1280 {
1281 if (list_added_cb (backend, printer: node->data, printer_list))
1282 {
1283 g_list_free (list);
1284 return TRUE;
1285 }
1286 }
1287
1288 g_list_free (list);
1289
1290 g_object_get (object: backend, first_property_name: "status", &status, NULL);
1291
1292 if (status == GTK_PRINT_BACKEND_STATUS_UNAVAILABLE ||
1293 gtk_print_backend_printer_list_is_done (print_backend: backend))
1294 {
1295 if (list_printers_remove_backend (printer_list, backend))
1296 return TRUE;
1297 }
1298 else
1299 {
1300 g_signal_connect (backend, "printer-added",
1301 (GCallback) list_added_cb,
1302 printer_list);
1303 g_signal_connect (backend, "printer-list-done",
1304 (GCallback) list_done_cb,
1305 printer_list);
1306 g_signal_connect (backend, "notify::status",
1307 (GCallback) backend_status_changed,
1308 printer_list);
1309 }
1310
1311 return FALSE;
1312}
1313
1314/**
1315 * gtk_enumerate_printers:
1316 * @func: a function to call for each printer
1317 * @data: user data to pass to @func
1318 * @destroy: function to call if @data is no longer needed
1319 * @wait: if %TRUE, wait in a recursive mainloop until
1320 * all printers are enumerated; otherwise return early
1321 *
1322 * Calls a function for all `GtkPrinter`s.
1323 *
1324 * If @func returns %TRUE, the enumeration is stopped.
1325 */
1326void
1327gtk_enumerate_printers (GtkPrinterFunc func,
1328 gpointer data,
1329 GDestroyNotify destroy,
1330 gboolean wait)
1331{
1332 PrinterList *printer_list;
1333 GList *node, *next;
1334 GtkPrintBackend *backend;
1335
1336 printer_list = g_new0 (PrinterList, 1);
1337
1338 printer_list->func = func;
1339 printer_list->data = data;
1340 printer_list->destroy = destroy;
1341
1342 if (g_module_supported ())
1343 printer_list->backends = gtk_print_backend_load_modules ();
1344
1345 if (printer_list->backends == NULL)
1346 {
1347 free_printer_list (printer_list);
1348 return;
1349 }
1350
1351 for (node = printer_list->backends; node != NULL; node = next)
1352 {
1353 next = node->next;
1354 backend = GTK_PRINT_BACKEND (node->data);
1355 if (list_printers_init (printer_list, backend))
1356 return;
1357 }
1358
1359 if (wait && printer_list->backends)
1360 {
1361 printer_list->loop = g_main_loop_new (NULL, FALSE);
1362 g_main_loop_run (loop: printer_list->loop);
1363 }
1364}
1365
1366GType
1367gtk_print_capabilities_get_type (void)
1368{
1369 static GType etype = 0;
1370
1371 if (G_UNLIKELY (etype == 0))
1372 {
1373 static const GFlagsValue values[] = {
1374 { GTK_PRINT_CAPABILITY_PAGE_SET, "GTK_PRINT_CAPABILITY_PAGE_SET", "page-set" },
1375 { GTK_PRINT_CAPABILITY_COPIES, "GTK_PRINT_CAPABILITY_COPIES", "copies" },
1376 { GTK_PRINT_CAPABILITY_COLLATE, "GTK_PRINT_CAPABILITY_COLLATE", "collate" },
1377 { GTK_PRINT_CAPABILITY_REVERSE, "GTK_PRINT_CAPABILITY_REVERSE", "reverse" },
1378 { GTK_PRINT_CAPABILITY_SCALE, "GTK_PRINT_CAPABILITY_SCALE", "scale" },
1379 { GTK_PRINT_CAPABILITY_GENERATE_PDF, "GTK_PRINT_CAPABILITY_GENERATE_PDF", "generate-pdf" },
1380 { GTK_PRINT_CAPABILITY_GENERATE_PS, "GTK_PRINT_CAPABILITY_GENERATE_PS", "generate-ps" },
1381 { GTK_PRINT_CAPABILITY_PREVIEW, "GTK_PRINT_CAPABILITY_PREVIEW", "preview" },
1382 { GTK_PRINT_CAPABILITY_NUMBER_UP, "GTK_PRINT_CAPABILITY_NUMBER_UP", "number-up"},
1383 { GTK_PRINT_CAPABILITY_NUMBER_UP_LAYOUT, "GTK_PRINT_CAPABILITY_NUMBER_UP_LAYOUT", "number-up-layout" },
1384 { 0, NULL, NULL }
1385 };
1386
1387 etype = g_flags_register_static (I_("GtkPrintCapabilities"), const_static_values: values);
1388 }
1389
1390 return etype;
1391}
1392

source code of gtk/gtk/gtkprinter.c