/*DDK*************************************************************************/
/*                                                                           */
/* COPYRIGHT    Copyright (C) 1995 IBM Corporation                           */
/*                                                                           */
/*    The following IBM OS/2 WARP source code is provided to you solely for  */
/*    the purpose of assisting you in your development of OS/2 WARP device   */
/*    drivers. You may use this code in accordance with the IBM License      */
/*    Agreement provided in the IBM Device Driver Source Kit for OS/2. This  */
/*    Copyright statement may not be removed.                                */
/*                                                                           */
/*****************************************************************************/

/**********************************************************************/
/*                                                                    */
/*   Module          = EDDTESUB                                       */
/*                                                                    */
/*   Description     = Display Device Driver minor function handlers  */
/*                     subroutines for Fonts                          */
/*                                                                    */
/*   Function        = LocateFont()                                   */
/*                                                                    */
/*   Reference       = Winthorn Functional Specification              */
/*                     Device Driver Interface Specification          */
/*                     Display Device Driver Design Specification     */
/*                                                                    */
/*                                                                    */
/**********************************************************************/

/**********************************************************************/
/*                                                                    */
/* include Display Device Driver constants                            */
/* include Display Device Driver return codes                         */
/* include Display Device Driver types                                */
/* include Display Device Driver trace                                */
/*                                                                    */
/**********************************************************************/


#define INCL_DDIFONTSTRUCS
#define INCL_DDIMISC
#define INCL_GRE_FONTS

#include <eddinclt.h>
#include <edddtypt.h>
#include <eddttypt.h>
#include <eddtextf.h>
#include <eddacone.h>
#include <eddtcone.h>

#ifdef DBCS                                                             /*YOJN*//*YOJN*/
#include <eddjdef.h>                                                    /*YOJN*//*YOJN*/
#include <eddjfm.h>                                                     /*YOJN*/
#include <eddjfont.h>                                                   /*YOJN*//*YOJN*/
#include <eddjcp.h>                                                     /*YOJN*/
#endif                                                                  /*YOJN*//*YOJN*/

extern DDTType          DDT;
#ifdef DBCS                                                             /*YOJN*/
extern PFOCAFONT        pDefaultFont;                                   /*YOJN*/
#else /*DBCS*/                                                          /*YOJN*/
extern PVOID            pDefaultFont;
#endif /*DBCS*/                                                         /*YOJN*/

extern USHORT              usVersion;

#ifdef DBCS                                                             /*YOJN*/
extern USHORT           usDefaultCodePage;                              /*YOJN*/
                                                                        /*YOJN*/
BOOL SelectCodepage( PFOCAFONT pFocaFont,                               /*YOJN*/
                     ULONG ulCodepage,                                  /*YOJN*/
                     PFONTDETAILS pFontDtl );                           /*YOJN*/
#endif /*DBCS*/                                                         /*YOJN*/
/**********************************************************************/
/* Locate whether current font is a FOCAFONT or an AI font and set up */
/* value and pointers in the DC instance data appropriately.          */
/**********************************************************************/

USHORT eddt_LocateFont (VOID)

