00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033 #include "plDevs.h"
00034
00035 #ifdef PLD_pdf
00036
00037 #include <stdarg.h>
00038 #include <math.h>
00039 #include <setjmp.h>
00040
00041 #include "hpdf.h"
00042
00043
00044 #define DEBUG
00045 #define NEED_PLDEBUG
00046 #include "plplotP.h"
00047 #include "drivers.h"
00048 #include "plunicode-type1.h"
00049 #include "plfci-type1.h"
00050
00051
00052 #ifndef WIN32
00053 #define stricmp strcasecmp
00054 #define strnicmp strncasecmp
00055 #endif
00056
00057
00058
00059
00060
00061
00062
00063
00064 #define CANVAS_WIDTH ( 50.0 )
00065 #define CANVAS_HEIGHT ( 37.5 )
00066 #define DEVICE_PIXELS_PER_INCH ( 72 )
00067
00068
00069 #define MM_PER_INCH ( 25.4 )
00070
00071
00072 #define DEVICE_PIXELS_PER_MM ( DEVICE_PIXELS_PER_INCH / MM_PER_INCH )
00073
00074
00075 #define MAX_STRING_LEN 1000
00076
00077
00078 typedef struct
00079 {
00080 HPDF_Doc pdf;
00081 HPDF_Page page;
00082 HPDF_PageSizes pageSize;
00083 FILE *pdfFile;
00084 PLFLT scalex, scaley;
00085
00086
00087 HPDF_Font m_font;
00088 int nlookup, if_symbol_font;
00089 const Unicode_to_Type1_table *lookup;
00090 HPDF_REAL fontSize;
00091 HPDF_REAL fontScale;
00092 HPDF_REAL textWidth, textHeight;
00093 HPDF_REAL yOffset;
00094 HPDF_REAL textRed, textGreen, textBlue;
00095 } pdfdev;
00096
00097
00098 PLDLLIMPEXP_DRIVER const char* plD_DEVICE_INFO_pdf = "pdf:Portable Document Format PDF:1:pdf:58:pdf\n";
00099 static jmp_buf env;
00100
00101
00102
00103
00104
00105
00106 static short desired_offset( short, double );
00107 static void poly_line( PLStream *pls, short *xa, short *ya, PLINT npts, short fill );
00108
00109
00110 static void process_string( PLStream *, EscText * );
00111
00112
00113 void plD_dispatch_init_pdf( PLDispatchTable *pdt );
00114 void plD_init_pdf( PLStream * );
00115 void plD_line_pdf( PLStream *, short, short, short, short );
00116 void plD_polyline_pdf( PLStream *, short *, short *, PLINT );
00117 void plD_eop_pdf( PLStream * );
00118 void plD_bop_pdf( PLStream * );
00119 void plD_tidy_pdf( PLStream * );
00120 void plD_state_pdf( PLStream *, PLINT );
00121 void plD_esc_pdf( PLStream *, PLINT, void * );
00122
00123
00124
00125
00126
00127
00128
00129 #ifdef HPDF_DLL
00130 void __stdcall
00131 #else
00132 void
00133 #endif
00134 error_handler( HPDF_STATUS error_no, HPDF_STATUS detail_no, void *user_data )
00135 {
00136
00137 printf( "ERROR: error_no=%04X, detail_no=%d\n", (unsigned int) error_no, (int) detail_no );
00138 longjmp( env, 1 );
00139 }
00140
00141
00142
00143
00144
00145
00146
00147 void plD_dispatch_init_pdf( PLDispatchTable *pdt )
00148 {
00149 #ifndef ENABLE_DYNDRIVERS
00150 pdt->pl_MenuStr = "Portable Document Format PDF";
00151 pdt->pl_DevName = "pdf";
00152 #endif
00153 pdt->pl_type = plDevType_FileOriented;
00154 pdt->pl_seq = 58;
00155 pdt->pl_init = (plD_init_fp) plD_init_pdf;
00156 pdt->pl_line = (plD_line_fp) plD_line_pdf;
00157 pdt->pl_polyline = (plD_polyline_fp) plD_polyline_pdf;
00158 pdt->pl_eop = (plD_eop_fp) plD_eop_pdf;
00159 pdt->pl_bop = (plD_bop_fp) plD_bop_pdf;
00160 pdt->pl_tidy = (plD_tidy_fp) plD_tidy_pdf;
00161 pdt->pl_state = (plD_state_fp) plD_state_pdf;
00162 pdt->pl_esc = (plD_esc_fp) plD_esc_pdf;
00163 }
00164
00165
00166
00167 static PLINT text = 1;
00168 static PLINT compress = 1;
00169 static PLINT hrshsym = 1;
00170 static PLINT color = 1;
00171 static char * pageSize = NULL;
00172
00173 DrvOpt pdf_options[] = {
00174 { "text", DRV_INT, &text, "Use own text routines (text=0|1)" },
00175 { "color", DRV_INT, &color, "Use color (color=0|1)" },
00176 { "compress", DRV_INT, &compress, "Compress pdf output (compress=0|1)" },
00177 { "hrshsym", DRV_INT, &hrshsym, "Use Hershey symbol set (hrshsym=0|1)" },
00178 { "pagesize", DRV_STR, &pageSize, "Set page size (pagesize=A4|letter|A3|A5)" },
00179 { NULL, DRV_INT, NULL, NULL }
00180 };
00181
00182
00183
00184
00185
00186
00187
00188 void plD_init_pdf( PLStream *pls )
00189 {
00190 pdfdev* dev;
00191
00192
00193 dev = (pdfdev *) calloc( 1, sizeof ( pdfdev ) );
00194 if ( dev == NULL )
00195 plexit( "Insufficient memory\n" );
00196 pls->dev = (void *) dev;
00197
00198
00199 plParseDrvOpts( pdf_options );
00200
00201 pls->termin = 0;
00202 if ( color )
00203 pls->color = 1;
00204 else
00205 pls->color = 0;
00206 pls->width = 1;
00207 pls->bytecnt = 0;
00208
00209 if ( text )
00210 {
00211 pls->dev_text = 1;
00212 pls->dev_unicode = 1;
00213 if ( hrshsym )
00214 pls->dev_hrshsym = 1;
00215 }
00216
00217 pls->page = 0;
00218 pls->dev_fill0 = 1;
00219 pls->dev_fill1 = 0;
00220
00221 pls->graphx = GRAPHICS_MODE;
00222
00223 if ( !pls->colorset )
00224 pls->color = 1;
00225
00226
00227
00228 plspage( DEVICE_PIXELS_PER_INCH, DEVICE_PIXELS_PER_INCH,
00229 (PLINT) ( CANVAS_WIDTH * DEVICE_PIXELS_PER_INCH ), (PLINT) ( CANVAS_HEIGHT * DEVICE_PIXELS_PER_INCH ), 0, 0 );
00230
00231
00232 plP_setphy( 0, (PLINT) ( CANVAS_WIDTH * DEVICE_PIXELS_PER_INCH ),
00233 0, (PLINT) ( CANVAS_HEIGHT * DEVICE_PIXELS_PER_INCH ) );
00234
00235
00236 plP_setpxl( (PLFLT) DEVICE_PIXELS_PER_MM, (PLFLT) DEVICE_PIXELS_PER_MM );
00237
00238
00239
00240
00241
00242
00243
00244 if ( pls->portrait )
00245 {
00246 plsdiori( (PLFLT) ( 4 - ORIENTATION ) );
00247 pls->freeaspect = 1;
00248 }
00249
00250
00251 plFamInit( pls );
00252
00253
00254 plOpenFile( pls );
00255 dev->pdfFile = pls->OutFile;
00256
00257 dev->pdf = HPDF_New( error_handler, NULL );
00258 if ( !dev->pdf )
00259 plexit( "ERROR: cannot create pdf object.\n" );
00260
00261 if ( compress )
00262 HPDF_SetCompressionMode( dev->pdf, HPDF_COMP_ALL );
00263
00264
00265 dev->pageSize = HPDF_PAGE_SIZE_EOF;
00266 if ( pageSize == NULL )
00267 dev->pageSize = HPDF_PAGE_SIZE_A4;
00268 else if ( !stricmp( pageSize, "letter" ) )
00269 dev->pageSize = HPDF_PAGE_SIZE_LETTER;
00270 else if ( !stricmp( pageSize, "A3" ) )
00271 dev->pageSize = HPDF_PAGE_SIZE_A3;
00272 else if ( !stricmp( pageSize, "A4" ) )
00273 dev->pageSize = HPDF_PAGE_SIZE_A4;
00274 else if ( !stricmp( pageSize, "A5" ) )
00275 dev->pageSize = HPDF_PAGE_SIZE_A5;
00276
00277 if ( dev->pageSize == HPDF_PAGE_SIZE_EOF )
00278 plexit( "ERROR: Unknown page size. Allowed strings are: letter, A3, A4, A5.\n" );
00279
00280 if ( setjmp( env ) )
00281 {
00282
00283
00284
00285
00286
00287 fprintf( stderr, "ERROR in haru library\n" );
00288 exit( 1 );
00289 }
00290 }
00291
00292
00293
00294
00295
00296
00297 void plD_bop_pdf( PLStream *pls )
00298 {
00299 pdfdev * dev = (pdfdev *) pls->dev;
00300 HPDF_REAL width, height;
00301
00302 pls->page++;
00303
00304
00305 dev->page = HPDF_AddPage( dev->pdf );
00306 if ( pls->portrait )
00307 HPDF_Page_SetSize( dev->page, dev->pageSize, HPDF_PAGE_PORTRAIT );
00308 else
00309 HPDF_Page_SetSize( dev->page, dev->pageSize, HPDF_PAGE_LANDSCAPE );
00310
00311
00312 width = HPDF_Page_GetWidth( dev->page );
00313 height = HPDF_Page_GetHeight( dev->page );
00314 dev->scalex = (PLFLT) ( width / ( CANVAS_WIDTH * DEVICE_PIXELS_PER_INCH ) );
00315 dev->scaley = (PLFLT) ( height / ( CANVAS_HEIGHT * DEVICE_PIXELS_PER_INCH ) );
00316 HPDF_Page_Concat( dev->page, (HPDF_REAL) ( dev->scalex ), 0, 0, (HPDF_REAL) ( dev->scaley ), 0, 0 );
00317
00318
00319
00320 HPDF_Page_SetRGBFill( dev->page, (HPDF_REAL) ( pls->cmap0[0].r / 255.0 ),
00321 (HPDF_REAL) ( pls->cmap0[0].g / 255.0 ), (HPDF_REAL) ( pls->cmap0[0].b / 255.0 ) );
00322 width /= (HPDF_REAL) ( dev->scalex );
00323 height /= (HPDF_REAL) ( dev->scaley );
00324 HPDF_Page_MoveTo( dev->page, (HPDF_REAL) 0.0, (HPDF_REAL) 0.0 );
00325 HPDF_Page_LineTo( dev->page, width, (HPDF_REAL) 0.0 );
00326 HPDF_Page_LineTo( dev->page, width, (HPDF_REAL) height );
00327 HPDF_Page_LineTo( dev->page, 0.0, (HPDF_REAL) height );
00328 HPDF_Page_Fill( dev->page );
00329 }
00330
00331
00332
00333
00334
00335
00336
00337 void plD_line_pdf( PLStream *pls, short x1a, short y1a, short x2a, short y2a )
00338 {
00339 short xa[2], ya[2];
00340
00341 xa[0] = x1a; xa[1] = x2a;
00342 ya[0] = y1a; ya[1] = y2a;
00343
00344 poly_line( pls, xa, ya, 2, 0 );
00345 }
00346
00347
00348
00349
00350
00351
00352
00353 void plD_polyline_pdf( PLStream *pls, short *xa, short *ya, PLINT npts )
00354 {
00355 poly_line( pls, xa, ya, npts, 0 );
00356 }
00357
00358
00359
00360
00361
00362
00363
00364 void plD_eop_pdf( PLStream *pls )
00365 {
00366
00367 }
00368
00369
00370
00371
00372
00373
00374
00375 void plD_tidy_pdf( PLStream *pls )
00376 {
00377 pdfdev* dev = (pdfdev *) pls->dev;
00378
00379
00380 HPDF_SaveToStream( dev->pdf );
00381
00382
00383 HPDF_ResetStream( dev->pdf );
00384
00385
00386 for (;; )
00387 {
00388 HPDF_BYTE buf[4096];
00389 HPDF_UINT32 size = 4096;
00390 HPDF_STATUS ret = HPDF_ReadFromStream( dev->pdf, buf, &size );
00391
00392 if ( size == 0 )
00393 break;
00394
00395 if ( fwrite( buf, size, 1, dev->pdfFile ) != 1 )
00396 plexit( "ERROR: Cannot write to file!" );
00397 }
00398
00399 plCloseFile( pls );
00400
00401
00402 HPDF_Free( dev->pdf );
00403 }
00404
00405
00406
00407
00408
00409
00410
00411
00412
00413
00414 void plD_state_pdf( PLStream *pls, PLINT op )
00415 {
00416
00417 }
00418
00419
00420
00421
00422
00423
00424
00425 void plD_esc_pdf( PLStream *pls, PLINT op, void *ptr )
00426 {
00427 switch ( op )
00428 {
00429 case PLESC_FILL:
00430 poly_line( pls, pls->dev_x, pls->dev_y, pls->dev_npts, 1 );
00431 break;
00432 case PLESC_HAS_TEXT:
00433 process_string( pls, (EscText *) ptr );
00434 break;
00435 }
00436 }
00437
00438
00439
00440
00441
00442
00443
00444 void poly_line( PLStream *pls, short *xa, short *ya, PLINT npts, short fill )
00445 {
00446 pdfdev* dev = (pdfdev *) pls->dev;
00447 PLINT i;
00448
00449 HPDF_Page_SetLineWidth( dev->page, (HPDF_REAL) ( pls->width ) );
00450 HPDF_Page_SetLineCap( dev->page, HPDF_ROUND_END );
00451 HPDF_Page_SetLineJoin( dev->page, HPDF_ROUND_JOIN );
00452 HPDF_Page_SetRGBStroke( dev->page, (HPDF_REAL) ( pls->curcolor.r / 255.0 ),
00453 (HPDF_REAL) ( pls->curcolor.g / 255.0 ), (HPDF_REAL) ( pls->curcolor.b / 255.0 ) );
00454 HPDF_Page_SetRGBFill( dev->page, (HPDF_REAL) ( pls->curcolor.r / 255.0 ),
00455 (HPDF_REAL) ( pls->curcolor.g / 255.0 ), (HPDF_REAL) ( pls->curcolor.b / 255.0 ) );
00456
00457 HPDF_Page_MoveTo( dev->page, (HPDF_REAL) xa[0], (HPDF_REAL) ya[0] );
00458 for ( i = 1; i < npts; i++ )
00459 HPDF_Page_LineTo( dev->page, (HPDF_REAL) xa[i], (HPDF_REAL) ya[i] );
00460
00461 if ( fill == 1 )
00462 {
00463 if ( pls->dev_eofill )
00464 HPDF_Page_EofillStroke( dev->page );
00465 else
00466 HPDF_Page_FillStroke( dev->page );
00467 }
00468 else
00469 {
00470 HPDF_Page_Stroke( dev->page );
00471 }
00472 }
00473
00474
00475
00476
00477
00478
00479
00480
00481
00482
00483
00484
00485 static unsigned char plunicode2type1( const PLUNICODE index,
00486 const Unicode_to_Type1_table lookup[],
00487 const int nlookup )
00488 {
00489 int jlo = -1, jmid, jhi = nlookup;
00490
00491 while ( jhi - jlo > 1 )
00492 {
00493
00494
00495
00496
00497 jmid = ( jlo + jhi ) / 2;
00498 if ( index > lookup[jmid].Unicode )
00499 jlo = jmid;
00500 else if ( index < lookup[jmid].Unicode )
00501 jhi = jmid;
00502 else
00503
00504
00505
00506 return ( lookup[jmid].Type1 );
00507 }
00508
00509
00510
00511
00512
00513 return ( ' ' );
00514 }
00515
00516
00517
00518
00519
00520
00521
00522
00523 void PSDrawTextToCanvas( pdfdev* dev, unsigned char* type1_string, short drawText )
00524 {
00525 HPDF_REAL th;
00526
00527
00528 if ( drawText )
00529 {
00530 HPDF_Page_BeginText( dev->page );
00531 HPDF_Page_SetTextRenderingMode( dev->page, HPDF_FILL );
00532 HPDF_Page_SetRGBFill( dev->page, dev->textRed, dev->textGreen, dev->textBlue );
00533 HPDF_Page_MoveTextPos( dev->page, dev->textWidth, dev->yOffset );
00534 HPDF_Page_ShowText( dev->page, (char *) type1_string );
00535 HPDF_Page_EndText( dev->page );
00536 }
00537
00538
00539 dev->textWidth += HPDF_Page_TextWidth( dev->page, (char *) type1_string );
00540 th = (HPDF_REAL) ( HPDF_Font_GetCapHeight( dev->m_font ) * dev->fontSize * dev->fontScale / 1000.0 );
00541 dev->textHeight = dev->textHeight > ( th + dev->yOffset ) ? dev->textHeight : ( th + dev->yOffset );
00542
00543
00544 memset( type1_string, '\0', MAX_STRING_LEN );
00545 }
00546
00547
00548
00549
00550
00551
00552
00553 void PSSetFont( pdfdev* dev, PLUNICODE fci )
00554 {
00555 char *font;
00556
00557
00558
00559
00560 if ( fci == 0 )
00561 {
00562 font = "Symbol";
00563 dev->nlookup = number_of_entries_in_unicode_to_symbol_table;
00564 dev->lookup = unicode_to_symbol_lookup_table;
00565 dev->if_symbol_font = 1;
00566 }
00567 else
00568 {
00569
00570 font = plP_FCI2FontName( fci, Type1Lookup, N_Type1Lookup );
00571 dev->nlookup = number_of_entries_in_unicode_to_standard_table;
00572 dev->lookup = unicode_to_standard_lookup_table;
00573 dev->if_symbol_font = 0;
00574 }
00575
00576 if ( !( dev->m_font = HPDF_GetFont( dev->pdf, font, NULL ) ) )
00577 plexit( "ERROR: Couldn't open font\n" );
00578
00579 HPDF_Page_SetFontAndSize( dev->page, dev->m_font, dev->fontSize * dev->fontScale );
00580 }
00581
00582
00583
00584
00585
00586
00587
00588 # define RISE_FACTOR 0.6
00589
00590
00591
00592
00593
00594
00595
00596
00597 void PSDrawText( pdfdev* dev, PLUNICODE* ucs4, int ucs4Len, short drawText )
00598 {
00599 int i, s;
00600 unsigned char type1_string[MAX_STRING_LEN];
00601 char plplotEsc;
00602 PLUNICODE fci;
00603 int last_chance = 0;
00604 PLFLT old_sscale, sscale, old_soffset, soffset, dup;
00605 PLINT level = 0;
00606
00607 memset( type1_string, '\0', MAX_STRING_LEN );
00608
00609
00610 plgesc( &plplotEsc );
00611
00612
00613 dev->fontScale = 1.0;
00614 dev->yOffset = 0.0;
00615 plgfci( &fci );
00616 PSSetFont( dev, fci );
00617 dev->textWidth = 0;
00618 dev->textHeight = 0;
00619
00620 i = 0; s = 0;
00621 while ( i < ucs4Len )
00622 {
00623 if ( ucs4[i] < PL_FCI_MARK )
00624 {
00625 if ( ucs4[i] != (PLUNICODE) plplotEsc )
00626 {
00627 type1_string[s] = plunicode2type1( ucs4[i], dev->lookup, dev->nlookup );
00628 if ( ucs4[i] != ' ' && type1_string[s] == ' ' )
00629 {
00630
00631 if ( !dev->if_symbol_font )
00632 {
00633
00634
00635 type1_string[s] = '\0';
00636 PSDrawTextToCanvas( dev, type1_string, drawText );
00637 s = 0;
00638 last_chance = 1;
00639 PSSetFont( dev, 0 );
00640 continue;
00641 }
00642 else if ( !last_chance )
00643 {
00644
00645
00646
00647 type1_string[s] = '\0';
00648 PSDrawTextToCanvas( dev, type1_string, drawText );
00649 s = 0;
00650 last_chance = 0;
00651 PSSetFont( dev, fci );
00652 continue;
00653 }
00654 else
00655 {
00656
00657
00658
00659
00660 PSDrawTextToCanvas( dev, type1_string, drawText );
00661 s = 0;
00662 last_chance = 0;
00663 PSSetFont( dev, fci );
00664 i++;
00665 continue;
00666 }
00667 }
00668 else
00669 {
00670
00671 s++;
00672 i++;
00673 last_chance = 0;
00674 continue;
00675 }
00676 }
00677 i++;
00678 if ( ucs4[i] == (PLUNICODE) plplotEsc )
00679 {
00680 type1_string[s] = plunicode2type1( ucs4[i], dev->lookup, dev->nlookup );
00681 if ( ucs4[i] != ' ' && type1_string[s] == ' ' )
00682 {
00683
00684 if ( !dev->if_symbol_font )
00685 {
00686
00687
00688 type1_string[s] = '\0';
00689 PSDrawTextToCanvas( dev, type1_string, drawText );
00690 s = 0;
00691 last_chance = 1;
00692 PSSetFont( dev, 0 );
00693 continue;
00694 }
00695 else if ( !last_chance )
00696 {
00697
00698
00699
00700 type1_string[s] = '\0';
00701 PSDrawTextToCanvas( dev, type1_string, drawText );
00702 s = 0;
00703 last_chance = 0;
00704 PSSetFont( dev, fci );
00705 continue;
00706 }
00707 else
00708 {
00709
00710
00711
00712
00713 PSDrawTextToCanvas( dev, type1_string, drawText );
00714 s = 0;
00715 last_chance = 0;
00716 PSSetFont( dev, fci );
00717 i++;
00718 continue;
00719 }
00720 }
00721 else
00722 {
00723
00724 s++;
00725 i++;
00726 last_chance = 0;
00727 continue;
00728 }
00729 }
00730 else
00731 {
00732 if ( ucs4[i] == (PLUNICODE) 'u' )
00733 {
00734
00735 PSDrawTextToCanvas( dev, type1_string, drawText );
00736 s = 0;
00737
00738 plP_script_scale( TRUE, &level,
00739 &old_sscale, &sscale, &old_soffset, &soffset );
00740
00741
00742
00743
00744 dup = 0.5 * ( 1.0 - sscale );
00745 dev->fontScale = sscale;
00746 PSSetFont( dev, fci );
00747 dev->yOffset = dev->fontSize * ( soffset * RISE_FACTOR + dup );
00748 }
00749 if ( ucs4[i] == (PLUNICODE) 'd' )
00750 {
00751
00752 PSDrawTextToCanvas( dev, type1_string, drawText );
00753 s = 0;
00754
00755 plP_script_scale( FALSE, &level,
00756 &old_sscale, &sscale, &old_soffset, &soffset );
00757
00758
00759
00760
00761 dup = -0.5 * ( 1.0 - sscale );
00762 dev->fontScale = sscale;
00763 PSSetFont( dev, fci );
00764 dev->yOffset = -dev->fontSize * ( soffset * RISE_FACTOR + dup );
00765 }
00766 if ( ucs4[i] == (PLUNICODE) '-' )
00767 {
00768 PSDrawTextToCanvas( dev, type1_string, drawText );
00769 s = 0;
00770
00771
00772 PSSetFont( dev, fci );
00773 }
00774 if ( ucs4[i] == (PLUNICODE) '+' )
00775 {
00776 }
00777 i++;
00778 }
00779 }
00780 else
00781 {
00782
00783 PSDrawTextToCanvas( dev, type1_string, drawText );
00784 s = 0;
00785
00786
00787 fci = ucs4[i];
00788 PSSetFont( dev, fci );
00789 i++;
00790 }
00791 }
00792
00793 PSDrawTextToCanvas( dev, type1_string, drawText );
00794 }
00795
00796
00797
00798
00799
00800
00801
00802 void process_string( PLStream* pls, EscText* args )
00803 {
00804 pdfdev * dev = (pdfdev *) pls->dev;
00805 PLFLT rotation, shear, stride;
00806 HPDF_REAL cos_rot, sin_rot, cos_shear, sin_shear;
00807
00808
00809 if ( args->unicode_array_len == 0 )
00810 {
00811 printf( "Non unicode string passed to a pdf driver, ignoring\n" );
00812 return;
00813 }
00814
00815
00816 if ( args->unicode_array_len >= MAX_STRING_LEN )
00817 {
00818 printf( "Sorry, the pdf drivers only handles strings of length < %d\n", MAX_STRING_LEN );
00819 return;
00820 }
00821
00822
00823 dev->fontSize = (HPDF_REAL) ( pls->chrht * DEVICE_PIXELS_PER_INCH / 25.4 * 1.6 );
00824
00825
00826 dev->textRed = (HPDF_REAL) ( pls->curcolor.r / 255.0 );
00827 dev->textGreen = (HPDF_REAL) ( pls->curcolor.g / 255.0 );
00828 dev->textBlue = (HPDF_REAL) ( pls->curcolor.b / 255.0 );
00829
00830
00831 plRotationShear( args->xform, &rotation, &shear, &stride );
00832 rotation -= pls->diorot * M_PI / 2.0;
00833 cos_rot = (HPDF_REAL) cos( rotation );
00834 sin_rot = (HPDF_REAL) sin( rotation );
00835 cos_shear = (HPDF_REAL) cos( shear );
00836 sin_shear = (HPDF_REAL) sin( shear );
00837
00838
00839 PSDrawText( dev, args->unicode_array, args->unicode_array_len, 0 );
00840
00841
00842 HPDF_Page_GSave( dev->page );
00843 HPDF_Page_Concat( dev->page, cos_rot, sin_rot,
00844 -cos_rot * sin_shear - sin_rot * cos_shear,
00845 -sin_rot * sin_shear + cos_rot * cos_shear,
00846 (HPDF_REAL) ( args->x ), (HPDF_REAL) ( args->y ) );
00847 HPDF_Page_Concat( dev->page, (HPDF_REAL) 1.0, (HPDF_REAL) 0.0, (HPDF_REAL) 0.0, (HPDF_REAL) 1.0,
00848 (HPDF_REAL) ( -args->just * dev->textWidth ), (HPDF_REAL) ( -0.5 * dev->textHeight ) );
00849 PSDrawText( dev, args->unicode_array, args->unicode_array_len, 1 );
00850 HPDF_Page_GRestore( dev->page );
00851 }
00852
00853 #else
00854
00855
00856
00857
00858
00859
00860 int pldummy_pdf()
00861 {
00862 return 0;
00863 }
00864
00865 #endif // PLD_pdf
00866