Jump to content

DEVESC_SETJOBPROPERTIES

From EDM2
Revision as of 00:36, 12 July 2025 by Martini (talk | contribs) (Created page with "{{DISPLAYTITLE:DEVESC_SETJOBPROPERTIES}} GreEscape DEVESC_SETJOBPROPERTIES writes the specified job property types and values into the job properties structure that is passed in. ;Simulation support: This function is mandatory for all drivers and must be implemented in order to have a valid OS/2 hardcopy driver. ==Syntax== GreEscape(hdc, lEscape, cInCount, pInData, pcOutCount, pOutData, pInstance, lFunction); ==Parameters== ;''hdc'' (HDC) - input: Device context...")
(diff) ← Older revision | Latest revision (diff) | Newer revision → (diff)

GreEscape DEVESC_SETJOBPROPERTIES writes the specified job property types and values into the job properties structure that is passed in.

Simulation support
This function is mandatory for all drivers and must be implemented in order to have a valid OS/2 hardcopy driver.

Syntax

GreEscape(hdc, lEscape, cInCount, pInData, pcOutCount, pOutData, pInstance, lFunction);

Parameters

hdc (HDC) - input
Device context handle.
lEscape (LONG) - input
DEVESC_SETJOBPROPERTIES escape code.
cInCount (LONG) - input
Number of bytes pointed to by pInData.
pInData (PBYTE) - output
Pointer to a list of DJP_ITEM data structures. The end of the list is indicated by a DJP_ITEM data structure that has DJP_NONE as its ulProperty value.
pcOutCount (PLONG) - input
Number of bytes pointed to by pOutData.
pOutData (PLONG) - input
Pointer to the printer driver's job properties structure as returned by SplQueryQueue. On output, the job properties are changed.
pInstance (PVOID) - input
Pointer to instance data.
lFunction (ULONG) - input
High-order WORD=flags; low-order WORD=NGreEscape.

Returns

rc (LONG) - returns
Return Code.
The handling routine returns:
DEV_OK
Successful
DEV_PROP_BUF_TOO_SMALL
Job properties buffer was too small to contain the proper job properties data. The buffer will not be updated.
DEV_INV_INP_JOBPROPERTIES
Invalid job properties were passed in. The driver changed them to default values. This is an error and the item buffer will not be updated.
DEV_WARNING
One or more of the DJP_ITEMs has an error in the lType field.
Valid input for lType
DJP_CURRENT
The application requests the current value to be changed in the input job properties.
Valid output for lType
DJP_CURRENT
Unchanged; successful query.
DJP_ERROR_NOT_SUPPORTED
The driver does not support the value in the ulProperty field of the DJP_ITEMs data structure.
DEVESC_ERROR_INV_PARMS
The value in the ulValue field of the DJP_ITEMs data structure is not valid.
DJP_ERROR_OUT_OF_RANGE
The value in ulValue is not in the valid range for the specified property.
DJP_ERROR
Error

Remarks

DEVESC_SETJOBPROPERTIES is used to set information in the printer's job properties structure. This structure is known only to the printer presentation driver, and this escape is the only way for an application to set values inside the structure.

Since DEVESC_SETJOBPROPERTIES is new, applications will call GreEscape DEVESC_QUERYESCSUPPORT to determine if you support this DevEscape.

The DevEscape path has a handle to a device context (HDC) that should already have printer property information associated with the HDC. Job property information may change or may be dependent upon the printer property information in the HDC. In that case, if an application passes job properties for a different device or for a different spooler printer name, then misleading information will be returned.

You should test the input job properties to make sure that they are valid. This includes passing tests such as whether they contain your driver's signature string, whether the device name is yours, and whether the values are within proper ranges (only landscape or portrait). If these tests fail, then fail the call.

Refer to Dynamic Job Properties for related information.

Source Code Sample

Declaration:

#define INCL_DEV
#define INCL_DEVDJP
#include <os2.h>

HDC      hdc;         /* Device context handle. */
LONG     lEscape;     /* DEVESC_SETJOBPROPERTIES escape code. */
LONG     cInCount;    /* Number of bytes pointed to by pInData. */
PBYTE    pInData;     /* Pointer to a list of DJP_ITEM data structures. */
PLONG    pcOutCount;  /* Number of bytes pointed to by pOutData. */
PLONG    pOutData;    /* Pointer to the printer driver's job properties structure. */
PVOID    pInstance;   /* Pointer to instance data. */
ULONG    lFunction;   /* High-order WORD=flags; low-order WORD=NGreEscape. */
LONG     rc;          /* Return Code. */

