4 * Copyright 2012 Samsung Electronics Co., Ltd
6 * Licensed under the Flora License, Version 1.1 (the "License");
7 * you may not use this file except in compliance with the License.
8 * You may obtain a copy of the License at
10 * http://floralicense.org/license/
12 * Unless required by applicable law or agreed to in writing, software
13 * distributed under the License is distributed on an "AS IS" BASIS,
14 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
15 * See the License for the specific language governing permissions and
16 * limitations under the License.
23 #include "pt_common.h"
26 #include "pt_optionmapping.h"
28 typedef ppd_choice_t *OPTIONCUBE[PT_QUALITY_MAX][PT_PAPER_MAX][PT_GRAYSCALE_MAX][PT_DUPLEX_MAX];
34 static int aPaperSize;
35 static ppd_option_t *paper_sizes;
36 static OPTIONCUBE *optionCube;
37 static char *aModelName;
39 int pt_get_print_option_default_papersize(void);
41 #include "pt_optionkeywords.c"
43 #ifdef PT_OPTIONCUBE_TEST_PRINT
44 static const char *papernames[] = {
51 static const char *qualitynames[] = {
58 static const char *colornames[] = {
66 static void parse_pagesize(ppd_option_t *opt)
70 for (index = paper_sizes->num_choices-1; index > 0; --index)
71 if (!strcasecmp(paper_sizes->choices[index].choice, paper_sizes->defchoice)) {
74 aPaperSize = pt_get_print_option_default_papersize();
78 static void parse_quality(ppd_option_t *opt)
81 for (i = opt->num_choices-1; i >= 0; i--) {
82 const pt_choice_keyword *lookingup = pt_quality_words;
83 while (lookingup->keyword != NULL) {
84 if (strcasecmp(lookingup->keyword, opt->choices[i].choice) == 0) {
85 optionCube[0][lookingup->quality][lookingup->papertype][lookingup->grayscale][lookingup->duplex] = &opt->choices[i];
86 PT_DEBUG("quality choice found: %s - q:%d p:%d c:%d", lookingup->keyword, lookingup->quality, lookingup->papertype, lookingup->grayscale);
92 if ((strcasecmp(opt->choices[i].choice, opt->defchoice) == 0) && (lookingup->keyword != NULL)) {
93 if (lookingup->quality != PT_QUALITY_ANY) {
94 aQuality = lookingup->quality;
96 if (lookingup->papertype != PT_PAPER_ANY) {
97 aPaper = lookingup->papertype;
105 static void parse_printquality(ppd_option_t *opt)
108 for (i = 0; i < opt->num_choices; i++) {
109 if (strcasecmp("BestPhoto", opt->choices[i].choice) == 0) {
110 optionCube[0][PT_QUALITY_HIGH][PT_PAPER_ANY][PT_GRAYSCALE_ANY][PT_DUPLEX_ANY] = &opt->choices[i];
111 } else if (strcasecmp("TextImage", opt->choices[i].choice) == 0) {
112 optionCube[0][PT_QUALITY_STANDARD][PT_PAPER_ANY][PT_GRAYSCALE_ANY][PT_DUPLEX_ANY] = &opt->choices[i];
113 } else if (strcasecmp("Draft", opt->choices[i].choice) == 0) {
114 optionCube[0][PT_QUALITY_DRAFT][PT_PAPER_ANY][PT_GRAYSCALE_ANY][PT_DUPLEX_ANY] = &opt->choices[i];
117 // setup the default value:
118 if (strcasecmp("BestPhoto", opt->defchoice) == 0) {
119 aQuality = PT_QUALITY_HIGH;
120 } else if (strcasecmp("Draft", opt->defchoice) == 0) {
121 aQuality = PT_QUALITY_DRAFT;
123 aQuality = PT_QUALITY_STANDARD;
128 static void parse_economode(ppd_option_t *opt)
131 for (i = 0; i < opt->num_choices; i++) {
132 if (strcasecmp("FALSE", opt->choices[i].choice) == 0) {
133 optionCube[0][PT_QUALITY_HIGH][PT_PAPER_ANY][PT_GRAYSCALE_ANY][PT_DUPLEX_ANY] = &opt->choices[i];
134 aQuality = PT_QUALITY_HIGH;
135 // } else if (strcasecmp("PrinterDefault", opt->choices[i].choice) == 0) {
136 // optionCube[0][PT_QUALITY_STANDARD][PT_PAPER_ANY][PT_GRAYSCALE_ANY] = &opt->choices[i];
137 } else if (strcasecmp("TRUE", opt->choices[i].choice) == 0) {
138 optionCube[0][PT_QUALITY_DRAFT][PT_PAPER_ANY][PT_GRAYSCALE_ANY][PT_DUPLEX_ANY] = &opt->choices[i];
141 // setup the default value:
142 if (strcasecmp("FALSE", opt->defchoice) == 0) {
143 aQuality = PT_QUALITY_HIGH;
145 aQuality = PT_QUALITY_DRAFT;
150 static void parse_hpeconomode(ppd_option_t *opt)
153 for (i = 0; i < opt->num_choices; i++) {
154 if (strcasecmp("False", opt->choices[i].choice) == 0) {
155 optionCube[0][PT_QUALITY_HIGH][PT_PAPER_ANY][PT_GRAYSCALE_ANY][PT_DUPLEX_ANY] = &opt->choices[i];
156 aQuality = PT_QUALITY_HIGH;
157 } else if (strcasecmp("PrinterDefault", opt->choices[i].choice) == 0) {
158 optionCube[0][PT_QUALITY_STANDARD][PT_PAPER_ANY][PT_GRAYSCALE_ANY][PT_DUPLEX_ANY] = &opt->choices[i];
159 } else if (strcasecmp("True", opt->choices[i].choice) == 0) {
160 optionCube[0][PT_QUALITY_DRAFT][PT_PAPER_ANY][PT_GRAYSCALE_ANY][PT_DUPLEX_ANY] = &opt->choices[i];
163 // setup the default value:
164 if (strcasecmp("False", opt->defchoice) == 0) {
165 aQuality = PT_QUALITY_HIGH;
166 } else if (strcasecmp("True", opt->defchoice) == 0) {
167 aQuality = PT_QUALITY_DRAFT;
169 aQuality = PT_QUALITY_STANDARD;
174 static void parse_hpeconomic(ppd_option_t *opt)
177 for (i = 0; i < opt->num_choices; i++) {
178 if (strcasecmp("FALSE", opt->choices[i].choice) == 0) {
179 optionCube[0][PT_QUALITY_HIGH][PT_PAPER_ANY][PT_GRAYSCALE_ANY][PT_DUPLEX_ANY] = &opt->choices[i];
180 aQuality = PT_QUALITY_HIGH;
181 // } else if (strcasecmp("PrinterDefault", opt->choices[i].choice) == 0) {
182 // optionCube[0][PT_QUALITY_STANDARD][PT_PAPER_ANY][PT_GRAYSCALE_ANY] = &opt->choices[i];
183 } else if (strcasecmp("TRUE", opt->choices[i].choice) == 0) {
184 optionCube[0][PT_QUALITY_DRAFT][PT_PAPER_ANY][PT_GRAYSCALE_ANY][PT_DUPLEX_ANY] = &opt->choices[i];
187 // setup the default value:
188 if (strcasecmp("FALSE", opt->defchoice) == 0) {
189 aQuality = PT_QUALITY_HIGH;
191 aQuality = PT_QUALITY_DRAFT;
196 static void parse_hpclean(ppd_option_t *opt)
199 for (i = 0; i < opt->num_choices; i++) {
200 if (strcasecmp("TRUE", opt->choices[i].choice) == 0) {
201 optionCube[0][PT_QUALITY_HIGH][PT_PAPER_ANY][PT_GRAYSCALE_ANY][PT_DUPLEX_ANY] = &opt->choices[i];
202 } else if (strcasecmp("FALSE", opt->choices[i].choice) == 0) {
203 optionCube[0][PT_QUALITY_STANDARD][PT_PAPER_ANY][PT_GRAYSCALE_ANY][PT_DUPLEX_ANY] = &opt->choices[i];
206 // setup the default value:
207 if (strcasecmp("TRUE", opt->defchoice) == 0) {
208 aQuality = PT_QUALITY_HIGH;
210 aQuality = PT_QUALITY_STANDARD;
215 static void parse_hpprintquality(ppd_option_t *opt)
218 for (i = 0; i < opt->num_choices; i++) {
219 if (strcasecmp("FastRes1200", opt->choices[i].choice) == 0 ||
220 strcasecmp("1200x1200dpi", opt->choices[i].choice) == 0) {
221 optionCube[0][PT_QUALITY_HIGH][PT_PAPER_ANY][PT_GRAYSCALE_ANY][PT_DUPLEX_ANY] = &opt->choices[i];
222 } else if (strcasecmp("600dpi", opt->choices[i].choice) == 0 ||
223 strcasecmp("600x600dpi", opt->choices[i].choice) == 0 ||
224 strcasecmp("ImageRet3600", opt->choices[i].choice) == 0) {
225 optionCube[0][PT_QUALITY_STANDARD][PT_PAPER_ANY][PT_GRAYSCALE_ANY][PT_DUPLEX_ANY] = &opt->choices[i];
228 // setup the default value:
229 if (strcasecmp("FastRes1200", opt->defchoice) == 0 || strcasecmp("1200x1200dpi", opt->defchoice)) {
230 aQuality = PT_QUALITY_HIGH;
232 aQuality = PT_QUALITY_STANDARD;
237 static void parse_hpoutputquality(ppd_option_t *opt)
240 for (i = 0; i < opt->num_choices; i++) {
241 if (strcasecmp("Best", opt->choices[i].choice) == 0) {
242 optionCube[0][PT_QUALITY_HIGH][PT_PAPER_ANY][PT_GRAYSCALE_ANY][PT_DUPLEX_ANY] = &opt->choices[i];
243 } else if (strcasecmp("Normal", opt->choices[i].choice) == 0) {
244 optionCube[0][PT_QUALITY_STANDARD][PT_PAPER_ANY][PT_GRAYSCALE_ANY][PT_DUPLEX_ANY] = &opt->choices[i];
245 } else if (strcasecmp("Fast", opt->choices[i].choice) == 0) {
246 optionCube[0][PT_QUALITY_DRAFT][PT_PAPER_ANY][PT_GRAYSCALE_ANY][PT_DUPLEX_ANY] = &opt->choices[i];
249 // setup the default value:
250 if (strcasecmp("Best", opt->defchoice) == 0) {
251 aQuality = PT_QUALITY_HIGH;
252 } else if (strcasecmp("Fast", opt->defchoice) == 0) {
253 aQuality = PT_QUALITY_DRAFT;
255 aQuality = PT_QUALITY_STANDARD;
260 static void parse_mediatype(ppd_option_t *opt)
263 aPaper = PT_PAPER_NORMAL;
264 for (i = opt->num_choices-1; i >= 0; i--) {
265 const pt_choice_keyword *lookingup = pt_mediatype_words;
266 while (lookingup->keyword != NULL) {
267 if (strcasecmp(lookingup->keyword, opt->choices[i].choice) == 0) {
268 optionCube[0][lookingup->quality][lookingup->papertype][lookingup->grayscale][lookingup->duplex] = &opt->choices[i];
269 PT_DEBUG("mediatype choice found: %s - q:%d p:%d c:%d", lookingup->keyword, lookingup->quality, lookingup->papertype, lookingup->grayscale);
275 if ((strcasecmp(opt->choices[i].choice, opt->defchoice) == 0) && (lookingup->keyword != NULL)) {
276 if (lookingup->papertype != PT_PAPER_ANY) {
277 aPaper = lookingup->papertype;
284 static void parse_resolution(ppd_option_t *opt)
287 int j = PT_RESOLUTION_HIGH;
288 ppd_choice_t *resolutions[PT_RESOLUTION_MAX];
290 for (i = 0; i < PT_RESOLUTION_MAX; i++) {
291 resolutions[i] = NULL;
294 for (i = 0; i < opt->num_choices; i++) {
295 const pt_resolution_keyword *lookingup = pt_resoultion_words;
296 while(lookingup->keyword != NULL) {
297 if(strcasecmp(lookingup->keyword, opt->choices[i].choice) == 0) {
298 resolutions[lookingup->weight] = &opt->choices[i];
306 for (i = PT_QUALITY_HIGH; i >= PT_QUALITY_DRAFT; i--) {
307 while(resolutions[j] == NULL && j >= 0) {
313 optionCube[0][i][PT_PAPER_ANY][PT_GRAYSCALE_ANY][PT_DUPLEX_ANY] = resolutions[j];
317 aQuality = PT_QUALITY_ANY;
318 for(i = PT_QUALITY_DRAFT; i < PT_QUALITY_ANY; i++) {
319 if (optionCube[0][i][PT_PAPER_ANY][PT_GRAYSCALE_ANY][PT_DUPLEX_ANY] != NULL) {
320 if ((strcasecmp(optionCube[0][i][PT_PAPER_ANY][PT_GRAYSCALE_ANY][PT_DUPLEX_ANY]->choice, opt->defchoice) == 0)) {
328 static void parse_ink(ppd_option_t *opt)
331 for (i = 0; i < opt->num_choices; i++) {
332 if (strcasecmp("COLOR", opt->choices[i].choice) == 0) {
333 optionCube[0][PT_QUALITY_ANY][PT_PAPER_ANY][PT_GRAYSCALE_COLOUR][PT_DUPLEX_ANY] = &opt->choices[i];
334 } else if (strcasecmp("MONO", opt->choices[i].choice) == 0) {
335 optionCube[0][PT_QUALITY_ANY][PT_PAPER_ANY][PT_GRAYSCALE_GRAYSCALE][PT_DUPLEX_ANY] = &opt->choices[i];
338 // setup the default value:
339 if (strcasecmp("COLOR", opt->defchoice) == 0) {
340 aColor = PT_GRAYSCALE_COLOUR;
342 aColor = PT_GRAYSCALE_GRAYSCALE;
347 static void parse_color(ppd_option_t *opt)
350 for (i = 0; i < opt->num_choices; i++) {
351 if (strcasecmp("Color", opt->choices[i].choice) == 0) {
352 optionCube[0][PT_QUALITY_ANY][PT_PAPER_ANY][PT_GRAYSCALE_COLOUR][PT_DUPLEX_ANY] = &opt->choices[i];
353 } else if (strcasecmp("Grayscale", opt->choices[i].choice) == 0) {
354 optionCube[0][PT_QUALITY_ANY][PT_PAPER_ANY][PT_GRAYSCALE_GRAYSCALE][PT_DUPLEX_ANY] = &opt->choices[i];
355 } else if (strcasecmp("Mono", opt->choices[i].choice) == 0) {
356 optionCube[0][PT_QUALITY_ANY][PT_PAPER_ANY][PT_GRAYSCALE_GRAYSCALE][PT_DUPLEX_ANY] = &opt->choices[i];
359 // setup the default value:
360 if (strcasecmp("Color", opt->defchoice) == 0) {
361 aColor = PT_GRAYSCALE_COLOUR;
363 aColor = PT_GRAYSCALE_GRAYSCALE;
368 static void parse_hpcoloroutput(ppd_option_t *opt)
371 for (i = 0; i < opt->num_choices; i++) {
372 if (strcasecmp("ColorPrint", opt->choices[i].choice) == 0) {
373 optionCube[0][PT_QUALITY_ANY][PT_PAPER_ANY][PT_GRAYSCALE_COLOUR][PT_DUPLEX_ANY] = &opt->choices[i];
374 } else if (strcasecmp("GrayscalePrint", opt->choices[i].choice) == 0) {
375 optionCube[0][PT_QUALITY_ANY][PT_PAPER_ANY][PT_GRAYSCALE_GRAYSCALE][PT_DUPLEX_ANY] = &opt->choices[i];
378 // setup the default value:
379 if (strcasecmp("ColorPrint", opt->defchoice) == 0) {
380 aColor = PT_GRAYSCALE_COLOUR;
382 aColor = PT_GRAYSCALE_GRAYSCALE;
387 static void parse_colormode(ppd_option_t *opt)
390 for (i = 0; i < opt->num_choices; i++) {
391 if (strcasecmp("TRUE", opt->choices[i].choice) == 0) {
392 optionCube[0][PT_QUALITY_ANY][PT_PAPER_ANY][PT_GRAYSCALE_COLOUR][PT_DUPLEX_ANY] = &opt->choices[i];
393 } else if (strcasecmp("FALSE", opt->choices[i].choice) == 0) {
394 optionCube[0][PT_QUALITY_ANY][PT_PAPER_ANY][PT_GRAYSCALE_GRAYSCALE][PT_DUPLEX_ANY] = &opt->choices[i];
397 // setup the default value:
398 if (strcasecmp("TRUE", opt->defchoice) == 0) {
399 aColor = PT_GRAYSCALE_COLOUR;
401 aColor = PT_GRAYSCALE_GRAYSCALE;
406 static void parse_colormodel(ppd_option_t *opt)
409 for (i = 0; i < opt->num_choices; i++) {
410 if (strcasecmp("BlackWhite", opt->choices[i].choice) == 0 ||
411 strcasecmp("CMYGray", opt->choices[i].choice) == 0 ||
412 strcasecmp("KGray", opt->choices[i].choice) == 0 ||
413 strcasecmp("Gray", opt->choices[i].choice) == 0 ||
414 strcasecmp("W", opt->choices[i].choice) == 0) {
415 if (optionCube[0][PT_QUALITY_ANY][PT_PAPER_ANY][PT_GRAYSCALE_GRAYSCALE][PT_DUPLEX_ANY] == NULL) {
416 optionCube[0][PT_QUALITY_ANY][PT_PAPER_ANY][PT_GRAYSCALE_GRAYSCALE][PT_DUPLEX_ANY] = &opt->choices[i];
418 if (strcasecmp(opt->choices[i].choice, opt->defchoice) == 0) {
419 aColor = PT_GRAYSCALE_GRAYSCALE;
421 } else if (strcasecmp("CMYK", opt->choices[i].choice) == 0 ||
422 strcasecmp("Color", opt->choices[i].choice) == 0 ||
423 strcasecmp("RGBA", opt->choices[i].choice) == 0 ||
424 strcasecmp("RGB", opt->choices[i].choice) == 0) {
425 if (optionCube[0][PT_QUALITY_ANY][PT_PAPER_ANY][PT_GRAYSCALE_COLOUR][PT_DUPLEX_ANY] == NULL) {
426 optionCube[0][PT_QUALITY_ANY][PT_PAPER_ANY][PT_GRAYSCALE_COLOUR][PT_DUPLEX_ANY] = &opt->choices[i];
428 if (strcasecmp(opt->choices[i].choice, opt->defchoice) == 0) {
429 aColor = PT_GRAYSCALE_COLOUR;
437 static void parse_hpcolorasgray(ppd_option_t *opt)
440 for (i = 0; i < opt->num_choices; i++) {
441 if (strcasecmp("False", opt->choices[i].choice) == 0 ||
442 strcasecmp("Off", opt->choices[i].choice) == 0 ) {
443 optionCube[0][PT_QUALITY_ANY][PT_PAPER_ANY][PT_GRAYSCALE_COLOUR][PT_DUPLEX_ANY] = &opt->choices[i];
444 } else if (strcasecmp("True", opt->choices[i].choice) == 0 ||
445 strcasecmp("HighQuality", opt->choices[i].choice) == 0 ||
446 strcasecmp("BlackInkOnly", opt->choices[i].choice) == 0) {
447 optionCube[0][PT_QUALITY_ANY][PT_PAPER_ANY][PT_GRAYSCALE_GRAYSCALE][PT_DUPLEX_ANY] = &opt->choices[i];
450 // setup the default value:
451 if (strcasecmp("False", opt->defchoice) == 0 || strcasecmp("Off", opt->defchoice) == 0) {
452 aColor = PT_GRAYSCALE_COLOUR;
454 aColor = PT_GRAYSCALE_GRAYSCALE;
459 static void parse_hpprintingrayscale(ppd_option_t *opt)
462 // XXX - It's a way to get gray print by black ink or sum of all inks.
463 for (i = 0; i < opt->num_choices; i++) {
464 if (strcasecmp("GrayscalePrint", opt->choices[i].choice) == 0) {
465 optionCube[0][PT_QUALITY_ANY][PT_PAPER_ANY][PT_GRAYSCALE_GRAYSCALE][PT_DUPLEX_ANY] = &opt->choices[i];
466 if (strcasecmp(opt->choices[i].choice, opt->defchoice) == 0) {
467 aColor = PT_GRAYSCALE_GRAYSCALE;
469 } else if (strcasecmp("FullSetOfInks", opt->choices[i].choice) == 0) {
470 // FIXME - Currently GrayscalePrint only used
471 //optionCube[0][PT_QUALITY_ANY][PT_PAPER_ANY][PT_GRAYSCALE_GRAYSCALE] = &opt->choices[i];
478 static void parse_cmandresolution(ppd_option_t *opt)
481 for (i = 0; i < opt->num_choices; i++) {
482 const pt_choice_keyword *lookingup = pt_cmandresolution_words;
483 while (lookingup->keyword != NULL) {
484 if (strcasecmp(lookingup->keyword, opt->choices[i].choice) == 0) {
485 optionCube[0][lookingup->quality][lookingup->papertype][lookingup->grayscale][lookingup->duplex] = &opt->choices[i];
491 if ((strcasecmp(opt->choices[i].choice, opt->defchoice) == 0) && (lookingup->keyword != NULL)) {
492 aQuality = lookingup->quality;
493 aColor = lookingup->grayscale;
499 static void parse_outputmode(ppd_option_t *opt)
502 for (i=0; i < opt->num_choices; i++) {
503 const pt_choice_keyword *lookingup = pt_outputmode_words;
504 while (lookingup->keyword != NULL) {
505 if (strcasecmp(lookingup->keyword, opt->choices[i].choice) == 0) {
506 optionCube[0][lookingup->quality][lookingup->papertype][lookingup->grayscale][lookingup->duplex] = &opt->choices[i];
512 if ((strcasecmp(opt->choices[i].choice, opt->defchoice) == 0) && (lookingup->keyword != NULL)) {
513 aQuality = (lookingup->quality != PT_QUALITY_ANY) ? lookingup->quality : aQuality;
514 aPaper = (lookingup->papertype != PT_PAPER_ANY) ? lookingup->papertype : aPaper;
515 aColor = (lookingup->grayscale != PT_GRAYSCALE_ANY) ? lookingup->grayscale : aColor;
520 static void parse_duplex(ppd_option_t *opt)
523 for(i=0; i < opt->num_choices; i++) {
524 const pt_choice_keyword *lookingup = pt_duplex_words;
525 while (lookingup->keyword != NULL) {
526 if (strcasecmp(lookingup->keyword, opt->choices[i].choice) == 0) {
527 optionCube[0][lookingup->quality][lookingup->papertype][lookingup->grayscale][lookingup->duplex] = &opt->choices[i];
533 if ((strcasecmp(opt->choices[i].choice, opt->defchoice) == 0) && lookingup->keyword != NULL) {
534 aDuplex = lookingup->duplex;
539 /* KA: database with options and apropriate function */
540 static KeyActions KA[] = {
588 parse_hpprintquality,
593 parse_hpoutputquality,
623 parse_cmandresolution,
632 "HPPrintInGrayscale",
633 parse_hpprintingrayscale,
645 static ppd_choice_t *quality_exists(int q)
647 ppd_choice_t *choi = NULL;
649 if (!optionCube[aPaperSize][q][aPaper][aColor][aDuplex]) {
650 choi = optionCube[aPaperSize][q][PT_PAPER_ANY][PT_GRAYSCALE_ANY][PT_DUPLEX_ANY];
651 // choi == 1 is a special case: option doesn't exist in ppd file,
652 // but it is allowed as a printer default setting, for ex.:
653 // Standard quality as the only quality, a printer supports
654 if (!choi && choi != (ppd_choice_t *)1) {
655 choi = optionCube[aPaperSize][q][aPaper][PT_GRAYSCALE_ANY][PT_DUPLEX_ANY];
657 if (!choi && choi != (ppd_choice_t *)1) {
658 choi = optionCube[aPaperSize][q][PT_PAPER_ANY][aColor][PT_DUPLEX_ANY];
664 static ppd_choice_t *paper_exists(int p)
666 ppd_choice_t *choi = NULL;
668 if (!optionCube[aPaperSize][aQuality][p][aColor][aDuplex]) {
669 choi = optionCube[aPaperSize][PT_QUALITY_ANY][p][PT_GRAYSCALE_ANY][PT_DUPLEX_ANY];
670 // choi == 1 is a special case: option doesn't exist in ppd file,
671 // but it is allowed as printer default setting, for ex.:
672 // Plain paper as the only and default paper type
673 if (!choi && choi != (ppd_choice_t *)1) {
674 choi = optionCube[aPaperSize][aQuality][p][PT_GRAYSCALE_ANY][PT_DUPLEX_ANY];
676 if (!choi && choi != (ppd_choice_t *)1) {
677 choi = optionCube[aPaperSize][PT_QUALITY_ANY][p][aColor][PT_DUPLEX_ANY];
683 static ppd_choice_t *color_exists(int c)
685 ppd_choice_t *choi = NULL;
687 if (!optionCube[aPaperSize][aQuality][aPaper][c][aDuplex]) {
688 choi = optionCube[aPaperSize][PT_QUALITY_ANY][PT_PAPER_ANY][c][PT_DUPLEX_ANY];
689 // choi == 1 is a special case: option doesn't exist in ppd file,
690 // but it is allowed as printer default setting, for ex.:
691 // Grayscale for black & white printer.
692 if (!choi && choi != (ppd_choice_t *)1) {
693 choi = optionCube[aPaperSize][aQuality][PT_PAPER_ANY][c][PT_DUPLEX_ANY];
695 if (!choi && choi != (ppd_choice_t *)1) {
696 choi = optionCube[aPaperSize][PT_QUALITY_ANY][aPaper][c][PT_DUPLEX_ANY];
702 static ppd_choice_t *duplex_exists(int d)
704 ppd_choice_t *choi = NULL;
705 if (!optionCube[aPaperSize][aQuality][aPaper][aColor][d]) {
706 choi = optionCube[aPaperSize][PT_QUALITY_ANY][PT_PAPER_ANY][PT_GRAYSCALE_ANY][d];
711 static void reset_option_cube(int num_sizes)
713 if (optionCube != NULL) {
716 optionCube = calloc(num_sizes, sizeof(OPTIONCUBE));
717 // set current settings to their initial values
718 aColor = PT_GRAYSCALE_ANY;
719 aQuality = PT_QUALITY_ANY;
720 aPaper = PT_PAPER_ANY;
721 aDuplex = PT_DUPLEX_ANY;
724 static void check_defaults(ppd_file_t *ppd)
726 if (aColor == PT_GRAYSCALE_ANY) {
727 PT_DEBUG("Color option not found!");
728 ppd_attr_t *at = ppdFindAttr(ppd, "ColorDevice", NULL);
730 if (strcasecmp(at->text, "True") == 0) {
731 aColor = PT_GRAYSCALE_COLOUR;
733 aColor = PT_GRAYSCALE_GRAYSCALE;
735 optionCube[0][PT_QUALITY_ANY][PT_PAPER_ANY][aColor][PT_DUPLEX_ANY] = (ppd_choice_t *)1;
737 PT_DEBUG("Attribute ColorDevice not found! Check ppd file!");
740 if (aQuality == PT_QUALITY_ANY) {
741 PT_DEBUG("Qualtiy option not found!");
742 optionCube[0][PT_QUALITY_STANDARD][PT_PAPER_ANY][PT_GRAYSCALE_ANY][PT_DUPLEX_ANY] = (ppd_choice_t *)1;
743 aQuality = PT_QUALITY_STANDARD;
745 if (aPaper == PT_PAPER_ANY) {
746 PT_DEBUG("MediaType option not found!");
747 optionCube[0][PT_QUALITY_ANY][PT_PAPER_NORMAL][PT_GRAYSCALE_ANY][PT_DUPLEX_ANY] = (ppd_choice_t *)1;
748 aPaper = PT_PAPER_NORMAL;
750 if (aDuplex == PT_DUPLEX_ANY) {
751 PT_DEBUG("Duplex option not found!");
752 optionCube[0][PT_QUALITY_ANY][PT_PAPER_ANY][PT_GRAYSCALE_ANY][PT_DUPLEX_OFF] = (ppd_choice_t *)1;
753 aDuplex = PT_DUPLEX_OFF;
757 static int mark_choice(ppd_file_t *ppd, ppd_choice_t* ch) {
758 if (ch && ch != (ppd_choice_t*) 1) {
760 return ppdConflicts(ppd);
765 static void unmark_choice(ppd_choice_t* ch) {
766 if (ch && ch != (ppd_choice_t*) 1) {
771 static void check_constraints(ppd_file_t *ppd, int papersize)
773 int sPaperSize, sQuality, sPaper, sColor, sDuplex;
775 ppd_choice_t* qualityCh;
776 ppd_choice_t* paperCh;
777 ppd_choice_t* colorCh;
779 // saving default values
780 sPaperSize = aPaperSize;
785 aPaperSize = papersize;
786 ppdMarkDefaults(ppd);
787 ppdMarkOption(ppd, "PageSize", paper_sizes->choices[papersize].choice);
788 for (aQuality=0; aQuality<PT_QUALITY_ANY; aQuality++) {
789 qualityCh = pt_selected_choice(PT_OPTION_ID_QUALITY, PT_ORIENTATION_PORTRAIT);
790 mark_choice(ppd, qualityCh);
791 for (aPaper=0; aPaper<PT_PAPER_ANY; aPaper++) {
792 paperCh = pt_selected_choice(PT_OPTION_ID_PAPER, PT_ORIENTATION_PORTRAIT);
793 mark_choice(ppd, paperCh);
794 for (aColor=0; aColor<PT_GRAYSCALE_ANY; aColor++) {
795 colorCh = pt_selected_choice(PT_OPTION_ID_GRAYSCALE, PT_ORIENTATION_PORTRAIT);
796 mark_choice(ppd, colorCh);
797 for(aDuplex=0; aDuplex<PT_DUPLEX_ANY; aDuplex++) {
798 ch = duplex_exists(aDuplex);
799 if(ch && ch != (ppd_choice_t*)1) {
800 if (ppdMarkOption(ppd, ch->option->keyword, ch->choice) > 0) {
801 optionCube[papersize][aQuality][aPaper][aColor][aDuplex] = (ppd_choice_t *) -1;
804 } else if(ppdConflicts(ppd) > 0) {
805 optionCube[papersize][aQuality][aPaper][aColor][aDuplex] = (ppd_choice_t *) -1;
808 unmark_choice(colorCh);
810 unmark_choice(paperCh);
812 unmark_choice(qualityCh);
814 // restoring default values
819 aPaperSize = sPaperSize;
822 #ifdef PT_OPTIONCUBE_TEST_PRINT
824 static void testprint(int paper)
831 PT_DEBUG(" Gray Color Any for PaperSize: %s", paper_sizes->choices[paper].choice);
832 for (i=0; i<=PT_QUALITY_ANY; i++) {
833 PT_DEBUG("----------------- %s ------------------", qualitynames[i]);
834 for (j=0; j<=PT_PAPER_ANY; j++) {
835 dbgPrintPtr = dbgPrint;
836 dbgPrintPtr += sprintf(dbgPrintPtr, "%s", papernames[j]);
837 for (k=0; k<=PT_GRAYSCALE_ANY; k++) {
838 choi = optionCube[paper][i][j][k][PT_DUPLEX_ANY];
839 if (choi == (ppd_choice_t *)(-1)) {
840 dbgPrintPtr += sprintf(dbgPrintPtr, " disabled ");
841 } else if (choi == (ppd_choice_t *)1) {
842 dbgPrintPtr += sprintf(dbgPrintPtr, " enabled ");
844 dbgPrintPtr += sprintf(dbgPrintPtr, " %s ", choi->choice);
846 dbgPrintPtr += sprintf(dbgPrintPtr, " <n/a> ");
849 PT_DEBUG("%s", dbgPrint);
855 static bool pt_validate_settings(int s, int q, int p, int c, int d)
857 if (s < 0 || s >= paper_sizes->num_choices) {
860 if (q < PT_QUALITY_DRAFT || q > PT_QUALITY_HIGH) {
863 if (p < PT_PAPER_NORMAL || p > PT_PAPER_PHOTO) {
866 if (c < PT_GRAYSCALE_GRAYSCALE || c > PT_GRAYSCALE_COLOUR) {
869 if (d < PT_DUPLEX_OFF || d > PT_DUPLEX_TUMBLE) {
875 static void pt_try_settings(int s, int q, int p, int c, int d)
877 int sPaperSize = aPaperSize;
878 int sQuality = aQuality;
881 int sDuplex = aDuplex;
883 if(pt_validate_settings(s, q, p, c, d)) {
884 if (!pt_is_enabled(PT_OPTION_ID_QUALITY, q) || !pt_is_enabled(PT_OPTION_ID_PAPER, p) ||
885 !pt_is_enabled(PT_OPTION_ID_GRAYSCALE, c) || !pt_is_enabled(PT_OPTION_ID_DUPLEX, d)) {
886 aPaperSize = sPaperSize;
901 void pt_load_user_choice(void) {
903 char buf[255] = {0,};
910 char *null_check = NULL;
912 stream = fopen(PT_USER_OPTION_CONFIG_FILE,"r");
914 PT_DEBUG("Can't open settings file");
917 while(fgets(buf, sizeof(buf), stream) != NULL) {
918 null_check = strchr(buf, '\n');
923 gchar **tokens = g_strsplit((gchar *)buf, ",", 0);
924 if (g_strv_length(tokens) != 6) {
929 if (!strcasecmp(tokens[0], aModelName)) {
935 pt_try_settings(s, q, p, c, d);
944 int pt_set_choice(int op, int ch)
948 case PT_OPTION_ID_QUALITY:
949 if (quality_exists(ch)) {
954 case PT_OPTION_ID_PAPER:
955 if (paper_exists(ch)) {
960 case PT_OPTION_ID_GRAYSCALE:
961 if (color_exists(ch)) {
966 case PT_OPTION_ID_PAPERSIZE:
967 if (pt_is_enabled(op, ch)) {
972 case PT_OPTION_ID_DUPLEX:
973 if (duplex_exists(ch)) {
983 int pt_get_selected(int op)
987 case PT_OPTION_ID_QUALITY:
990 case PT_OPTION_ID_PAPER:
993 case PT_OPTION_ID_GRAYSCALE:
996 case PT_OPTION_ID_PAPERSIZE:
999 case PT_OPTION_ID_DUPLEX:
1008 int pt_is_enabled(int op, int ch)
1012 case PT_OPTION_ID_QUALITY:
1013 if (!quality_exists(ch)) {
1017 case PT_OPTION_ID_PAPER:
1018 if (!paper_exists(ch)) {
1022 case PT_OPTION_ID_GRAYSCALE:
1023 if (!color_exists(ch)) {
1027 case PT_OPTION_ID_PAPERSIZE:
1028 if (optionCube[ch][aQuality][aPaper][aColor][aDuplex] == (ppd_choice_t *)(-1)) {
1032 case PT_OPTION_ID_DUPLEX:
1033 if (!duplex_exists(ch)) {
1043 int pt_get_selected_paper_size_pts(pt_pagesize_t *s)
1046 ppd_size_t *size = pt_utils_paper_size_pts(paper_sizes->choices[aPaperSize].choice);
1049 s->y = size->length;
1050 strcpy(s->name, size->name);
1051 PT_DEBUG("%s pagesize selected (%f x %f)", s->name, s->x, s->y);
1053 PT_DEBUG("No pagesize selected!");
1059 char *pt_get_print_option_papersize(int papersize_num)
1061 PT_RETV_IF(paper_sizes == NULL, NULL, "paper_sizes is NULL");
1062 return paper_sizes->choices[papersize_num].text;
1065 char *pt_get_print_option_papersize_cmd(int papersize_num)
1067 PT_RETV_IF(paper_sizes == NULL, NULL, "paper_sizes is NULL");
1068 return paper_sizes->choices[papersize_num].choice;
1071 int pt_get_print_option_papersize_num(void)
1073 PT_RETV_IF(paper_sizes == NULL, 0, "paper_sizes is NULL");
1074 return paper_sizes->num_choices;
1077 int pt_get_print_option_default_papersize(void)
1079 PT_RETV_IF(paper_sizes == NULL, 0, "paper_sizes is NULL");
1081 for (i=0; i< paper_sizes->num_choices; i++)
1082 if (!strcasecmp(paper_sizes->choices[i].choice, paper_sizes->defchoice)) {
1088 /* parse_options: search ppd options and call certain function */
1089 void pt_parse_options(ppd_file_t *ppd)
1092 ppd_option_t *opt = NULL;
1093 ppd_attr_t *at = NULL;
1094 KeyActions *ka = NULL;
1096 opt = ppdFindOption(ppd, "PageSize");
1098 parse_pagesize(opt);
1101 at = ppdFindAttr(ppd, "ModelName", NULL);
1103 aModelName = at->value;
1104 PT_DEBUG("ModelName found, value: %s; spec: %s; text: %s", at->value, at->spec, at->text);
1106 PT_DEBUG("ModelName not found");
1109 reset_option_cube(paper_sizes->num_choices);
1111 //find all options and call necessary function
1112 for (i = 0, ka = &KA[i]; ka[i].key != NULL; i++) {
1113 opt = ppdFindOption(ppd, ka[i].key);
1118 // Check, if all options were set otherwise set them "by force"
1119 check_defaults(ppd);
1120 // copy found options and check UI constraints for all paper sizes
1121 for (i=1; i<paper_sizes->num_choices; i++) {
1122 PT_DEBUG("Copying option cubes %d", i);
1123 memcpy(optionCube[i], optionCube[0], sizeof(OPTIONCUBE));
1124 PT_DEBUG("Checking UI constraints");
1125 check_constraints(ppd, i);
1126 #ifdef PT_OPTIONCUBE_TEST_PRINT
1131 // check UI Constraints for paper size No 0 too.
1132 check_constraints(ppd, 0);
1133 pt_load_user_choice();
1137 ppd_choice_t *pt_selected_choice(int op, pt_orientation_e p)
1139 ppd_choice_t *choi = NULL;
1141 case PT_OPTION_ID_QUALITY:
1142 choi = quality_exists(aQuality);
1144 case PT_OPTION_ID_PAPER:
1145 choi = paper_exists(aPaper);
1147 case PT_OPTION_ID_GRAYSCALE:
1148 choi = color_exists(aColor);
1150 case PT_OPTION_ID_PAPERSIZE:
1151 choi = &paper_sizes->choices[aPaperSize];
1153 case PT_OPTION_ID_DUPLEX:
1154 choi = duplex_exists(aDuplex);
1155 if(aDuplex != PT_DUPLEX_OFF) {
1156 choi = (p == PT_ORIENTATION_PORTRAIT) ? duplex_exists(PT_DUPLEX_NO_TUMBLE) : duplex_exists(PT_DUPLEX_TUMBLE);
1162 if(choi == (ppd_choice_t*)1) {
1163 // Special case. Set by force, no ppd option. Use printer default.
1164 // No need to send smth. to printer.
1170 void pt_save_user_choice(void) {
1177 stream = fopen(PT_USER_OPTION_CONFIG_FILE,"r+");
1178 if(stream == NULL) {
1179 //may be file doesn't exist, try to create it...
1180 stream = fopen(PT_USER_OPTION_CONFIG_FILE,"w");
1181 if(stream == NULL) {
1182 PT_DEBUG("Can't create settings file");
1186 fgetpos(stream, &position);
1187 while(fgets(buf, sizeof(buf)-1, stream) != NULL) {
1188 args = strchr(buf, ',');
1193 if(!strcasecmp(buf, aModelName)) {
1194 ret = fsetpos(stream, &position);
1199 fprintf(stream, "%s,%03d,%03d,%03d,%03d,%03d\n", aModelName, aPaperSize, aQuality, aPaper, aColor, aDuplex);
1203 fgetpos(stream, &position);
1205 ret = fsetpos(stream, &position);
1210 fprintf(stream, "%s,%03d,%03d,%03d,%03d,%03d\n", aModelName, aPaperSize, aQuality, aPaper, aColor, aDuplex);