{
#define TFUNC "eddt_LocateFont"

    /******************************************************************/
    /* Local variables.                                               */
    /******************************************************************/
    USHORT                      usCodepage;
    PFOCAFONT                   pFocaFont;
    PFOCAFONT                   pFontInfo;
    PAIFONT                     pAIFont;
    USHORT                      usTableIndex;

    /******************************************************************/
    /* This is a standard FOCAFONT. (We do not support AA fonts now). */
    /******************************************************************/

    /******************************************************************/
    /* See if the font is "our" default font.                         */
    /******************************************************************/
    if (pdc->DCICurTxtAts.cdef.defSet == 0)
    {
        /**************************************************************/
        /* This is the default font.  Set up a pointer to it.         */
        /**************************************************************/
        pFocaFont = (PFOCAFONT)pDefaultFont;
    }
    else
    {
        /**************************************************************/
        /* This is not the default font.  Take the pointer to the     */
        /* font from the current text attributes.                     */
        /**************************************************************/
        pFocaFont = (PFOCAFONT)pdc->DCICurTxtAts.cdef.defSet;
    }

    /******************************************************************/
    /* See if the font is a default font (ie. LCID value of zero).    */
    /******************************************************************/
    if (pdc->DCICurTxtAts.cbnd.usSet == 0)
    {
        /**************************************************************/
        /* Take the codepage from the DC instance data.               */
        /**************************************************************/
        usCodepage = (USHORT)pdc->DCICodePage;
    }
    else
    {
        /**************************************************************/
        /* Take the codepage from the attribute bundle.               */
        /**************************************************************/
        usCodepage = pdc->DCICurTxtAts.cdef.CodePage;
    }

    pdc->CurrentFont.pFocaFont = pFocaFont;

#ifdef DBCS                                                             /*YOJN*/
    if (!SelectCodepage( pFocaFont,                                     /*YOJN*/
                         (ULONG)usCodepage,                             /*YOJN*/
                         &pdc->CurrentFont ))                           /*YOJN*/
      {                                /* if NO CP is available       *//*YOJN*/
        LogError( PMERR_INV_CODEPAGE );
        return ERROR_ZERO;             /*                             *//*YOJN*/
      }                                /* end of if:                  *//*YOJN*/
                                                                        /*YOJN*/
    eddj_GetDefaultCodepoint( &pdc->CurrentFont );                      /*YOJN*/
                                       /* get SBCS default codepoint  *//*YOJN*/
                                       /* meaningless if font is DBCS *//*YOJN*/
                                       /*   but anyway we will not    *//*YOJN*/
                                       /*   use this value then.      *//*YOJN*/
    pdc->CurrentFont.lMatch = eddj_QueryMatchNum( pFocaFont );          /*YOJN*/
                                       /* save match number since we  *//*YOJN*/
                                       /*   will be asked it many     *//*YOJN*/
                                       /*   times later               *//*YOJN*/
    pdc->CurrentFont.usDbcWidth = 0;   /* common width for 2bytes char*//*YOJN*/
                                       /* (will be used later if DBCS-*//*YOJN*/
                                       /* PROPORTIONAL switch is OFF) *//*YOJN*/
                                       /* 0 means we do not know width*//*YOJN*/
#else                                                                   /*YOJN*/
    /******************************************************************/
    /* Now try to get a codepage vector for the necessary codepage.   */
    /* we can only get a codepage mapping vector (which maps into     */
    /* codepage 850 if the font is actually designed to codepage 850) */
    /******************************************************************/
    if ( usCodepage &&
         pFocaFont->fmMetrics.usCodePage == 850 )
    {
        /**************************************************************/
        /* The codepage is non-zero, so we need a vector.             */
        /**************************************************************/
        if (pdc->CurrentFont.usCodePage != usCodepage)
        {
            /**********************************************************/
            /* Call the engine to get a pointer to the vector.        */
            /**********************************************************/
            pdc->CurrentFont.pCodePageVector =
                      (PUSHORT)(GreQueryCodePageVector(usCodepage));
            if (pdc->CurrentFont.pCodePageVector == GPI_ERROR)
            {
                DebugOutput("GreQueryCodePageVector failed\n\r");
                return (ERROR_ZERO);
            }
        }
    }
    else
    {
        /**************************************************************/
        /* The codepage is zero so we don't need a codepage vector.   */
        /**************************************************************/
        pdc->CurrentFont.pCodePageVector = FNULL;
    }
#endif                                                                  /*YOJN*/
    pdc->CurrentFont.usCodePage = usCodepage;

    /******************************************************************/
    /* Store the spacing type.                                        */
    /******************************************************************/
    if ( pFocaFont->fdDefinitions.fsFontdef == FONTDEFFONT1)
    {
        pdc->DCISpacingType = FIXED_PITCH;
    }
    else if (pFocaFont->fdDefinitions.fsChardef == FONTDEFCHAR3)
    {
        pdc->DCISpacingType = A_B_C_SPACED;
    }
    else
    {
        pdc->DCISpacingType = PROPORTIONAL_SPACED;
    }

    /******************************************************************/
    /* The test on version number means we DO locate fonts which only */
    /* contain one character at 1.3+.  This is because we may be      */
    /* passed IFI fonts that only have one character.                 */
    /******************************************************************/
//  if ( (usVersion >= 0x0A1E) ||
    if (pdc->CurrentFont.pFocaFont->fmMetrics.usLastChar > 0)
    {
        eddt_LocateCachedFont( &pdc->CurrentFont );
    }
    return(OK);
}
#undef TFUNC

