Changeset 91 for trunk/Lucide/SOURCE/gui/print.cpp
- Timestamp:
- Aug 2, 2006, 3:02:52 PM (15 years ago)
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/Lucide/SOURCE/gui/print.cpp
r90 r91 35 35 #define INCL_WIN 36 36 #define INCL_GPI 37 #define INCL_DOS 37 38 #define INCL_DEV 38 39 #define INCL_ERRORS … … 44 45 45 46 #include <string.h> 46 47 #include <process.h> 48 #include <stdio.h> 49 #include <io.h> 50 51 #include "globals.h" 52 #include "progressDlg.h" 47 53 #include "print.h" 54 #include "luutils.h" 55 #include "messages.h" 48 56 49 57 // OpenWatcom headers doesn't have GpiDrawBits() declaration … … 54 62 55 63 #define UNITS_MULTIPLIER 100 56 64 #define STD_IMAGE_ZOOM 2.0 65 #define HIGH_IMAGE_ZOOM 3.0 66 #define PS_PRINT_BUF_SIZE 32768 57 67 #define TEST_MARGIN 10 58 68 59 void printPage( LuDocument *doc, long page, HPS hpsPrinter, PHCINFO pcurForm ); 60 void queryCurrentForm( HDC hdcPrinter, PHCINFO pcurForm ); 61 62 void printDocument( LuDocument *doc, void *q ) 63 { 64 PPRQINFO3 pQueueInfo = (PPRQINFO3)q; 69 70 class LucidePrinting 71 { 72 public: 73 LucidePrinting( HWND hWndFrame, LuDocument *_doc, 74 const char *_title, PrintSetup *_psetup ); 75 ~LucidePrinting(); 76 void doPrint(); 77 78 private: 79 bool queryCurrentForm( HAB lhab, PHCINFO pcurForm ); 80 void printPagePm( long page, HPS hpsPrinter, PHCINFO pcurForm ); 81 bool doPmPrint( HAB lhab ); 82 bool doPsPrint( HAB lhab ); 83 84 HWND hFrame; 85 LuDocument *doc; 86 char *title; 87 PrintSetup *psetup; 88 bool abortPrinting; 89 ProgressDlg *progressDlg; 90 91 static void printabort( void *data ); 92 static void printthread( void *data ); 93 }; 94 95 96 void printDocument( HWND hWndFrame, LuDocument *doc, const char *title, PrintSetup *psetup ) 97 { 98 LucidePrinting *p = new LucidePrinting( hWndFrame, doc, title, psetup ); 99 p->doPrint(); 100 } 101 102 103 LucidePrinting::LucidePrinting( HWND hWndFrame, LuDocument *_doc, 104 const char *_title, PrintSetup *_psetup ) 105 { 106 hFrame = hWndFrame; 107 doc = _doc; 108 title = newstrdup( _title ); 109 psetup = new PrintSetup; 110 memcpy( psetup, _psetup, sizeof( PrintSetup ) ); 111 abortPrinting = false; 112 progressDlg = new ProgressDlg( hWndFrame ); 113 } 114 115 LucidePrinting::~LucidePrinting() 116 { 117 delete title; 118 delete psetup; 119 delete progressDlg; 120 } 121 122 void LucidePrinting::doPrint() 123 { 124 progressDlg->setBreakFunc( printabort, this ); 125 progressDlg->setText( "" ); 126 progressDlg->show( printthread, this ); 127 } 128 129 bool LucidePrinting::doPmPrint( HAB lhab ) 130 { 65 131 CHAR achDriverName[ DRIVERNAME_LENGTH ] = ""; 132 DEVOPENSTRUC dos = { 0 }; 66 133 SIZEL sizel = { 0 }; 67 DEVOPENSTRUC dos = { 0 }; 134 135 HCINFO curForm = { 0 }; 136 if ( !queryCurrentForm( lhab, &curForm ) ) { 137 return false; 138 } 68 139 69 140 // build a devopenstruct for the call to DevOpenDC 70 dos.pszLogAddress = p QueueInfo->pszName;71 strcpy( achDriverName, p QueueInfo->pszDriverName );141 dos.pszLogAddress = psetup->QueueInfo.pszName; // 1 142 strcpy( achDriverName, psetup->QueueInfo.pszDriverName ); 72 143 achDriverName[ strcspn( achDriverName, "." ) ] = '\0'; 73 dos.pszDriverName = achDriverName; 74 dos.pdriv = pQueueInfo->pDriverData; 75 76 HDC hdcPrinter = DevOpenDC( hab, OD_QUEUED, "*", 3L, (PDEVOPENDATA)&dos, NULLHANDLE ); 144 dos.pszDriverName = achDriverName; // 2 145 dos.pdriv = psetup->QueueInfo.pDriverData; // 3 146 dos.pszDataType = "PM_Q_STD"; // 4 147 148 HDC hdcPrinter = DevOpenDC( lhab, OD_QUEUED, "*", 4L, (PDEVOPENDATA)&dos, NULLHANDLE ); 77 149 if ( hdcPrinter == DEV_ERROR ) { 78 somPrintf( "DevOpenDC error\n" ); 79 return; 150 return false; 80 151 } 81 152 82 153 // PS in HiMetric, 0.01 mm 83 HPS hpsPrinter = GpiCreatePS( hab, hdcPrinter, &sizel, PU_HIMETRIC | GPIA_ASSOC );154 HPS hpsPrinter = GpiCreatePS( lhab, hdcPrinter, &sizel, PU_HIMETRIC | GPIA_ASSOC ); 84 155 if ( hpsPrinter == DEV_ERROR ) { 85 156 DevCloseDC( hdcPrinter ); 86 somPrintf( "GpiCreatePS error\n" ); 87 return; 88 } 89 90 HCINFO curForm = { 0 }; 91 queryCurrentForm( hdcPrinter, &curForm ); 92 char *psz = "test"; 157 return false; 158 } 159 93 160 // Issue STARTDOC to begin printing 94 DevEscape( hdcPrinter, DEVESC_STARTDOC, (LONG)strlen(psz), (PBYTE)psz, NULL, NULL ); 95 96 somPrintf( "begin!\n" ); 97 98 printPage( doc, 0, hpsPrinter, &curForm ); 99 100 somPrintf( "end!\n" ); 101 102 DevEscape( hdcPrinter, DEVESC_ENDDOC, 0L, NULL, NULL, NULL ); 161 DevEscape( hdcPrinter, DEVESC_STARTDOC, strlen(title), (PBYTE)title, NULL, NULL ); 162 163 long totalpages = psetup->pgto - psetup->pgfrom + 1; 164 for ( long pg = psetup->pgfrom; pg <= psetup->pgto; pg++ ) 165 { 166 char *fmt = newstrdupL( PRINT_PRINTING_PAGE_OF ); 167 char *buf = new char[ 255 ]; 168 snprintf( buf, 255, fmt, pg, totalpages ); 169 progressDlg->setText( buf ); 170 delete fmt; 171 delete buf; 172 173 printPagePm( pg - 1, hpsPrinter, &curForm ); 174 175 if ( pg != psetup->pgto ) { 176 DevEscape( hdcPrinter, DEVESC_NEWFRAME, 0L, NULL, NULL, NULL ); 177 } 178 179 if ( abortPrinting ) { 180 break; 181 } 182 } 183 184 // Issue DEVESC_ENDDOC, or DEVESC_ABORTDOC if printing was aborted 185 DevEscape( hdcPrinter, abortPrinting ? DEVESC_ABORTDOC : DEVESC_ENDDOC, 186 0L, NULL, NULL, NULL ); 103 187 104 188 // Release PS and DC … … 106 190 GpiDestroyPS( hpsPrinter ); 107 191 DevCloseDC( hdcPrinter ); 108 } 109 110 111 static void printPage( LuDocument *doc, long page, HPS hpsPrinter, PHCINFO pcurForm ) 192 return true; 193 } 194 195 196 void LucidePrinting::printPagePm( long page, HPS hpsPrinter, PHCINFO pcurForm ) 112 197 { 113 198 long bpp = doc->getBpp( ev ); … … 125 210 LONG pheight = ( pcurForm->cy - mTop - mBottom ) * UNITS_MULTIPLIER; 126 211 127 double zoom = __min( (double)pwidth / w, (double)pheight / h ); 128 if ( zoom > 2.0 ) { 129 zoom = 2.0; 130 } 131 132 somPrintf( "Doc pgsz: %g/%g zoom: %g\n", w, h, zoom ); 133 somPrintf( "Paper %s, pgsz: %d/%d\n", pcurForm->szFormname, pcurForm->cx, pcurForm->cy ); 134 somPrintf( "pw/ph %d/%d\n", pwidth, pheight ); 212 double zoom = 1.0; 213 if ( doc->isScalable( ev ) ) 214 { 215 double maxcoeff = psetup->higherQuality ? HIGH_IMAGE_ZOOM : STD_IMAGE_ZOOM; 216 zoom = __min( (double)pwidth / w, (double)pheight / h ); 217 if ( zoom > maxcoeff ) { 218 zoom = maxcoeff; 219 } 220 } 221 222 //somPrintf( "Doc pgsz: %g/%g zoom: %g\n", w, h, zoom ); 223 //somPrintf( "Paper %s, pgsz: %d/%d\n", pcurForm->szFormname, pcurForm->cx, pcurForm->cy ); 224 //somPrintf( "pw/ph %d/%d\n", pwidth, pheight ); 225 135 226 w *= zoom; 136 227 h *= zoom; … … 149 240 LONG rclx = w; 150 241 LONG rcly = h; 151 LuPixbuf *pixbuf = new LuPixbuf( ev, rclx, rcly, bpp ); 152 POINTL aptlPoints[4]={ rclDraw.xLeft, rclDraw.yBottom, 153 rclDraw.xRight-1, rclDraw.yTop-1, 154 0, 0, rclx, rcly }; 155 156 doc->renderPageToPixbuf( ev, page, 0, 0, rclx, rcly, zoom, 0, pixbuf ); 157 158 LONG lRop = ROP_SRCCOPY; 159 BITMAPINFO2 pbmi; 160 pbmi.cbFix = 16L; 161 pbmi.cx = rclx; 162 pbmi.cy = rcly; 163 pbmi.cPlanes = 1; 164 pbmi.cBitCount = bpp * 8; 165 GpiDrawBits( hpsPrinter, pixbuf->getDataPtr( ev ), &pbmi, 4L, 166 aptlPoints, lRop, BBO_IGNORE ); 167 delete pixbuf; 168 } 169 170 171 static void queryCurrentForm( HDC hdcPrinter, PHCINFO pcurForm ) 172 { 173 LONG lForms = DevQueryHardcopyCaps( hdcPrinter, 0, 0, NULL ); 242 if ( doc->isRenderIntoPS( ev ) ) 243 { 244 doc->renderPageToPS( ev, page, 0, 0, rclx, rcly, zoom, 0, hpsPrinter, &rclDraw ); 245 } 246 else 247 { 248 LuPixbuf *pixbuf = new LuPixbuf( ev, rclx, rcly, bpp ); 249 POINTL aptlPoints[4]={ rclDraw.xLeft, rclDraw.yBottom, 250 rclDraw.xRight-1, rclDraw.yTop-1, 251 0, 0, rclx, rcly }; 252 253 doc->renderPageToPixbuf( ev, page, 0, 0, rclx, rcly, zoom, 0, pixbuf ); 254 255 LONG lRop = ROP_SRCCOPY; 256 BITMAPINFO2 pbmi; 257 pbmi.cbFix = 16L; 258 pbmi.cx = rclx; 259 pbmi.cy = rcly; 260 pbmi.cPlanes = 1; 261 pbmi.cBitCount = bpp * 8; 262 GpiDrawBits( hpsPrinter, pixbuf->getDataPtr( ev ), &pbmi, 4L, 263 aptlPoints, lRop, BBO_IGNORE ); 264 delete pixbuf; 265 } 266 } 267 268 269 270 bool LucidePrinting::doPsPrint( HAB lhab ) 271 { 272 CHAR achDriverName[ DRIVERNAME_LENGTH ] = ""; 273 DEVOPENSTRUC dos = { 0 }; 274 SIZEL sizel = { 0 }; 275 276 HCINFO curForm = { 0 }; 277 if ( !queryCurrentForm( lhab, &curForm ) ) { 278 return false; 279 } 280 281 char *generating_ps = newstrdupL( PRINT_GENERATING_POSTSCRIPT ); 282 progressDlg->setText( generating_ps ); 283 delete generating_ps; 284 285 // Magrins 286 LONG mLeft = __max( TEST_MARGIN, curForm.xLeftClip ); 287 LONG mBottom = __max( TEST_MARGIN, curForm.yBottomClip ); 288 LONG mRight = __max( TEST_MARGIN, curForm.cx - curForm.xRightClip ); 289 LONG mTop = __max( TEST_MARGIN, curForm.cy - curForm.yTopClip ); 290 291 // Count paper page size in 1/72 inches 292 double pwidth = ( (double)( curForm.cx - mLeft - mRight ) / 25.4 ) * 72.0; 293 double pheight = ( (double)( curForm.cy - mTop - mBottom ) / 25.4 ) * 72.0; 294 295 char *tmpps = "TMPLUCID.PS"; 296 BOOL rc = doc->exportToPostScript( ev, tmpps, psetup->pgfrom-1, psetup->pgto-1, 297 pwidth, pheight, false ); 298 if ( !rc ) { 299 unlink( tmpps ); 300 return false; 301 } 302 if ( abortPrinting ) { 303 unlink( tmpps ); 304 return true; 305 } 306 307 char *spooling_ps = newstrdupL( PRINT_SPOOLING_POSTSCRIPT ); 308 progressDlg->setText( spooling_ps ); 309 delete spooling_ps; 310 311 // build a devopenstruct for the call to SplQmOpen 312 dos.pszLogAddress = psetup->QueueInfo.pszName; // 1 313 strcpy( achDriverName, psetup->QueueInfo.pszDriverName ); 314 achDriverName[ strcspn( achDriverName, "." ) ] = '\0'; 315 dos.pszDriverName = achDriverName; // 2 316 dos.pdriv = psetup->QueueInfo.pDriverData; // 3 317 dos.pszDataType = "PM_Q_RAW"; // 4 318 319 HSPL hspl = SplQmOpen( "*", 4L, (PQMOPENDATA)&dos ); 320 if ( hspl == SPL_ERROR ) { 321 unlink( tmpps ); 322 return false; 323 } 324 325 rc = SplQmStartDoc( hspl, title ); 326 if ( !rc ) { 327 SplQmAbort( hspl ); 328 unlink( tmpps ); 329 return false; 330 } 331 332 FILE *f = fopen( tmpps, "rb" ); 333 if ( f == NULL ) { 334 SplQmAbort( hspl ); 335 unlink( tmpps ); 336 return false; 337 } 338 339 bool splerr = false; 340 void *buf = malloc( PS_PRINT_BUF_SIZE ); 341 int rd = 0; 342 while ( rc && ( rd = fread( buf, 1, PS_PRINT_BUF_SIZE, f ) ) != 0 ) { 343 rc = SplQmWrite( hspl, rd, buf ); 344 if ( !rc || abortPrinting ) { 345 splerr = true; 346 break; 347 } 348 } 349 free( buf ); 350 fclose( f ); 351 unlink( tmpps ); 352 353 if ( splerr ) { 354 SplQmAbort( hspl ); 355 if ( !abortPrinting ) { 356 return false; 357 } 358 } 359 else { 360 SplQmEndDoc( hspl ); 361 SplQmClose( hspl ); 362 } 363 364 return true; 365 } 366 367 bool LucidePrinting::queryCurrentForm( HAB lhab, PHCINFO pcurForm ) 368 { 369 CHAR achDriverName[ DRIVERNAME_LENGTH ] = ""; 370 DEVOPENSTRUC dos = { 0 }; 371 // build a devopenstruct for the call to DevOpenDC 372 dos.pszLogAddress = psetup->QueueInfo.pszName; // 1 373 strcpy( achDriverName, psetup->QueueInfo.pszDriverName ); 374 achDriverName[ strcspn( achDriverName, "." ) ] = '\0'; 375 dos.pszDriverName = achDriverName; // 2 376 dos.pdriv = psetup->QueueInfo.pDriverData; // 3 377 378 HDC hdcPrinterInfo = DevOpenDC( lhab, OD_INFO, "*", 3L, (PDEVOPENDATA)&dos, NULLHANDLE ); 379 if ( hdcPrinterInfo == DEV_ERROR ) { 380 return false; 381 } 382 383 //long lTech = 0; 384 //DevQueryCaps( hdcPrinterInfo, CAPS_TECHNOLOGY, sizeof(long), &lTech ); 385 //somPrintf( "lTech: 0x%x\n", lTech ); 386 387 LONG lForms = DevQueryHardcopyCaps( hdcPrinterInfo, 0, 0, NULL ); 174 388 if ( lForms == DQHC_ERROR ) { 175 return; 389 DevCloseDC( hdcPrinterInfo ); 390 return false; 176 391 } 177 392 178 393 HCINFO *forms = new HCINFO[ lForms ]; 179 394 memset( forms, 0, sizeof( HCINFO ) * lForms ); 180 lForms = DevQueryHardcopyCaps( hdcPrinter , 0, lForms, forms );395 lForms = DevQueryHardcopyCaps( hdcPrinterInfo, 0, lForms, forms ); 181 396 if ( lForms == DQHC_ERROR ) { 182 397 delete forms; 183 return; 398 DevCloseDC( hdcPrinterInfo ); 399 return false; 184 400 } 185 401 … … 190 406 } 191 407 } 408 192 409 delete forms; 193 } 194 410 DevCloseDC( hdcPrinterInfo ); 411 return true; 412 } 413 414 // static method 415 void LucidePrinting::printabort( void *data ) 416 { 417 ((LucidePrinting *)data)->abortPrinting = true; 418 } 419 420 // static method, thread for asynchronous printing 421 void LucidePrinting::printthread( void *p ) 422 { 423 DosSetPriority( PRTYS_THREAD, PRTYC_IDLETIME, PRTYD_MAXIMUM, 0 ); 424 LucidePrinting *_this = (LucidePrinting *)p; 425 426 HAB thab = WinInitialize( 0 ); 427 HMQ thmq = WinCreateMsgQueue( thab, 0 ); 428 429 bool printOk = false; 430 if ( _this->psetup->ptype == TypePostScript ) { 431 printOk = _this->doPsPrint( thab ); 432 } 433 else { 434 printOk = _this->doPmPrint( thab ); 435 } 436 _this->progressDlg->hide(); 437 438 if ( !printOk ) 439 { 440 char *printfailed = newstrdupL( PRINT_FAILED ); 441 WinMessageBox( HWND_DESKTOP, _this->hFrame, printfailed, NULL, 442 1, MB_OK | MB_ERROR | MB_MOVEABLE ); 443 delete printfailed; 444 } 445 446 WinDestroyMsgQueue( thmq ); 447 WinTerminate( thab ); 448 _endthread(); 449 450 delete _this; 451 } 452
Note: See TracChangeset
for help on using the changeset viewer.