rc = GreEscape(hdc, lEscape, cInCount, pInData,
       pcOutCount, pOutData, pInstance, lFunction);

Sample Implementation:

LONG ENGENTRY Escape (HDC       hdc,
                      LONG      lEscape,
                      LONG      cInCount,
                      PBYTE     pInData,
                      PLONG     pcOutCount,
                      PBYTE     pOutData,
                      PDDC      pddc,
                      ULONG     ulFunction)
{
   switch (lEscape)
   {
   case DEVESC_SETJOBPROPERTIES:
   {
      INT            cbQueries   = cInCount;
      PBYTE          pbQueries   = pInData;
      PDJP_ITEM      pISet       = (PDJP_ITEM)pbQueries;
      BOOL           fError      = FALSE;
      ULONG          ulMaxSize;

      if (GRE_234 > globals.ulGreVersion)
      {
         assertstring ("Not supported on pre-DAX engine!\n");
         lrc = DEVESC_NOTIMPLEMENTED;
         break;
      }

      pGoodDrivData = ReturnDriverData (pddc->pdb,
                                        pdi,
                                        pddc->pdb->hmcbHeap,
                                        pDrivData,
                                        pddc->pdb->pszPrinterName,
                                        TRUE,
                                        pDevice,
                                        pDriver);
      assertF (pGoodDrivData);

      /* Is the size of the input driver data is not the same as
      ** the size of our good data?
      */
      if (pDrivData->cb != pGoodDrivData->cb)
         lrc = DEV_PROP_BUF_TOO_SMALL;

      /* Or, if the two don't compare, then fail the call.
      */
      if (0 != memcmp (pDrivData, pGoodDrivData, pGoodDrivData->cb))
         lrc = DEV_INV_INP_JOBPROPERTIES;

      // Update the job properties with the input set list
      do
      {
         DBPRINTF (("Set '%s'/%d.  Query type '%s'/%d. Simple value = %d\n",
                    pszProperty (pISet->ulProperty),
                    pISet->ulProperty,
                    pszType (pISet->lType),
                    pISet->lType,
                    pISet->ulValue));

         switch (pISet->ulProperty)
         {
         case DJP_SJ_ORIENTATION:
         {
            if (pISet->ulValue == DJP_ORI_PORTRAIT)
            {
               pJobProp->ulOrientation = ORIENTATION_PORTRAIT;
            }
            else if (pISet->ulValue == DJP_ORI_LANDSCAPE)
            {
               pJobProp->ulOrientation = ORIENTATION_LANDSCAPE;
            }
            else
            {
               pISet->lType = DJP_ERROR_OUT_OF_RANGE;
            }
            break;
         }

         case DJP_CJ_RESOLUTION:
         {
            PDJPT_RESOLUTION   pRes         = DJP_ELEMENTP (*pISet, DJPT_RESOLUTION);
            PRESINFO           pResInfo     = pDriver->pRES;
            ULONG              ulNumDefined = pDriver->ulNumRes;
            PULONG             pulResDevice = pDevice->pulRES;
            ULONG              ulNumDevice  = pDevice->usNumRes;
            BOOL               fFound       = FALSE;
            register INT       i, j;

            for (i = 0; !fFound && i < ulNumDevice; i++, pulResDevice++)
            {
               for (j = 0; j < ulNumDefined; j++)
               {
                  if (pResInfo[j].ulResID == *pulResDevice)
                  {
                     if (pRes->usXResolution == pResInfo[j].ulXRes &&
                         pRes->usYResolution == pResInfo[j].ulYRes  )
                     {
                        fFound = TRUE;
                        pJobProp->ulDefResID = *pulResDevice;
                        break;
                     }
                  }
               }
            }

            if (!fFound)
               pISet->lType = DJP_ERROR_OUT_OF_RANGE;
            break;
         }

         case DJP_SJ_BITSPERPEL:
         case DJP_SJ_COLOR:
         {
            PPRINTMODE       pPrintMode    = pDriver->pPrintModes;
            ULONG            ulNumDefined  = pDriver->ulNumPrintModes;
            PULONG           pulPrintModes = pDevice->pulPrintModes;
            ULONG            ulNumDevice   = pDevice->usNumPrintModes;
            PDJPT_BITSPERPEL pTmp          = DJP_ELEMENTP (*pISet, DJPT_BITSPERPEL);
            BOOL             fFound        = FALSE;
            register INT     i, j;

            for (i = 0; !fFound && i < ulNumDevice; i++, pulPrintModes++)
            {
               fFound = FALSE;

               for (j = 0; j < ulNumDefined; j++)
               {
                  if (pPrintMode[j].ulPrintModeID == *pulPrintModes)
                  {
                     if (DJP_SJ_BITSPERPEL == pISet->ulProperty)
                     {
                        if (*pTmp == pPrintMode[j].usLogBitCount)
                        {
                           pJobProp->ulDefPrintModeID = *pulPrintModes;
                           fFound = TRUE;
                           break;
                        }
                     }
                     else
                     {
                        if (((1     == pPrintMode[j].usBitsPerPel) &&
                             (*pTmp == DJP_CLR_MONOCHROME)          ) ||
                            ((1     <  pPrintMode[j].usBitsPerPel) &&
                             (*pTmp == DJP_CLR_COLOR)               )  )
                        {
                           pJobProp->ulDefPrintModeID = *pulPrintModes;
                           fFound = TRUE;
                           break;
                        }
                     }
                  }
               }
            }

            if (!fFound)
               pISet->lType = DJP_ERROR_OUT_OF_RANGE;
            break;
         }

         case DJP_SJ_PAPERSIZE:
         {
            ULONG           ulNumDefined = pDevice->ulNumForms;
            PFORMINFO2      pFormInfo    = pDevice->pFORMS;
            PDJPT_PAPERSIZE pSize        = DJP_ELEMENTP (*pISet, DJPT_PAPERSIZE);
            BOOL            fFound       = FALSE;
            LONG            lRet;
            register INT i;

            for (i = 0; i < ulNumDefined; i++)
            {
               lRet = pFormInfo[i].ulDJPid;

               if (DJP_PSI_NONE != lRet && *pSize == lRet)
               {
                  fFound = TRUE;
                  break;
               }
            }

            if (fFound)
            {
               ULONG  ulDefaultConnID  = pJobProp->ulDefConnID,
                      ulDefaultFormID  = 0,
                      ulDefaultTrayID  = 0,
                      ulDefaultMediaID = 0;
               BOOL   bOK;

               // Ask for the current connection id
               bOK = GetIDsFromConnID (pDriver,
                                       pDevice,
                                       ulDefaultConnID,
                                       &ulDefaultTrayID,
                                       &ulDefaultFormID,
                                       &ulDefaultMediaID);

               if (bOK)
                  // Get a new connection id
                  bOK = NewConnection (pdb,
                                       pGoodDrivData->szDeviceName,
                                       &ulDefaultConnID,
                                       pFormInfo[i].ulFormID, // Override form
                                       ulDefaultTrayID,
                                       ulDefaultMediaID,
                                       FALSE);                // Dont create a new one!

               // Set it!
               if (bOK)
                  pJobProp->ulDefConnID = ulDefaultConnID;
               else
                  pISet->lType = DJP_ERROR_OUT_OF_RANGE;
            }
            else
            {
               pISet->lType = DJP_ERROR_OUT_OF_RANGE;
            }
            break;
         }

         case DJP_CJ_FORM:
         {
            ULONG           ulNumDefined;
            ULONG           ulNumDevice;
            PDJPT_FORM      pDJPForm     = DJP_ELEMENTP (*pISet, DJPT_FORM);
            PFORMINFO2      pFormInfo    = (PFORMINFO2)NULL;
            PTRAYINFO       pTrayInfo    = (PTRAYINFO)NULL;
            PMEDIAINFO      pMediaInfo   = (PMEDIAINFO)NULL;
            CHAR            szTempName[32];
            BOOL            bOK;
            register INT    i, j;

            ulNumDevice = pDevice->ulNumForms;
            for (i = 0; i < ulNumDevice; i++)
            {
               FormNameFromID (pDriver,
                               pDevice,
                               szTempName,
                               pDevice->pFORMS[i].ulFormID);

               if (0 == strcmp (pDJPForm->szFormname, szTempName))
               {
                  pFormInfo = (PFORMINFO2) &pDevice->pFORMS[i];
                  break;
               }
            }

            if (pDJPForm->szTrayname[0])
            {
               ulNumDevice  = pDevice->usNumTrays;
               ulNumDefined = pDriver->ulNumTrays;

               for (i = 0; i < ulNumDefined && !pTrayInfo; i++)
               {
                  for (j = 0; j < ulNumDevice; j++)
                  {
                     if (pDriver->pTRAYS[i].ulTrayID == pDevice->pulTRAYS[j])
                     {
                        TrayNameFromID (pDriver,
                                        pDevice,
                                        szTempName,
                                        pDriver->pTRAYS[i].ulTrayID);

                        if (0 == strcmp (pDJPForm->szTrayname, szTempName))
                        {
                           pTrayInfo = (PTRAYINFO) &pDriver->pTRAYS[i];
                           break;
                        }
                     }
                  }
               }
            }

            if (pDJPForm->szMedianame[0])
            {
               ulNumDevice  = pDevice->ulNumMedias;
               ulNumDefined = pDriver->ulNumMedias;

               for (i = 0; i < ulNumDefined && !pMediaInfo; i++)
               {
                  for (j = 0; j < ulNumDevice; j++)
                  {
                     if (pDriver->pMEDIAS[i].ulMediaID == pDevice->pulMEDIAS[j])
                     {
                        MediaNameFromID (pDriver,
                                         pDevice,
                                         szTempName,
                                         pDriver->pMEDIAS[i].ulMediaID);

                        if (0 == strcmp (pDJPForm->szMedianame, szTempName))
                        {
                           pMediaInfo = (PMEDIAINFO) &pDriver->pMEDIAS[i];
                           break;
                        }
                     }
                  }
               }
            }

            if (pFormInfo)
            {
               ULONG  ulDefaultConnID  = pJobProp->ulDefConnID,
                      ulDefaultFormID  = 0,
                      ulDefaultTrayID  = 0,
                      ulDefaultMediaID = 0;

               // Ask for the current connection id
               bOK = GetIDsFromConnID (pDriver,
                                       pDevice,
                                       ulDefaultConnID,
                                       &ulDefaultTrayID,
                                       &ulDefaultFormID,
                                       &ulDefaultMediaID);

               ulDefaultFormID = pFormInfo->ulFormID;
               if (pTrayInfo)
                  ulDefaultTrayID = pTrayInfo->ulTrayID;
               if (pMediaInfo)
                  ulDefaultMediaID = pMediaInfo->ulMediaID;

               bOK = NewConnection (pdb,
                                    pGoodDrivData->szDeviceName,
                                    &ulDefaultConnID,
                                    ulDefaultFormID,
                                    ulDefaultTrayID,
                                    ulDefaultMediaID,
                                    FALSE);           // Dont create a new one!
            }
            else
               bOK = FALSE;

            if (bOK)
               pJobProp->ulDefConnID = ulDefaultConnID;
            else
               pISet->lType = DJP_ERROR_OUT_OF_RANGE;
            break;
         }

         case DJP_SJ_COPIES:
         {
            if (0 < pISet->ulValue && pISet->ulValue < 100)
               pJobProp->ulCopies = pISet->ulValue;
            else
               pISet->lType = DJP_ERROR_OUT_OF_RANGE;
            break;
         }

         case DJP_SJ_PRINTQUALITY:
         case DJP_SJ_TRAYTYPE:
         case DJP_SJ_MEDIA:
         case DJP_SJ_MEDIA_COLOR:
         case DJP_CJ_MIXEDFORMS:
         case DJP_SJ_FONTDOWNLOADING:
         case DJP_SJ_DUPLEX:
         case DJP_SJ_COLLATE:
         case DJP_SJ_FEED:
         case DJP_SJ_SCALING:
         case DJP_SJ_FORMFEEDCONTROL:
         case DJP_SJ_N_UP:
         default:
            pISet->lType = DJP_ERROR_NOT_SUPPORTED;
            DBPRINTF (("Unknow set '%s' = %d!\n",
                        pszProperty (pISet->ulProperty),
                        pISet->ulProperty));
            break;
         }

         // Move to the set item
         pISet = DJP_NEXT_STRUCTP (pISet);

      } while (pISet->ulProperty != DJP_NONE);

      cbDrivData = cbParm2;
      pDrivData  = (PDRIVDATA)pbParm2;

      /* Copy the updated job properties onto the user's job properties
      */
      ulMaxSize = min (pGoodDrivData->cb, cbDrivData);
      memcpy (pDrivData, pGoodDrivData, ulMaxSize);
      pDrivData->cb = ulMaxSize;

      if (fError)
      {
         GplErrSetWarning (PMERR_DATATYPE_ENTRY_INVALID);
         ulrc = DEV_ERROR;
      }
      else
      {
         ulrc = DEV_OK;
      }
      break;
   }
   }

   return lrc;
}