1 /************************************************************** 2 * 3 * Licensed to the Apache Software Foundation (ASF) under one 4 * or more contributor license agreements. See the NOTICE file 5 * distributed with this work for additional information 6 * regarding copyright ownership. The ASF licenses this file 7 * to you under the Apache License, Version 2.0 (the 8 * "License"); you may not use this file except in compliance 9 * with the License. You may obtain a copy of the License at 10 * 11 * http://www.apache.org/licenses/LICENSE-2.0 12 * 13 * Unless required by applicable law or agreed to in writing, 14 * software distributed under the License is distributed on an 15 * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY 16 * KIND, either express or implied. See the License for the 17 * specific language governing permissions and limitations 18 * under the License. 19 * 20 *************************************************************/ 21 22 23 24 // use this define to disable the DJP support 25 // #define NO_DJP 26 27 #define INCL_DOSMODULEMGR 28 #define INCL_DEV 29 #define INCL_SPL 30 #define INCL_SPLERRORS 31 #define INCL_SPLDOSPRINT 32 #define INCL_DEVDJP 33 34 #define INCL_GPI 35 #define INCL_DOSSEMAPHORES 36 #define INCL_PM 37 #include <svpm.h> 38 #include <pmdjp.h> 39 40 #include <string.h> 41 42 #include <osl/module.h> 43 44 #include <tools/urlobj.hxx> 45 #include <tools/svwin.h> 46 #ifdef __MINGW32__ 47 #include <excpt.h> 48 #endif 49 50 #include <os2/saldata.hxx> 51 #include <os2/salinst.h> 52 #include <os2/salgdi.h> 53 #include <os2/salframe.h> 54 #include <os2/salprn.h> 55 56 #include <salptype.hxx> 57 #include <print.h> 58 #include <jobset.h> 59 60 /* 61 #include <com/sun/star/ui/dialogs/TemplateDescription.hpp> 62 #include <com/sun/star/ui/dialogs/ExecutableDialogResults.hpp> 63 #include <com/sun/star/ui/dialogs/XFilePicker.hpp> 64 #include <com/sun/star/ui/dialogs/XFilterManager.hpp> 65 #include <com/sun/star/lang/XMultiServiceFactory.hpp> 66 #include <com/sun/star/lang/XInitialization.hpp> 67 #include <comphelper/processfactory.hxx> 68 */ 69 70 #include <malloc.h> 71 72 /* 73 #define _SV_SALPRN_CXX 74 #include <tools/debug.hxx> 75 #include <saldata.hxx> 76 #include <salinst.h> 77 #include <salgdi.h> 78 #include <salframe.h> 79 #include <vcl/salptype.hxx> 80 #include <salprn.h> 81 #include <vcl/print.h> 82 #include <vcl/jobset.h> 83 84 */ 85 86 #ifndef __H_FT2LIB 87 #include <os2/wingdi.h> 88 #include <ft2lib.h> 89 #endif 90 91 // ======================================================================= 92 93 // ----------------------- 94 // - struct ImplFormInfo - 95 // ----------------------- 96 97 struct ImplFormInfo 98 { 99 long mnPaperWidth; 100 long mnPaperHeight; 101 #ifndef NO_DJP 102 DJPT_PAPERSIZE mnId; 103 #endif 104 }; 105 106 // ======================================================================= 107 108 // ----------------------- 109 // - struct ImplTrayInfo - 110 // ----------------------- 111 112 struct ImplTrayInfo 113 { 114 CHAR maName[32]; 115 CHAR maDisplayName[64]; 116 DJPT_TRAYTYPE mnId; 117 118 ImplTrayInfo( const char* pTrayName, 119 const char* pTrayDisplayName ) 120 { 121 strcpy( maName, pTrayName); 122 strcpy( maDisplayName, pTrayDisplayName); 123 } 124 }; 125 126 // ======================================================================= 127 128 struct ImplQueueSalSysData 129 { 130 ByteString maPrinterName; // pszPrinters 131 ByteString maName; // pszName bzw. LogAddress 132 ByteString maOrgDriverName; // pszDriverName (maDriverName.maDeviceName) 133 ByteString maDriverName; // pszDriverName bis . 134 ByteString maDeviceName; // pszDriverName nach . 135 PDRIVDATA mpDrivData; 136 137 ImplQueueSalSysData( const ByteString& rPrinterName, 138 const ByteString& rName, 139 const ByteString& rDriverName, 140 const ByteString& rDeviceName, 141 const ByteString& rOrgDriverName, 142 PDRIVDATA pDrivData ); 143 ~ImplQueueSalSysData(); 144 }; 145 146 // ----------------------------------------------------------------------- 147 148 ImplQueueSalSysData::ImplQueueSalSysData( const ByteString& rPrinterName, 149 const ByteString& rName, 150 const ByteString& rOrgDriverName, 151 const ByteString& rDriverName, 152 const ByteString& rDeviceName, 153 PDRIVDATA pDrivData ) : 154 maPrinterName( rPrinterName ), 155 maName( rName ), 156 maOrgDriverName( rName ), 157 maDriverName( rDriverName ), 158 maDeviceName( rDeviceName ) 159 { 160 if ( pDrivData ) 161 { 162 mpDrivData = (PDRIVDATA)new PM_BYTE[pDrivData->cb]; 163 memcpy( mpDrivData, pDrivData, pDrivData->cb ); 164 } 165 else 166 mpDrivData = NULL; 167 } 168 169 // ----------------------------------------------------------------------- 170 171 ImplQueueSalSysData::~ImplQueueSalSysData() 172 { 173 delete mpDrivData; 174 } 175 176 // ======================================================================= 177 178 static ULONG ImplPMQueueStatusToSal( USHORT nPMStatus ) 179 { 180 ULONG nStatus = 0; 181 if ( nPMStatus & PRQ3_PAUSED ) 182 nStatus |= QUEUE_STATUS_PAUSED; 183 if ( nPMStatus & PRQ3_PENDING ) 184 nStatus |= QUEUE_STATUS_PENDING_DELETION; 185 if ( !nStatus ) 186 nStatus |= QUEUE_STATUS_READY; 187 return nStatus; 188 } 189 190 // ----------------------------------------------------------------------- 191 192 void Os2SalInstance::GetPrinterQueueInfo( ImplPrnQueueList* pList ) 193 { 194 APIRET rc; 195 ULONG nNeeded; 196 ULONG nReturned; 197 ULONG nTotal; 198 199 // query needed size of the buffer for the QueueInfo 200 rc = SplEnumQueue( (PSZ)NULL, 3, NULL, 0, &nReturned, &nTotal, &nNeeded, NULL ); 201 if( nNeeded == 0 ) 202 return; 203 204 // create the buffer for the QueueInfo 205 PCHAR pQueueData = new CHAR[nNeeded]; 206 207 // query QueueInfos 208 rc = SplEnumQueue( (PSZ)NULL, 3, pQueueData, nNeeded, &nReturned, &nTotal, &nNeeded, NULL ); 209 210 PPRQINFO3 pPrqInfo = (PPRQINFO3)pQueueData; 211 for ( int i = 0; i < nReturned; i++ ) 212 { 213 // create entry for the QueueInfo array 214 SalPrinterQueueInfo* pInfo = new SalPrinterQueueInfo; 215 216 ByteString aOrgDriverName( pPrqInfo->pszDriverName); 217 ByteString aName( pPrqInfo->pszName); 218 pInfo->maDriver = ::rtl::OStringToOUString (aOrgDriverName, gsl_getSystemTextEncoding()); 219 pInfo->maPrinterName = ::rtl::OStringToOUString (pPrqInfo->pszComment, gsl_getSystemTextEncoding()); 220 pInfo->maLocation = ::rtl::OStringToOUString (aName, gsl_getSystemTextEncoding()); 221 pInfo->mnStatus = ImplPMQueueStatusToSal( pPrqInfo->fsStatus ); 222 pInfo->mnJobs = pPrqInfo->cJobs; 223 // pInfo->maComment = !!! 224 225 // Feststellen, ob Name doppelt 226 PPRQINFO3 pTempPrqInfo = (PPRQINFO3)pQueueData; 227 for ( int j = 0; j < nReturned; j++ ) 228 { 229 // Wenn Name doppelt, erweitern wir diesen um die Location 230 if ( (j != i) && 231 (strcmp( pPrqInfo->pszComment, pTempPrqInfo->pszComment ) == 0) ) 232 { 233 pInfo->maPrinterName += ';'; 234 pInfo->maPrinterName += pInfo->maLocation; 235 } 236 pTempPrqInfo++; 237 } 238 239 // pszDriver in DriverName (bis .) und DeviceName (nach .) aufsplitten 240 PSZ pDriverName; 241 PSZ pDeviceName; 242 if ( (pDriverName = strchr( pPrqInfo->pszDriverName, '.' )) != 0 ) 243 { 244 *pDriverName = 0; 245 pDeviceName = pDriverName + 1; 246 } 247 else 248 pDeviceName = NULL; 249 250 // Alle Bytes hinter dem DeviceNamen auf 0 initialisieren, damit 251 // ein memcmp vom JobSetup auch funktioniert 252 if ( pPrqInfo->pDriverData && 253 (pPrqInfo->pDriverData->cb >= sizeof( pPrqInfo->pDriverData )) ) 254 { 255 int nDeviceNameLen = strlen( pPrqInfo->pDriverData->szDeviceName ); 256 memset( pPrqInfo->pDriverData->szDeviceName+nDeviceNameLen, 257 0, 258 sizeof( pPrqInfo->pDriverData->szDeviceName )-nDeviceNameLen ); 259 } 260 261 // save driver data and driver names 262 ByteString aPrinterName( pPrqInfo->pszPrinters); 263 ByteString aDriverName( pPrqInfo->pszDriverName); 264 ByteString aDeviceName; 265 if ( pDeviceName ) 266 aDeviceName = pDeviceName; 267 pInfo->mpSysData = new ImplQueueSalSysData( aPrinterName, aName, 268 aOrgDriverName, 269 aDriverName, aDeviceName, 270 pPrqInfo->pDriverData ); 271 272 // add queue to the list 273 pList->Add( pInfo ); 274 275 // increment to next element of the QueueInfo array 276 pPrqInfo++; 277 } 278 279 delete [] pQueueData; 280 } 281 282 // ----------------------------------------------------------------------- 283 284 void Os2SalInstance::GetPrinterQueueState( SalPrinterQueueInfo* pInfo ) 285 { 286 APIRET rc; 287 ULONG nNeeded; 288 ULONG nReturned; 289 ULONG nTotal; 290 291 // query needed size of the buffer for the QueueInfo 292 rc = SplEnumQueue( (PSZ)NULL, 3, NULL, 0, &nReturned, &nTotal, &nNeeded, NULL ); 293 if( nNeeded == 0 ) 294 return; 295 296 // create the buffer for the QueueInfo 297 PCHAR pQueueData = new CHAR[nNeeded]; 298 299 // query QueueInfos 300 rc = SplEnumQueue( (PSZ)NULL, 3, pQueueData, nNeeded, &nReturned, &nTotal, &nNeeded, NULL ); 301 302 PPRQINFO3 pPrqInfo = (PPRQINFO3)pQueueData; 303 for ( int i = 0; i < nReturned; i++ ) 304 { 305 ImplQueueSalSysData* pSysData = (ImplQueueSalSysData*)(pInfo->mpSysData); 306 if ( pSysData->maPrinterName.Equals( pPrqInfo->pszPrinters ) && 307 pSysData->maName.Equals( pPrqInfo->pszName ) && 308 pSysData->maOrgDriverName.Equals( pPrqInfo->pszDriverName ) ) 309 { 310 pInfo->mnStatus = ImplPMQueueStatusToSal( pPrqInfo->fsStatus ); 311 pInfo->mnJobs = pPrqInfo->cJobs; 312 break; 313 } 314 315 // increment to next element of the QueueInfo array 316 pPrqInfo++; 317 } 318 319 delete [] pQueueData; 320 } 321 322 // ----------------------------------------------------------------------- 323 324 void Os2SalInstance::DeletePrinterQueueInfo( SalPrinterQueueInfo* pInfo ) 325 { 326 delete ((ImplQueueSalSysData*)(pInfo->mpSysData)); 327 delete pInfo; 328 } 329 330 // ----------------------------------------------------------------------- 331 332 XubString Os2SalInstance::GetDefaultPrinter() 333 { 334 APIRET rc; 335 ULONG nNeeded; 336 ULONG nReturned; 337 ULONG nTotal; 338 char szQueueName[255]; 339 XubString aDefaultName; 340 341 // query default queue 342 if ( !PrfQueryProfileString( HINI_PROFILE, SPL_INI_SPOOLER, "QUEUE", 0, szQueueName, sizeof( szQueueName ) ) ) 343 return aDefaultName; 344 345 // extract first queue name 346 PSZ pStr; 347 if ( (pStr = strchr( szQueueName, ';' )) != 0 ) 348 *pStr = 0; 349 350 // query needed size of the buffer for the QueueInfo 351 rc = SplEnumQueue( (PSZ)NULL, 3, NULL, 0, &nReturned, &nTotal, &nNeeded, NULL ); 352 if ( nNeeded == 0 ) 353 return aDefaultName; 354 355 // create the buffer for the QueueInfo 356 PCHAR pQueueData = new CHAR[ nNeeded ]; 357 358 // query QueueInfos 359 rc = SplEnumQueue ((PSZ)NULL, 3, pQueueData, nNeeded, &nReturned, &nTotal, &nNeeded, NULL ); 360 361 // find printer name for default queue 362 PPRQINFO3 pPrqInfo = (PPRQINFO3) pQueueData; 363 for ( int i = 0; i < nReturned; i++ ) 364 { 365 if ( strcmp( pPrqInfo->pszName, szQueueName ) == 0 ) 366 { 367 aDefaultName = ::rtl::OStringToOUString (pPrqInfo->pszComment, gsl_getSystemTextEncoding()); 368 369 // Feststellen, ob Name doppelt 370 PPRQINFO3 pTempPrqInfo = (PPRQINFO3)pQueueData; 371 for ( int j = 0; j < nReturned; j++ ) 372 { 373 // Wenn Name doppelt, erweitern wir diesen um die Location 374 if ( (j != i) && 375 (strcmp( pPrqInfo->pszComment, pTempPrqInfo->pszComment ) == 0) ) 376 { 377 String pszName( ::rtl::OStringToOUString (pPrqInfo->pszName, gsl_getSystemTextEncoding())); 378 aDefaultName += ';'; 379 aDefaultName += pszName; 380 } 381 pTempPrqInfo++; 382 } 383 break; 384 } 385 386 // increment to next element of the QueueInfo array 387 pPrqInfo++; 388 } 389 390 delete [] pQueueData; 391 392 return aDefaultName; 393 } 394 395 // ======================================================================= 396 397 static void* ImplAllocPrnMemory( size_t n ) 398 { 399 return calloc( n, 1); 400 } 401 402 // ----------------------------------------------------------------------- 403 404 inline void ImplFreePrnMemory( void* p ) 405 { 406 free( p ); 407 } 408 409 // ----------------------------------------------------------------------- 410 411 static PDRIVDATA ImplPrnDrivData( const ImplJobSetup* pSetupData ) 412 { 413 // Diese Funktion wird eingesetzt, damit Druckertreiber nicht auf 414 // unseren Daten arbeiten, da es durch Konfigurationsprobleme 415 // sein kann, das der Druckertreiber bei uns Daten ueberschreibt. 416 // Durch diese vorgehensweise werden einige Abstuerze vermieden, bzw. 417 // sind dadurch leichter zu finden 418 419 if ( !pSetupData->mpDriverData ) 420 return NULL; 421 422 DBG_ASSERT( ((PDRIVDATA)(pSetupData->mpDriverData))->cb == pSetupData->mnDriverDataLen, 423 "ImplPrnDrivData() - SetupDataLen != DriverDataLen" ); 424 425 PDRIVDATA pDrivData = (PDRIVDATA)ImplAllocPrnMemory( pSetupData->mnDriverDataLen ); 426 memcpy( pDrivData, pSetupData->mpDriverData, pSetupData->mnDriverDataLen ); 427 return pDrivData; 428 } 429 430 // ----------------------------------------------------------------------- 431 432 static void ImplUpdateSetupData( const PDRIVDATA pDrivData, ImplJobSetup* pSetupData ) 433 { 434 // Diese Funktion wird eingesetzt, damit Druckertreiber nicht auf 435 // unseren Daten arbeiten, da es durch Konfigurationsprobleme 436 // sein kann, das der Druckertreiber bei uns Daten ueberschreibt. 437 // Durch diese vorgehensweise werden einige Abstuerze vermieden, bzw. 438 // sind dadurch leichter zu finden 439 440 if ( !pDrivData || !pDrivData->cb ) 441 { 442 if ( pSetupData->mpDriverData ) 443 rtl_freeMemory( pSetupData->mpDriverData ); 444 pSetupData->mpDriverData = NULL; 445 pSetupData->mnDriverDataLen = 0; 446 } 447 else 448 { 449 // Alle Bytes hinter dem DeviceNamen auf 0 initialisieren, damit 450 // ein memcmp vom JobSetup auch funktioniert 451 if ( pDrivData->cb >= sizeof( pDrivData ) ) 452 { 453 int nDeviceNameLen = strlen( pDrivData->szDeviceName ); 454 memset( pDrivData->szDeviceName+nDeviceNameLen, 455 0, 456 sizeof( pDrivData->szDeviceName )-nDeviceNameLen ); 457 } 458 459 if ( pSetupData->mpDriverData ) 460 { 461 if ( pSetupData->mnDriverDataLen != pDrivData->cb ) 462 rtl_freeMemory( pSetupData->mpDriverData ); 463 pSetupData->mpDriverData = (sal_uInt8*)rtl_allocateMemory( pDrivData->cb); 464 } 465 else 466 pSetupData->mpDriverData = (sal_uInt8*)rtl_allocateMemory( pDrivData->cb); 467 pSetupData->mnDriverDataLen = pDrivData->cb; 468 memcpy( pSetupData->mpDriverData, pDrivData, pDrivData->cb ); 469 } 470 471 if ( pDrivData ) 472 ImplFreePrnMemory( pDrivData ); 473 } 474 475 // ----------------------------------------------------------------------- 476 477 static sal_Bool ImplPaperSizeEqual( long nPaperWidth1, long nPaperHeight1, 478 long nPaperWidth2, long nPaperHeight2 ) 479 { 480 return (((nPaperWidth1 >= nPaperWidth2-1) && (nPaperWidth1 <= nPaperWidth2+1)) && 481 ((nPaperHeight1 >= nPaperHeight2-1) && (nPaperHeight1 <= nPaperHeight2+1))); 482 } 483 484 // ----------------------------------------------------------------------- 485 486 static sal_Bool ImplIsDriverDJPEnabled( HDC hDC ) 487 { 488 #ifdef NO_DJP 489 return FALSE; 490 #else 491 // Ueber OS2-Ini kann DJP disablte werden 492 if ( !PrfQueryProfileInt( HINI_PROFILE, SAL_PROFILE_APPNAME, SAL_PROFILE_USEDJP, 1 ) ) 493 return FALSE; 494 495 // Testen, ob DJP-Interface am Drucker vorhanden 496 LONG lQuery; 497 APIRET rc; 498 499 lQuery = DEVESC_QUERYSIZE; 500 rc = DevEscape( hDC, 501 DEVESC_QUERYESCSUPPORT, 502 sizeof( lQuery ), 503 (PBYTE)&lQuery, 504 0, 505 (PBYTE)NULL ); 506 if ( DEV_OK != rc ) 507 return FALSE; 508 509 lQuery = DEVESC_QUERYJOBPROPERTIES; 510 rc = DevEscape( hDC, 511 DEVESC_QUERYESCSUPPORT, 512 sizeof( lQuery ), 513 (PBYTE)&lQuery, 514 0, 515 (PBYTE)NULL ); 516 if ( DEV_OK != rc ) 517 return FALSE; 518 519 lQuery = DEVESC_SETJOBPROPERTIES; 520 rc = DevEscape( hDC, 521 DEVESC_QUERYESCSUPPORT, 522 sizeof( lQuery ), 523 (PBYTE)&lQuery, 524 0, 525 (PBYTE)NULL ); 526 if ( DEV_OK != rc ) 527 return FALSE; 528 529 return TRUE; 530 #endif 531 } 532 533 // ----------------------------------------------------------------------- 534 535 static void ImplFormatInputList( PDJP_ITEM pDJP, PQUERYTUPLE pTuple ) 536 { 537 // Loop through the query elements 538 sal_Bool fContinue = TRUE; 539 do 540 { 541 pDJP->cb = sizeof (DJP_ITEM); 542 pDJP->ulProperty = pTuple->ulProperty; 543 pDJP->lType = pTuple->lType; 544 pDJP->ulNumReturned = 0; 545 pDJP->ulValue = DJP_NONE; 546 547 // at EOL? 548 fContinue = DJP_NONE != pTuple->ulProperty; 549 550 // Move to next item structure and tuplet 551 pDJP++; 552 pTuple++; 553 } 554 while ( fContinue ); 555 } 556 557 // ----------------------------------------------------------------------- 558 559 static void ImplFreeFormAndTrayList( Os2SalInfoPrinter* pOs2SalInfoPrinter ) 560 { 561 if ( pOs2SalInfoPrinter->mnFormCount ) 562 { 563 for ( USHORT i = 0; i < pOs2SalInfoPrinter->mnFormCount; i++ ) 564 delete pOs2SalInfoPrinter->mpFormArray[i]; 565 delete [] pOs2SalInfoPrinter->mpFormArray; 566 pOs2SalInfoPrinter->mnFormCount = 0; 567 } 568 569 if ( pOs2SalInfoPrinter->mnTrayCount ) 570 { 571 for ( USHORT i = 0; i < pOs2SalInfoPrinter->mnTrayCount; i++ ) 572 delete pOs2SalInfoPrinter->mpTrayArray[i]; 573 delete [] pOs2SalInfoPrinter->mpTrayArray; 574 pOs2SalInfoPrinter->mnTrayCount = 0; 575 } 576 } 577 578 // ----------------------------------------------------------------------- 579 580 static void ImplGetFormAndTrayList( Os2SalInfoPrinter* pOs2SalInfoPrinter, const ImplJobSetup* pSetupData ) 581 { 582 ImplFreeFormAndTrayList( pOs2SalInfoPrinter ); 583 584 LONG alQuery[] = 585 { 586 0, 0, // First two members of QUERYSIZE 587 DJP_CJ_FORM, DJP_ALL, 588 DJP_CJ_TRAYNAME, DJP_ALL, 589 DJP_NONE, DJP_NONE // EOL marker 590 }; 591 592 APIRET rc; 593 PQUERYSIZE pQuerySize = (PQUERYSIZE)alQuery; 594 PBYTE pBuffer = NULL; 595 LONG nAlloc = 0; 596 PDRIVDATA pCopyDrivData = ImplPrnDrivData( pSetupData ); 597 LONG nDrivDataSize = pCopyDrivData->cb; 598 PBYTE pDrivData = (PBYTE)pCopyDrivData; 599 600 // find out how many bytes to allocate 601 pQuerySize->cb = sizeof( alQuery ); 602 rc = DevEscape( pOs2SalInfoPrinter->mhDC, 603 DEVESC_QUERYSIZE, 604 sizeof( alQuery ), 605 (PBYTE)pQuerySize, 606 &nDrivDataSize, 607 pDrivData ); 608 if ( DEV_OK != rc ) 609 { 610 ImplFreePrnMemory( pCopyDrivData ); 611 return; 612 } 613 614 // allocate the memory 615 nAlloc = pQuerySize->ulSizeNeeded; 616 pBuffer = (PBYTE)new PM_BYTE[nAlloc]; 617 618 // set up the input 619 PDJP_ITEM pDJP = (PDJP_ITEM)pBuffer; 620 ImplFormatInputList( pDJP, pQuerySize->aTuples ); 621 622 // do it! 623 rc = DevEscape( pOs2SalInfoPrinter->mhDC, 624 DEVESC_QUERYJOBPROPERTIES, 625 nAlloc, 626 pBuffer, 627 &nDrivDataSize, 628 pDrivData ); 629 ImplFreePrnMemory( pCopyDrivData ); 630 631 if ( (DEV_OK == rc) || (DEV_WARNING == rc) ) 632 { 633 // Loop through the query elements 634 PQUERYTUPLE pTuple = pQuerySize->aTuples; 635 while ( DJP_NONE != pTuple->ulProperty ) 636 { 637 if ( pDJP->ulProperty == DJP_CJ_FORM ) 638 { 639 if ( pDJP->ulNumReturned ) 640 { 641 PDJPT_FORM pElm = DJP_ELEMENTP( *pDJP, DJPT_FORM ); 642 643 pOs2SalInfoPrinter->mnFormCount = pDJP->ulNumReturned; 644 pOs2SalInfoPrinter->mpFormArray = new PIMPLFORMINFO[pOs2SalInfoPrinter->mnFormCount]; 645 for( int i = 0; i < pDJP->ulNumReturned; i++, pElm++ ) 646 { 647 ImplFormInfo* pInfo = new ImplFormInfo; 648 pInfo->mnPaperWidth = pElm->hcInfo.cx; 649 pInfo->mnPaperHeight = pElm->hcInfo.cy; 650 pInfo->mnId = pElm->djppsFormID; 651 pOs2SalInfoPrinter->mpFormArray[i] = pInfo; 652 } 653 } 654 } 655 else if ( pDJP->ulProperty == DJP_CJ_TRAYNAME ) 656 { 657 if ( pDJP->ulNumReturned ) 658 { 659 PDJPT_TRAYNAME pElm = DJP_ELEMENTP( *pDJP, DJPT_TRAYNAME ); 660 661 pOs2SalInfoPrinter->mnTrayCount = pDJP->ulNumReturned; 662 pOs2SalInfoPrinter->mpTrayArray = new PIMPLTRAYINFO[pOs2SalInfoPrinter->mnTrayCount]; 663 for( int i = 0; i < pDJP->ulNumReturned; i++, pElm++ ) 664 { 665 ImplTrayInfo* pInfo = new ImplTrayInfo( pElm->szTrayname, pElm->szDisplayTrayname ); 666 pInfo->mnId = pElm->djpttTrayID; 667 pOs2SalInfoPrinter->mpTrayArray[i] = pInfo; 668 } 669 } 670 } 671 672 pDJP = DJP_NEXT_STRUCTP( pDJP ); 673 pTuple++; 674 } 675 } 676 677 delete [] pBuffer; 678 } 679 680 // ----------------------------------------------------------------------- 681 682 static sal_Bool ImplGetCurrentSettings( Os2SalInfoPrinter* pOs2SalInfoPrinter, ImplJobSetup* pSetupData ) 683 { 684 // Um den aktuellen Tray zu ermitteln, brauchen wir auch die Listen dazu 685 if ( !pOs2SalInfoPrinter->mnFormCount ) 686 ImplGetFormAndTrayList( pOs2SalInfoPrinter, pSetupData ); 687 688 LONG alQuery[] = 689 { 690 0, 0, // First two members of QUERYSIZE 691 DJP_SJ_ORIENTATION, DJP_CURRENT, 692 DJP_CJ_FORM, DJP_CURRENT, 693 DJP_NONE, DJP_NONE // EOL marker 694 }; 695 696 APIRET rc; 697 PQUERYSIZE pQuerySize = (PQUERYSIZE)alQuery; 698 PBYTE pBuffer = NULL; 699 LONG nAlloc = 0; 700 PDRIVDATA pCopyDrivData = ImplPrnDrivData( pSetupData ); 701 LONG nDrivDataSize = pCopyDrivData->cb; 702 PBYTE pDrivData = (PBYTE)pCopyDrivData; 703 sal_Bool bResult; 704 705 // find out how many bytes to allocate 706 pQuerySize->cb = sizeof( alQuery ); 707 rc = DevEscape( pOs2SalInfoPrinter->mhDC, 708 DEVESC_QUERYSIZE, 709 sizeof( alQuery ), 710 (PBYTE)pQuerySize, 711 &nDrivDataSize, 712 pDrivData ); 713 if ( DEV_OK != rc ) 714 { 715 ImplFreePrnMemory( pCopyDrivData ); 716 return FALSE; 717 } 718 719 // allocate the memory 720 nAlloc = pQuerySize->ulSizeNeeded; 721 pBuffer = (PBYTE)new PM_BYTE[nAlloc]; 722 723 // set up the input 724 PDJP_ITEM pDJP = (PDJP_ITEM)pBuffer; 725 ImplFormatInputList( pDJP, pQuerySize->aTuples ); 726 727 rc = DevEscape( pOs2SalInfoPrinter->mhDC, 728 DEVESC_QUERYJOBPROPERTIES, 729 nAlloc, 730 pBuffer, 731 &nDrivDataSize, 732 pDrivData ); 733 if ( (DEV_OK == rc) || (DEV_WARNING == rc) ) 734 { 735 // aktuelle Setup-Daten uebernehmen 736 ImplUpdateSetupData( pCopyDrivData, pSetupData ); 737 738 // Loop through the query elements 739 PQUERYTUPLE pTuple = pQuerySize->aTuples; 740 while ( DJP_NONE != pTuple->ulProperty ) 741 { 742 if ( pDJP->ulProperty == DJP_SJ_ORIENTATION ) 743 { 744 if ( pDJP->ulNumReturned ) 745 { 746 PDJPT_ORIENTATION pElm = DJP_ELEMENTP( *pDJP, DJPT_ORIENTATION ); 747 if ( (DJP_ORI_PORTRAIT == *pElm) || (DJP_ORI_REV_PORTRAIT == *pElm) ) 748 pSetupData->meOrientation = ORIENTATION_PORTRAIT; 749 else 750 pSetupData->meOrientation = ORIENTATION_LANDSCAPE; 751 } 752 } 753 else if ( pDJP->ulProperty == DJP_CJ_FORM ) 754 { 755 if ( pDJP->ulNumReturned ) 756 { 757 PDJPT_FORM pElm = DJP_ELEMENTP( *pDJP, DJPT_FORM ); 758 759 pSetupData->mnPaperWidth = pElm->hcInfo.cx*100; 760 pSetupData->mnPaperHeight = pElm->hcInfo.cy*100; 761 switch( pElm->djppsFormID ) 762 { 763 case DJP_PSI_A3: 764 pSetupData->mePaperFormat = PAPER_A3; 765 break; 766 767 case DJP_PSI_A4: 768 pSetupData->mePaperFormat = PAPER_A4; 769 break; 770 771 case DJP_PSI_A5: 772 pSetupData->mePaperFormat = PAPER_A5; 773 break; 774 775 case DJP_PSI_B4: 776 pSetupData->mePaperFormat = PAPER_B4_JIS; 777 break; 778 779 case DJP_PSI_B5: 780 pSetupData->mePaperFormat = PAPER_B5_JIS; 781 break; 782 783 case DJP_PSI_LETTER: 784 pSetupData->mePaperFormat = PAPER_LETTER; 785 break; 786 787 case DJP_PSI_LEGAL: 788 pSetupData->mePaperFormat = PAPER_LEGAL; 789 break; 790 791 case DJP_PSI_TABLOID: 792 pSetupData->mePaperFormat = PAPER_TABLOID; 793 break; 794 795 default: 796 pSetupData->mePaperFormat = PAPER_USER; 797 break; 798 } 799 800 // Wir suchen zuerst ueber den Namen/Id und dann ueber die Id 801 sal_Bool bTrayFound = FALSE; 802 USHORT j; 803 for ( j = 0; j < pOs2SalInfoPrinter->mnTrayCount; j++ ) 804 { 805 if ( (pOs2SalInfoPrinter->mpTrayArray[j]->mnId == pElm->djpttTrayID) && 806 (pOs2SalInfoPrinter->mpTrayArray[j]->maName == pElm->szTrayname) ) 807 { 808 pSetupData->mnPaperBin = j; 809 bTrayFound = TRUE; 810 break; 811 } 812 } 813 if ( !bTrayFound ) 814 { 815 for ( j = 0; j < pOs2SalInfoPrinter->mnTrayCount; j++ ) 816 { 817 if ( pOs2SalInfoPrinter->mpTrayArray[j]->mnId == pElm->djpttTrayID ) 818 { 819 pSetupData->mnPaperBin = j; 820 bTrayFound = TRUE; 821 break; 822 } 823 } 824 } 825 // Wenn wir Ihn immer noch nicht gefunden haben, setzen 826 // wir ihn auf DontKnow 827 if ( !bTrayFound ) 828 pSetupData->mnPaperBin = 0xFFFF; 829 } 830 } 831 832 pDJP = DJP_NEXT_STRUCTP( pDJP ); 833 pTuple++; 834 } 835 836 bResult = TRUE; 837 } 838 else 839 { 840 ImplFreePrnMemory( pCopyDrivData ); 841 bResult = FALSE; 842 } 843 844 delete [] pBuffer; 845 846 return bResult; 847 } 848 849 // ----------------------------------------------------------------------- 850 851 static sal_Bool ImplSetOrientation( HDC hPrinterDC, PDRIVDATA pDriverData, 852 Orientation eOrientation ) 853 { 854 LONG alQuery[] = 855 { 856 0, 0, // First two members of QUERYSIZE 857 DJP_SJ_ORIENTATION, DJP_CURRENT, 858 DJP_NONE, DJP_NONE // EOL marker 859 }; 860 861 APIRET rc; 862 PQUERYSIZE pQuerySize = (PQUERYSIZE)alQuery; 863 PBYTE pBuffer = NULL; 864 LONG nAlloc = 0; 865 LONG nDrivDataSize = pDriverData->cb; 866 867 // find out how many bytes to allocate 868 pQuerySize->cb = sizeof( alQuery ); 869 rc = DevEscape( hPrinterDC, 870 DEVESC_QUERYSIZE, 871 sizeof( alQuery ), 872 (PBYTE)pQuerySize, 873 &nDrivDataSize, 874 (PBYTE)pDriverData ); 875 if ( DEV_OK != rc ) 876 return FALSE; 877 878 // allocate the memory 879 nAlloc = pQuerySize->ulSizeNeeded; 880 pBuffer = (PBYTE)new PM_BYTE[nAlloc]; 881 882 // set up the input 883 PDJP_ITEM pDJP = (PDJP_ITEM)pBuffer; 884 ImplFormatInputList( pDJP, pQuerySize->aTuples ); 885 886 pDJP->cb = sizeof( DJP_ITEM ); 887 pDJP->ulProperty = DJP_SJ_ORIENTATION; 888 pDJP->lType = DJP_CURRENT; 889 pDJP->ulValue = (eOrientation == ORIENTATION_PORTRAIT) 890 ? DJP_ORI_PORTRAIT 891 : DJP_ORI_LANDSCAPE; 892 893 // do it! 894 rc = DevEscape( hPrinterDC, 895 DEVESC_SETJOBPROPERTIES, 896 nAlloc, 897 pBuffer, 898 &nDrivDataSize, 899 (PBYTE)pDriverData ); 900 901 delete [] pBuffer; 902 903 return ((DEV_OK == rc) || (DEV_WARNING == rc)); 904 } 905 906 // ----------------------------------------------------------------------- 907 908 static sal_Bool ImplSetPaperSize( HDC hPrinterDC, PDRIVDATA pDriverData, 909 DJPT_PAPERSIZE nOS2PaperFormat ) 910 { 911 LONG alQuery[] = 912 { 913 0, 0, // First two members of QUERYSIZE 914 DJP_SJ_PAPERSIZE, DJP_CURRENT, 915 DJP_NONE, DJP_NONE // EOL marker 916 }; 917 918 APIRET rc; 919 PQUERYSIZE pQuerySize = (PQUERYSIZE)alQuery; 920 PBYTE pBuffer = NULL; 921 LONG nAlloc = 0; 922 LONG nDrivDataSize = pDriverData->cb; 923 924 // find out how many bytes to allocate 925 pQuerySize->cb = sizeof( alQuery ); 926 rc = DevEscape( hPrinterDC, 927 DEVESC_QUERYSIZE, 928 sizeof( alQuery ), 929 (PBYTE)pQuerySize, 930 &nDrivDataSize, 931 (PBYTE)pDriverData ); 932 if ( DEV_OK != rc ) 933 return FALSE; 934 935 // allocate the memory 936 nAlloc = pQuerySize->ulSizeNeeded; 937 pBuffer = (PBYTE)new PM_BYTE[nAlloc]; 938 939 // set up the input 940 PDJP_ITEM pDJP = (PDJP_ITEM)pBuffer; 941 PDJP_ITEM pStartDJP = pDJP; 942 ImplFormatInputList( pDJP, pQuerySize->aTuples ); 943 944 // Neue Daten zuweisen 945 pDJP->cb = sizeof( DJP_ITEM ); 946 pDJP->ulProperty = DJP_SJ_PAPERSIZE; 947 pDJP->lType = DJP_CURRENT; 948 pDJP->ulValue = nOS2PaperFormat; 949 950 // und setzen 951 rc = DevEscape( hPrinterDC, 952 DEVESC_SETJOBPROPERTIES, 953 nAlloc, 954 pBuffer, 955 &nDrivDataSize, 956 (PBYTE)pDriverData ); 957 958 delete [] pBuffer; 959 960 return ((DEV_OK == rc) || (DEV_WARNING == rc)); 961 } 962 963 // ----------------------------------------------------------------------- 964 965 static sal_Bool ImplSetPaperBin( HDC hPrinterDC, PDRIVDATA pDriverData, 966 ImplTrayInfo* pTrayInfo ) 967 { 968 LONG alQuery[] = 969 { 970 0, 0, // First two members of QUERYSIZE 971 DJP_SJ_TRAYTYPE, DJP_CURRENT, 972 DJP_NONE, DJP_NONE // EOL marker 973 }; 974 975 APIRET rc; 976 PQUERYSIZE pQuerySize = (PQUERYSIZE)alQuery; 977 PBYTE pBuffer = NULL; 978 LONG nAlloc = 0; 979 LONG nDrivDataSize = pDriverData->cb; 980 981 // find out how many bytes to allocate 982 pQuerySize->cb = sizeof( alQuery ); 983 rc = DevEscape( hPrinterDC, 984 DEVESC_QUERYSIZE, 985 sizeof( alQuery ), 986 (PBYTE)pQuerySize, 987 &nDrivDataSize, 988 (PBYTE)pDriverData ); 989 if ( DEV_OK != rc ) 990 return FALSE; 991 992 // allocate the memory 993 nAlloc = pQuerySize->ulSizeNeeded; 994 pBuffer = (PBYTE)new PM_BYTE[nAlloc]; 995 996 // set up the input 997 PDJP_ITEM pDJP = (PDJP_ITEM)pBuffer; 998 ImplFormatInputList( pDJP, pQuerySize->aTuples ); 999 1000 // Neue Daten zuweisen 1001 pDJP->cb = sizeof( DJP_ITEM ); 1002 pDJP->ulProperty = DJP_SJ_TRAYTYPE; 1003 pDJP->lType = DJP_CURRENT; 1004 pDJP->ulValue = pTrayInfo->mnId; 1005 1006 // und setzen 1007 rc = DevEscape( hPrinterDC, 1008 DEVESC_SETJOBPROPERTIES, 1009 nAlloc, 1010 pBuffer, 1011 &nDrivDataSize, 1012 (PBYTE)pDriverData ); 1013 1014 delete [] pBuffer; 1015 1016 return ((DEV_OK == rc) || (DEV_WARNING == rc)); 1017 } 1018 1019 // ======================================================================= 1020 1021 static sal_Bool ImplSalCreateInfoPrn( Os2SalInfoPrinter* pPrinter, PDRIVDATA pDriverData, 1022 HDC& rDC, HPS& rPS ) 1023 { 1024 SalData* pSalData = GetSalData(); 1025 1026 // create info context 1027 DEVOPENSTRUC devOpenStruc; 1028 memset( &devOpenStruc, 0, sizeof( devOpenStruc ) ); 1029 devOpenStruc.pszLogAddress = (char*)pPrinter->maName.GetBuffer(); 1030 devOpenStruc.pszDriverName = (char*)pPrinter->maDriverName.GetBuffer(); 1031 devOpenStruc.pdriv = pDriverData; 1032 devOpenStruc.pszDataType = "PM_Q_STD"; 1033 1034 HDC hDC = DevOpenDC( pSalData->mhAB, OD_INFO, "*", 1035 4, (PDEVOPENDATA)&devOpenStruc, (HDC)NULL); 1036 if ( !hDC ) 1037 return FALSE; 1038 1039 // create presentation space 1040 SIZEL sizel; 1041 sizel.cx = 0; 1042 sizel.cy = 0; 1043 HPS hPS = Ft2CreatePS( pSalData->mhAB, hDC, &sizel, GPIA_ASSOC | GPIT_MICRO | PU_PELS ); 1044 if ( !hPS ) 1045 { 1046 DevCloseDC( hDC ); 1047 return FALSE; 1048 } 1049 1050 rDC = hDC; 1051 rPS = hPS; 1052 return TRUE; 1053 } 1054 1055 // ----------------------------------------------------------------------- 1056 1057 static void ImplSalDestroyInfoPrn( Os2SalInfoPrinter* pPrinter ) 1058 { 1059 ImplSalDeInitGraphics( pPrinter->mpGraphics); 1060 Ft2Associate( pPrinter->mhPS, 0 ); 1061 Ft2DestroyPS( pPrinter->mhPS ); 1062 DevCloseDC( pPrinter->mhDC ); 1063 } 1064 1065 // ======================================================================= 1066 1067 SalInfoPrinter* Os2SalInstance::CreateInfoPrinter( SalPrinterQueueInfo* pQueueInfo, 1068 ImplJobSetup* pSetupData ) 1069 { 1070 ImplQueueSalSysData* pSysQueueData = (ImplQueueSalSysData*)(pQueueInfo->mpSysData); 1071 Os2SalInfoPrinter* pPrinter = new Os2SalInfoPrinter; 1072 pPrinter->maPrinterName = pSysQueueData->maPrinterName; 1073 pPrinter->maName = pSysQueueData->maName; 1074 pPrinter->maDriverName = pSysQueueData->maDriverName; 1075 pPrinter->maDeviceName = pSysQueueData->maDeviceName; 1076 1077 // Nur Setup-Daten uebernehmen, wenn Treiber und Laenge der Treiberdaten 1078 // uebereinstimmt 1079 PDRIVDATA pDriverData; 1080 sal_Bool bUpdateDriverData; 1081 if ( pSetupData->mpDriverData && pSysQueueData->mpDrivData && 1082 (pSetupData->mnSystem == JOBSETUP_SYSTEM_OS2) && 1083 (pSetupData->mnDriverDataLen == pSysQueueData->mpDrivData->cb) && 1084 (strcmp( ((PDRIVDATA)pSetupData->mpDriverData)->szDeviceName, 1085 pSysQueueData->mpDrivData->szDeviceName ) == 0) ) 1086 { 1087 pDriverData = PDRIVDATA( pSetupData->mpDriverData ); 1088 bUpdateDriverData = FALSE; 1089 } 1090 else 1091 { 1092 pDriverData = pSysQueueData->mpDrivData; 1093 bUpdateDriverData = TRUE; 1094 } 1095 if ( pDriverData ) 1096 pPrinter->maJobSetupDeviceName = pDriverData->szDeviceName; 1097 1098 if ( !ImplSalCreateInfoPrn( pPrinter, pDriverData, 1099 pPrinter->mhDC, 1100 pPrinter->mhPS ) ) 1101 { 1102 delete pPrinter; 1103 return NULL; 1104 } 1105 1106 // create graphics object for output 1107 Os2SalGraphics* pGraphics = new Os2SalGraphics; 1108 pGraphics->mhDC = pPrinter->mhDC; 1109 pGraphics->mhPS = pPrinter->mhPS; 1110 pGraphics->mhWnd = 0; 1111 pGraphics->mbPrinter = TRUE; 1112 pGraphics->mbVirDev = FALSE; 1113 pGraphics->mbWindow = FALSE; 1114 pGraphics->mbScreen = FALSE; 1115 1116 ImplSalInitGraphics( pGraphics ); 1117 pPrinter->mpGraphics = pGraphics; 1118 1119 // check printer driver for DJP support 1120 pPrinter->mbDJPSupported = ImplIsDriverDJPEnabled( pPrinter->mhDC ); 1121 1122 if ( bUpdateDriverData ) 1123 { 1124 if ( pSetupData->mpDriverData ) 1125 rtl_freeMemory( pSetupData->mpDriverData); 1126 pSetupData->mpDriverData = (sal_uInt8*)rtl_allocateMemory( pDriverData->cb); 1127 memcpy( pSetupData->mpDriverData, pDriverData, pDriverData->cb ); 1128 pSetupData->mnDriverDataLen = pDriverData->cb; 1129 } 1130 1131 // retrieve current settings from printer driver and store them to system independend data! 1132 if ( pPrinter->mbDJPSupported ) 1133 ImplGetCurrentSettings( pPrinter, pSetupData ); 1134 pSetupData->mnSystem = JOBSETUP_SYSTEM_OS2; 1135 1136 return pPrinter; 1137 } 1138 1139 // ----------------------------------------------------------------------- 1140 1141 void Os2SalInstance::DestroyInfoPrinter( SalInfoPrinter* pPrinter ) 1142 { 1143 delete pPrinter; 1144 } 1145 1146 // ======================================================================= 1147 1148 Os2SalInfoPrinter::Os2SalInfoPrinter() 1149 { 1150 mhDC = 0; 1151 mhPS = 0; 1152 mpGraphics = NULL; 1153 mbGraphics = FALSE; 1154 mbDJPSupported = FALSE; 1155 mnFormCount = 0; 1156 mpFormArray = NULL; 1157 mnTrayCount = 0; 1158 mpTrayArray = NULL; 1159 } 1160 1161 // ----------------------------------------------------------------------- 1162 1163 Os2SalInfoPrinter::~Os2SalInfoPrinter() 1164 { 1165 if ( mpGraphics ) 1166 { 1167 ImplSalDestroyInfoPrn( this ); 1168 delete mpGraphics; 1169 } 1170 1171 ImplFreeFormAndTrayList( this ); 1172 } 1173 1174 // ----------------------------------------------------------------------- 1175 1176 SalGraphics* Os2SalInfoPrinter::GetGraphics() 1177 { 1178 if ( mbGraphics ) 1179 return NULL; 1180 1181 if ( mpGraphics ) 1182 mbGraphics = TRUE; 1183 1184 return mpGraphics; 1185 } 1186 1187 // ----------------------------------------------------------------------- 1188 1189 void Os2SalInfoPrinter::ReleaseGraphics( SalGraphics* ) 1190 { 1191 mbGraphics = FALSE; 1192 } 1193 1194 // ----------------------------------------------------------------------- 1195 1196 sal_Bool Os2SalInfoPrinter::Setup( SalFrame* pFrame, ImplJobSetup* pSetupData ) 1197 { 1198 PDRIVDATA pDrivData = ImplPrnDrivData( pSetupData ); 1199 if ( !pDrivData ) 1200 return FALSE; 1201 1202 APIRET rc = DevPostDeviceModes( GetSalData()->mhAB, pDrivData, 1203 maDriverName.GetBuffer(), 1204 maDeviceName.GetBuffer(), 1205 maPrinterName.GetBuffer(), 1206 DPDM_POSTJOBPROP ); 1207 if ( rc == DEV_OK ) 1208 { 1209 ImplUpdateSetupData( pDrivData, pSetupData ); 1210 1211 // update DC and PS 1212 HDC hDC; 1213 HPS hPS; 1214 if ( !ImplSalCreateInfoPrn( this, (PDRIVDATA)(pSetupData->mpDriverData), hDC, hPS ) ) 1215 return FALSE; 1216 1217 // Alten Printer DC/PS zerstoeren 1218 ImplSalDestroyInfoPrn( this ); 1219 1220 // Neue Daten setzen und initialisieren 1221 mhDC = hDC; 1222 mhPS = hPS; 1223 mpGraphics->mhDC = mhDC; 1224 mpGraphics->mhPS = mhPS; 1225 ImplSalInitGraphics( mpGraphics ); 1226 1227 // retrieve current settings from printer driver and store them to system independend data! 1228 ImplFreeFormAndTrayList( this ); 1229 if ( mbDJPSupported ) 1230 ImplGetCurrentSettings( this, pSetupData ); 1231 1232 return TRUE; 1233 } 1234 else 1235 { 1236 ImplFreePrnMemory( pDrivData ); 1237 return FALSE; 1238 } 1239 } 1240 1241 // ----------------------------------------------------------------------- 1242 1243 sal_Bool Os2SalInfoPrinter::SetPrinterData( ImplJobSetup* pSetupData ) 1244 { 1245 // Wir koennen nur Treiberdaten von OS2 setzen 1246 if ( pSetupData->mnSystem != JOBSETUP_SYSTEM_OS2 ) 1247 return FALSE; 1248 1249 PDRIVDATA pNewDrivData = (PDRIVDATA)(pSetupData->mpDriverData); 1250 if ( !pNewDrivData ) 1251 return FALSE; 1252 1253 // Testen, ob Printerdaten fuer den gleichen Printer uebergeben werden, 1254 // da einige Treiber zu Abstuerzen neigen, wenn Daten von einem anderen 1255 // Printer gesetzt werden 1256 if ( !maJobSetupDeviceName.Equals( pNewDrivData->szDeviceName )) 1257 return FALSE; 1258 1259 // update DC and PS 1260 HDC hDC; 1261 HPS hPS; 1262 if ( !ImplSalCreateInfoPrn( this, pNewDrivData, hDC, hPS ) ) 1263 return FALSE; 1264 1265 // Alten Printer DC/PS zerstoeren 1266 ImplSalDestroyInfoPrn( this ); 1267 1268 // Neue Daten setzen und initialisieren 1269 mhDC = hDC; 1270 mhPS = hPS; 1271 mpGraphics->mhDC = mhDC; 1272 mpGraphics->mhPS = mhPS; 1273 ImplSalInitGraphics( mpGraphics ); 1274 1275 // retrieve current settings from printer driver and store them to system independend data! 1276 ImplFreeFormAndTrayList( this ); 1277 if ( mbDJPSupported ) 1278 ImplGetCurrentSettings( this, pSetupData ); 1279 1280 return TRUE; 1281 } 1282 1283 // ----------------------------------------------------------------------- 1284 1285 sal_Bool Os2SalInfoPrinter::SetData( ULONG nFlags, ImplJobSetup* pSetupData ) 1286 { 1287 // needs DJP support 1288 if ( !mbDJPSupported ) 1289 return FALSE; 1290 1291 PDRIVDATA pDrivData = ImplPrnDrivData( pSetupData ); 1292 1293 if ( !pDrivData ) 1294 return FALSE; 1295 1296 sal_Bool bOK = FALSE; 1297 1298 // set orientation 1299 if ( nFlags & SAL_JOBSET_ORIENTATION ) 1300 { 1301 if ( ImplSetOrientation( mhDC, pDrivData, pSetupData->meOrientation ) ) 1302 bOK = TRUE; 1303 } 1304 1305 // set paper size 1306 if ( nFlags & SAL_JOBSET_PAPERSIZE ) 1307 { 1308 // Papierformat ermitteln 1309 DJPT_PAPERSIZE nOS2PaperFormat; 1310 switch ( pSetupData->mePaperFormat ) 1311 { 1312 case PAPER_A3: 1313 nOS2PaperFormat = DJP_PSI_A3; 1314 break; 1315 1316 case PAPER_A4: 1317 nOS2PaperFormat = DJP_PSI_A4; 1318 break; 1319 1320 case PAPER_A5: 1321 nOS2PaperFormat = DJP_PSI_A5; 1322 break; 1323 1324 case PAPER_B4_JIS: 1325 nOS2PaperFormat = DJP_PSI_B4; 1326 break; 1327 1328 case PAPER_B5_JIS: 1329 nOS2PaperFormat = DJP_PSI_B5; 1330 break; 1331 1332 case PAPER_LETTER: 1333 nOS2PaperFormat = DJP_PSI_LETTER; 1334 break; 1335 1336 case PAPER_LEGAL: 1337 nOS2PaperFormat = DJP_PSI_LEGAL; 1338 break; 1339 1340 case PAPER_TABLOID: 1341 nOS2PaperFormat = DJP_PSI_TABLOID; 1342 break; 1343 1344 default: 1345 { 1346 nOS2PaperFormat = DJP_PSI_NONE; 1347 // OS2 rechnet in Millimetern 1348 long nPaperWidth = pSetupData->mnPaperWidth / 100; 1349 long nPaperHeight = pSetupData->mnPaperHeight / 100; 1350 // Ansonsten ueber die Papiergroesse suchen 1351 for( int i = 0; i < mnFormCount; i++ ) 1352 { 1353 ImplFormInfo* pFormInfo = mpFormArray[i]; 1354 if ( ImplPaperSizeEqual( nPaperWidth, nPaperHeight, 1355 pFormInfo->mnPaperWidth, pFormInfo->mnPaperHeight ) ) 1356 { 1357 nOS2PaperFormat = pFormInfo->mnId; 1358 break; 1359 } 1360 } 1361 } 1362 break; 1363 } 1364 1365 if ( nOS2PaperFormat != DJP_PSI_NONE ) 1366 { 1367 if ( ImplSetPaperSize( mhDC, pDrivData, nOS2PaperFormat ) ) 1368 bOK = TRUE; 1369 } 1370 } 1371 1372 // set paper tray 1373 if ( (nFlags & SAL_JOBSET_PAPERBIN) && (pSetupData->mnPaperBin < mnTrayCount) ) 1374 { 1375 if ( ImplSetPaperBin( mhDC, pDrivData, 1376 mpTrayArray[pSetupData->mnPaperBin] ) ) 1377 bOK = TRUE; 1378 } 1379 1380 if ( bOK ) 1381 { 1382 ImplUpdateSetupData( pDrivData, pSetupData ); 1383 1384 // query current driver settings 1385 ImplFreeFormAndTrayList( this ); 1386 if ( ImplGetCurrentSettings( this, pSetupData ) ) 1387 { 1388 // update DC and PS 1389 HDC hDC; 1390 HPS hPS; 1391 if ( ImplSalCreateInfoPrn( this, (PDRIVDATA)(pSetupData->mpDriverData), hDC, hPS ) ) 1392 { 1393 // Alten Printer DC/PS zerstoeren 1394 ImplSalDestroyInfoPrn( this ); 1395 1396 // Neue Daten setzen und initialisieren 1397 mhDC = hDC; 1398 mhPS = hPS; 1399 mpGraphics->mhDC = mhDC; 1400 mpGraphics->mhPS = mhPS; 1401 ImplSalInitGraphics( mpGraphics ); 1402 } 1403 else 1404 bOK = FALSE; 1405 } 1406 else 1407 bOK = FALSE; 1408 } 1409 1410 return bOK; 1411 } 1412 1413 // ----------------------------------------------------------------------- 1414 1415 ULONG Os2SalInfoPrinter::GetPaperBinCount( const ImplJobSetup* pJobSetup ) 1416 { 1417 if ( !mbDJPSupported ) 1418 return 1; 1419 1420 // init paperbinlist if empty 1421 if ( !mnTrayCount ) 1422 ImplGetFormAndTrayList( this, pJobSetup ); 1423 1424 // Wir haben immer einen PaperTray und wenn, das eben einen ohne 1425 // Namen 1426 if ( !mnTrayCount ) 1427 return 1; 1428 else 1429 return mnTrayCount; 1430 } 1431 1432 // ----------------------------------------------------------------------- 1433 1434 XubString Os2SalInfoPrinter::GetPaperBinName( const ImplJobSetup* pJobSetup, 1435 ULONG nPaperBin ) 1436 { 1437 XubString aPaperBinName; 1438 1439 if ( mbDJPSupported ) 1440 { 1441 // init paperbinlist if empty 1442 if ( !mnTrayCount ) 1443 ImplGetFormAndTrayList( this, pJobSetup ); 1444 1445 if ( nPaperBin < mnTrayCount ) 1446 aPaperBinName = ::rtl::OStringToOUString (mpTrayArray[nPaperBin]->maDisplayName, gsl_getSystemTextEncoding()); 1447 } 1448 1449 return aPaperBinName; 1450 } 1451 1452 // ----------------------------------------------------------------------- 1453 1454 ULONG Os2SalInfoPrinter::GetCapabilities( const ImplJobSetup*, USHORT nType ) 1455 { 1456 switch ( nType ) 1457 { 1458 case PRINTER_CAPABILITIES_SUPPORTDIALOG: 1459 return TRUE; 1460 case PRINTER_CAPABILITIES_COPIES: 1461 return 0xFFFF; 1462 case PRINTER_CAPABILITIES_COLLATECOPIES: 1463 return 0; 1464 case PRINTER_CAPABILITIES_SETORIENTATION: 1465 case PRINTER_CAPABILITIES_SETPAPERBIN: 1466 case PRINTER_CAPABILITIES_SETPAPERSIZE: 1467 case PRINTER_CAPABILITIES_SETPAPER: 1468 return mbDJPSupported; 1469 } 1470 1471 return 0; 1472 } 1473 1474 // ----------------------------------------------------------------------- 1475 1476 void Os2SalInfoPrinter::GetPageInfo( const ImplJobSetup*, 1477 long& rOutWidth, long& rOutHeight, 1478 long& rPageOffX, long& rPageOffY, 1479 long& rPageWidth, long& rPageHeight ) 1480 { 1481 HDC hDC = mhDC; 1482 1483 // search current form 1484 HCINFO aInfo; 1485 int nForms = DevQueryHardcopyCaps( hDC, 0, 0, &aInfo ); 1486 for( int i = 0; i < nForms; i++ ) 1487 { 1488 if ( DevQueryHardcopyCaps( hDC, i, 1, &aInfo ) >= 0 ) 1489 { 1490 if ( aInfo.flAttributes & HCAPS_CURRENT ) 1491 { 1492 // query resolution 1493 long nXResolution; 1494 long nYResolution; 1495 DevQueryCaps( hDC, CAPS_HORIZONTAL_RESOLUTION, 1, &nXResolution ); 1496 DevQueryCaps( hDC, CAPS_VERTICAL_RESOLUTION, 1, &nYResolution ); 1497 rPageOffX = aInfo.xLeftClip * nXResolution / 1000; 1498 rPageOffY = (aInfo.cy-aInfo.yTopClip) * nYResolution / 1000; 1499 rPageWidth = aInfo.cx * nXResolution / 1000; 1500 rPageHeight = aInfo.cy * nYResolution / 1000; 1501 rOutWidth = aInfo.xPels; 1502 rOutHeight = aInfo.yPels; 1503 return; 1504 } 1505 } 1506 } 1507 1508 // use device caps if no form selected/found 1509 long lCapsWidth = 0; 1510 long lCapsHeight = 0; 1511 DevQueryCaps( hDC, CAPS_WIDTH, 1L, &lCapsWidth ); 1512 DevQueryCaps( hDC, CAPS_HEIGHT, 1L, &lCapsHeight ); 1513 rPageOffX = 0; 1514 rPageOffY = 0; 1515 rOutWidth = lCapsWidth; 1516 rOutHeight = lCapsHeight; 1517 rPageWidth = rOutWidth; 1518 rPageHeight = rOutHeight; 1519 } 1520 1521 // ======================================================================= 1522 1523 static sal_Bool ImplIsDriverPrintDJPEnabled( HDC hDC ) 1524 { 1525 #ifdef NO_DJP 1526 return FALSE; 1527 #else 1528 // Ueber OS2-Ini kann DJP disablte werden 1529 if ( !PrfQueryProfileInt( HINI_PROFILE, SAL_PROFILE_APPNAME, SAL_PROFILE_PRINTDJP, 1 ) ) 1530 return FALSE; 1531 1532 // Testen, ob DJP-Interface am Drucker vorhanden 1533 LONG lQuery; 1534 APIRET rc; 1535 1536 lQuery = DEVESC_QUERYSIZE; 1537 rc = DevEscape( hDC, 1538 DEVESC_QUERYESCSUPPORT, 1539 sizeof( lQuery ), 1540 (PBYTE)&lQuery, 1541 0, 1542 (PBYTE)NULL ); 1543 if ( DEV_OK != rc ) 1544 return FALSE; 1545 1546 return TRUE; 1547 #endif 1548 } 1549 1550 // ======================================================================= 1551 1552 SalPrinter* Os2SalInstance::CreatePrinter( SalInfoPrinter* pInfoPrinter ) 1553 { 1554 Os2SalPrinter* pPrinter = new Os2SalPrinter; 1555 pPrinter->mpInfoPrinter = static_cast<Os2SalInfoPrinter*>(pInfoPrinter); 1556 return pPrinter; 1557 } 1558 1559 // ----------------------------------------------------------------------- 1560 1561 void Os2SalInstance::DestroyPrinter( SalPrinter* pPrinter ) 1562 { 1563 delete pPrinter; 1564 } 1565 1566 // ======================================================================= 1567 1568 Os2SalPrinter::Os2SalPrinter() 1569 { 1570 mhDC = 0; 1571 mhPS = 0; 1572 mpGraphics = NULL; 1573 mbAbort = FALSE; 1574 mbPrintDJPSupported = FALSE; 1575 } 1576 1577 // ----------------------------------------------------------------------- 1578 1579 Os2SalPrinter::~Os2SalPrinter() 1580 { 1581 } 1582 1583 // ----------------------------------------------------------------------- 1584 1585 sal_Bool Os2SalPrinter::StartJob( const XubString* pFileName, 1586 const XubString& rJobName, 1587 const XubString& rAppName, 1588 ULONG nCopies, 1589 bool bCollate, 1590 bool bDirect, 1591 ImplJobSetup* pSetupData ) 1592 { 1593 DEVOPENSTRUC aDevOpenStruc; 1594 LONG lType; 1595 APIRET rc; 1596 1597 // prepare queue information 1598 memset( &aDevOpenStruc, 0, sizeof( aDevOpenStruc ) ); 1599 aDevOpenStruc.pszDriverName = (PSZ)(mpInfoPrinter->maDriverName.GetBuffer()); 1600 1601 // print into file? 1602 if ( pFileName ) 1603 { 1604 aDevOpenStruc.pszLogAddress = (PSZ)pFileName->GetBuffer(); 1605 aDevOpenStruc.pszDataType = "PM_Q_RAW"; 1606 lType = OD_DIRECT; 1607 } 1608 else 1609 { 1610 aDevOpenStruc.pszLogAddress = (PSZ)(mpInfoPrinter->maName.GetBuffer()); 1611 if ( PrfQueryProfileInt( HINI_PROFILE, SAL_PROFILE_APPNAME, SAL_PROFILE_PRINTRAW, 0 ) ) 1612 aDevOpenStruc.pszDataType = "PM_Q_RAW"; 1613 else 1614 aDevOpenStruc.pszDataType = "PM_Q_STD"; 1615 lType = OD_QUEUED; 1616 } 1617 1618 #if 0 // YD FIXME 1619 // Set comment (AppName nur bis zum 1. Space-Zeichen nehmen) 1620 const xub_Unicode* pComment = rAppName; 1621 USHORT nCommentLen = 0; 1622 memset( maCommentBuf, 0, sizeof( maCommentBuf ) ); 1623 while ( (nCommentLen < 32) && 1624 (((*pComment >= 'a') && (*pComment <= 'z')) || 1625 ((*pComment >= 'A') && (*pComment <= 'Z')) || 1626 ((*pComment >= '0') && (*pComment <= '9')) || 1627 (*pComment == '-'))) 1628 { 1629 maCommentBuf[nCommentLen] = (char)(*pComment); 1630 nCommentLen++; 1631 pComment++; 1632 } 1633 aDevOpenStruc.pszComment = (PSZ)maCommentBuf; 1634 #endif 1635 ByteString jobName( rJobName, gsl_getSystemTextEncoding()); 1636 aDevOpenStruc.pszComment = (PSZ)jobName.GetBuffer(); 1637 1638 // Kopien 1639 if ( nCopies > 1 ) 1640 { 1641 // OS2 kann maximal 999 Kopien 1642 if ( nCopies > 999 ) 1643 nCopies = 999; 1644 sprintf( maCopyBuf, "COP=%d", nCopies); 1645 aDevOpenStruc.pszQueueProcParams = (PSZ)maCopyBuf; 1646 } 1647 1648 // open device context 1649 SalData* pSalData = GetSalData(); 1650 HAB hAB = pSalData->mhAB; 1651 aDevOpenStruc.pdriv = (PDRIVDATA)pSetupData->mpDriverData; 1652 mhDC = DevOpenDC( hAB, 1653 lType, 1654 "*", 1655 7, 1656 (PDEVOPENDATA)&aDevOpenStruc, 1657 0 ); 1658 if ( mhDC == 0 ) 1659 { 1660 ERRORID nLastError = WinGetLastError( hAB ); 1661 if ( (nLastError & 0xFFFF) == PMERR_SPL_PRINT_ABORT ) 1662 mnError = SAL_PRINTER_ERROR_ABORT; 1663 else 1664 mnError = SAL_PRINTER_ERROR_GENERALERROR; 1665 return FALSE; 1666 } 1667 1668 // open presentation space 1669 SIZEL sizel; 1670 sizel.cx = 0; 1671 sizel.cy = 0; 1672 mhPS = Ft2CreatePS( hAB, mhDC, &sizel, GPIA_ASSOC | GPIT_MICRO | PU_PELS ); 1673 if ( !mhPS ) 1674 { 1675 DevCloseDC( mhDC ); 1676 mnError = SAL_PRINTER_ERROR_GENERALERROR; 1677 return NULL; 1678 } 1679 1680 // Can we print with DJP 1681 mbPrintDJPSupported = ImplIsDriverPrintDJPEnabled( mhDC ); 1682 1683 // JobName ermitteln und Job starten 1684 PSZ pszJobName = NULL; 1685 int nJobNameLen = 0; 1686 if ( jobName.Len() > 0 ) 1687 { 1688 pszJobName = (PSZ)jobName.GetBuffer(); 1689 nJobNameLen = jobName.Len(); 1690 } 1691 rc = DevEscape( mhDC, 1692 DEVESC_STARTDOC, 1693 nJobNameLen, (PBYTE)pszJobName, 1694 0, (PBYTE)NULL ); 1695 1696 if ( rc != DEV_OK ) 1697 { 1698 ERRORID nLastError = WinGetLastError( hAB ); 1699 if ( (nLastError & 0xFFFF) == PMERR_SPL_PRINT_ABORT ) 1700 mnError = SAL_PRINTER_ERROR_ABORT; 1701 else 1702 mnError = SAL_PRINTER_ERROR_GENERALERROR; 1703 Ft2Associate( mhPS, NULL ); 1704 Ft2DestroyPS( mhPS ); 1705 DevCloseDC( mhDC ); 1706 return FALSE; 1707 } 1708 1709 // init for first page 1710 mbFirstPage = TRUE; 1711 mnError = 0; 1712 1713 return TRUE; 1714 } 1715 1716 // ----------------------------------------------------------------------- 1717 1718 sal_Bool Os2SalPrinter::EndJob() 1719 { 1720 APIRET rc; 1721 rc = DevEscape( mhDC, 1722 DEVESC_ENDDOC, 1723 0, NULL, 1724 0, NULL); 1725 1726 // destroy presentation space and device context 1727 Ft2Associate( mhPS, NULL ); 1728 Ft2DestroyPS( mhPS ); 1729 DevCloseDC( mhDC ); 1730 return TRUE; 1731 } 1732 1733 // ----------------------------------------------------------------------- 1734 1735 sal_Bool Os2SalPrinter::AbortJob() 1736 { 1737 APIRET rc; 1738 1739 rc = DevEscape( mhDC, 1740 DEVESC_ABORTDOC, 1741 0, NULL, 1742 0, NULL ); 1743 1744 // destroy SalGraphics 1745 if ( mpGraphics ) 1746 { 1747 ImplSalDeInitGraphics( mpGraphics ); 1748 delete mpGraphics; 1749 mpGraphics = NULL; 1750 } 1751 1752 // destroy presentation space and device context 1753 Ft2Associate( mhPS, NULL ); 1754 Ft2DestroyPS( mhPS ); 1755 DevCloseDC( mhDC ); 1756 return TRUE; 1757 } 1758 1759 // ----------------------------------------------------------------------- 1760 1761 SalGraphics* Os2SalPrinter::StartPage( ImplJobSetup* pSetupData, sal_Bool bNewJobSetup ) 1762 { 1763 APIRET rc; 1764 1765 if ( mbFirstPage ) 1766 mbFirstPage = FALSE; 1767 else 1768 { 1769 PBYTE pJobData; 1770 LONG nJobDataSize; 1771 LONG nEscape; 1772 if ( mbPrintDJPSupported && bNewJobSetup ) 1773 { 1774 nEscape = DEVESC_NEWFRAME_WPROP; 1775 nJobDataSize = ((PDRIVDATA)(pSetupData->mpDriverData))->cb; 1776 pJobData = (PBYTE)(pSetupData->mpDriverData); 1777 } 1778 else 1779 { 1780 nEscape = DEVESC_NEWFRAME; 1781 nJobDataSize = 0; 1782 pJobData = NULL; 1783 } 1784 rc = DevEscape( mhDC, 1785 nEscape, 1786 0, NULL, 1787 &nJobDataSize, pJobData ); 1788 1789 if ( rc != DEV_OK ) 1790 { 1791 DevEscape( mhDC, DEVESC_ENDDOC, 0, NULL, 0, NULL); 1792 Ft2Associate( mhPS, NULL ); 1793 Ft2DestroyPS( mhPS ); 1794 DevCloseDC( mhDC ); 1795 mnError = SAL_PRINTER_ERROR_GENERALERROR; 1796 return NULL; 1797 } 1798 } 1799 1800 // create SalGraphics with copy of hPS 1801 Os2SalGraphics* pGraphics = new Os2SalGraphics; 1802 pGraphics->mhDC = mhDC; 1803 pGraphics->mhPS = mhPS; 1804 pGraphics->mhWnd = 0; 1805 pGraphics->mbPrinter = TRUE; 1806 pGraphics->mbVirDev = FALSE; 1807 pGraphics->mbWindow = FALSE; 1808 pGraphics->mbScreen = FALSE; 1809 pGraphics->mnHeight = 0; 1810 // search current form for actual page height 1811 HCINFO aInfo; 1812 int nForms = DevQueryHardcopyCaps( mhDC, 0, 0, &aInfo ); 1813 for( int i = 0; i < nForms; i++ ) 1814 { 1815 if ( DevQueryHardcopyCaps( mhDC, i, 1, &aInfo ) >= 0 ) 1816 { 1817 if ( aInfo.flAttributes & HCAPS_CURRENT ) 1818 pGraphics->mnHeight = aInfo.yPels; 1819 } 1820 } 1821 // use device caps if no form selected/found 1822 if ( !pGraphics->mnHeight ) 1823 DevQueryCaps( mhDC, CAPS_HEIGHT, 1L, &pGraphics->mnHeight ); 1824 1825 ImplSalInitGraphics( pGraphics ); 1826 mpGraphics = pGraphics; 1827 1828 return pGraphics; 1829 } 1830 1831 // ----------------------------------------------------------------------- 1832 1833 sal_Bool Os2SalPrinter::EndPage() 1834 { 1835 if ( mpGraphics ) 1836 { 1837 // destroy SalGraphics 1838 ImplSalDeInitGraphics( mpGraphics ); 1839 delete mpGraphics; 1840 mpGraphics = NULL; 1841 } 1842 1843 return TRUE; 1844 } 1845 1846 // ----------------------------------------------------------------------- 1847 1848 ULONG Os2SalPrinter::GetErrorCode() 1849 { 1850 return mnError; 1851 } 1852 1853 void Os2SalInfoPrinter::InitPaperFormats( const ImplJobSetup* pSetupData ) 1854 { 1855 printf("Os2SalInfoPrinter::InitPaperFormats\n"); 1856 } 1857 int Os2SalInfoPrinter::GetLandscapeAngle( const ImplJobSetup* pSetupData ) 1858 { 1859 printf("Os2SalInfoPrinter::GetLandscapeAngle\n"); 1860 return 0; 1861 } 1862 1863