#ifdef DBCS                                                             /*YOJN*/
/*===================== Private  Routine =============================*//*YOJN*/
/*      SelectCodepage                                                *//*YOJN*/
/*                                                                    *//*YOJN*/
/* Select a codepage which is usable for given font                   *//*YOJN*/
/*                                                                    *//*YOJN*/
/* Entry       :      - Ptr to FOCAFONT struct of font being used     *//*YOJN*/
/*                    - Codepage supplied by GRE                      *//*YOJN*/
/*                    - Ptr to FONTDETAILS struct where result should *//*YOJN*/
/*                      be returned                                   *//*YOJN*/
/*                                                                    *//*YOJN*/
/* Returns     :        Returns TRUE if completes                     *//*YOJN*/
/*                                                                    *//*YOJN*/
/*                    - The following field of FONTDETAILS struct is  *//*YOJN*/
/*                      set on return:                                *//*YOJN*/
/*                              NLSFontFlag                           *//*YOJN*/
/*                              NLSParseFlag                          *//*YOJN*/
/*                              pCodePageVector                       *//*YOJN*/
/*                              pDBCSMap                              *//*YOJN*/
/*                              usECodePage                           *//*YOJN*/
/*                              FMCacheSize                           *//*YOJN*/
/*                                                                    *//*YOJN*/
/* Error Returns :      Returns FALSE when NO CP IS USABLE            *//*YOJN*/
/*                                                                    *//*YOJN*/
/* Note        :                                                      *//*YOJN*/
/*    - Logic for Codepage selection                                  *//*YOJN*/
/*                                                                    *//*YOJN*/
/*      Font             CP requested       CP not requested          *//*YOJN*/
/*    ===========================================================     *//*YOJN*/
/*      != 850           Given CP             Font's CP               *//*YOJN*/
/*                       (no SBCS map)        (no SBCS map)           *//*YOJN*/
/*    -----------------------------------------------------------     *//*YOJN*/
/*     SBCS 850          Given CP             Font's CP               *//*YOJN*/
/*                       (w/ SBCS map)        (no SBCS map)           *//*YOJN*/
/*    -----------------------------------------------------------     *//*YOJN*/
/*     MBCS 850          Given CP             DC's default CP         *//*YOJN*/
/*                       (w/ SBCS map)                                *//*YOJN*/
/*                                                                    *//*YOJN*/
/*    - GRE passes IFI (vector) fonts with font's CP=0.  In this      *//*YOJN*/
/*      case, we should use it with any CP requested, without SBCS    *//*YOJN*/
/*      mapping.  This is achieved by strategy above.                 *//*YOJN*/
/*                                                                    *//*YOJN*/
/* Calls       :                                                      *//*YOJN*/
/*                                                                    *//*YOJN*/
/*====================================================================*//*YOJN*/
BOOL SelectCodepage( PFOCAFONT pFocaFont,                               /*YOJN*/
                     ULONG ulCodePage,                                  /*YOJN*/
                     PFONTDETAILS pFontDtl )                            /*YOJN*/
{                                      /* top of func: SelectCodepage *//*YOJN*/
  BOOL fResult;                        /* TRUE if mapping OK          *//*YOJN*/
                                                                        /*YOJN*/
  /*------------------------------------------------------------------*//*YOJN*/
  /* fill fields:  NLSFontFlag, FMCacheSize                           *//*YOJN*/
  /*------------------------------------------------------------------*//*YOJN*/
  if (CHECKENV(ENV_DBCS_CAPABLE))      /* if DBCS-capable system      *//*YOJN*/
    {                                                                   /*YOJN*/
      eddj_QueryFontProfile( pFocaFont,                                 /*YOJN*/
                             &pFontDtl->NLSFontFlag,                    /*YOJN*/
                             &pFontDtl->FMCacheSize );                  /*YOJN*/
                                       /* may need to call Font Mgr to*//*YOJN*/
                                       /* query font's attributes     *//*YOJN*/
    }                                  /* end of if:                  *//*YOJN*/
  else                                 /* or if SBCS-only system      *//*YOJN*/
    {                                  /*                             *//*YOJN*/
      pFontDtl->NLSFontFlag = NLSCA_FONT_SBCS;                          /*YOJN*/
      pFontDtl->FMCacheSize = 0;                                        /*YOJN*/
                                       /* this is only possible value *//*YOJN*/
    }                                  /* end of else:                *//*YOJN*/
                                                                        /*YOJN*/
  /*------------------------------------------------------------------*/
  /* select CP to be used                                             */
  /*------------------------------------------------------------------*/
  if (ulCodePage)                      /* if any CP requested         */
    {                                  /*                             */
      pFontDtl->usECodePage = (USHORT)ulCodePage;
                                       /* we must use it anyway       */
    }                                  /* end of if:                  */
  else                                 /* or no CP requested          */
    {                                  /*                             */
      if ((pFontDtl->NLSFontFlag & (NLSCA_MBCS | NLSCA_DBCS)) &&
          (pFocaFont->fmMetrics.usCodePage == CP_UGL_FONT))
        {                              /* if it is MBCS/DBCS UGL font */
          pFontDtl->usECodePage = pdc->DCICodePage;
                                       /* will use DC's default       */
        }                              /* end of if:                  */
      else                             /*                             */
        {                              /*                             */
          pFontDtl->usECodePage = pFocaFont->fmMetrics.usCodePage;
        }                              /* end of else:                */
    }                                  /* end of else:                */

  /*------------------------------------------------------------------*//*YOJN*/
  /* check SBCS mapping                                               *//*YOJN*/
  /*------------------------------------------------------------------*//*YOJN*/
  if ((pFocaFont->fmMetrics.usCodePage != CP_UGL_FONT) ||
      (pFocaFont->fmMetrics.usCodePage == pFontDtl->usECodePage))
    {                                  /* non UGL font or using font's*/
                                       /* CP: need no SBCS mapping    */
      fResult = eddj_QueryCPVectors( (ULONG)pFontDtl->usECodePage,      /*YOJN*/
                                     NULL,                              /*YOJN*/
                                     &pFontDtl->pDBCSMap,               /*YOJN*/
                                     &pFontDtl->NLSParseFlag );         /*YOJN*/
      pFontDtl->pCodePageVector = NULL;                                 /*YOJN*/
      pFontDtl->NLSParseFlag &= ~NLSCA_MAP_SBCS;                        /*YOJN*/
    }                                  /* end of if:                  */

  else                                 /* UGL font and not font's CP: */
    {                                  /* need SBCS mapping           */
      fResult =
        eddj_QueryCPVectors( (ULONG)pFontDtl->usECodePage,
                             &pFontDtl->pCodePageVector,
                             &pFontDtl->pDBCSMap,
                             &pFontDtl->NLSParseFlag );
                                       /* try to map this CP to 850   *//*YOJN*/
    }                                  /* end of else:                */

  return fResult;                      /*                             */
}                                      /* end of func: SelectCodepage *//*YOJN*/
                                                                        /*YOJN*/
#endif /*DBCS*/                                                         /*YOJN*/
