/***************************************************************************/
/*                                                                         */
/*  afglobal.c                                                             */
/*                                                                         */
/*    Auto-fitter routines to compute global hinting values (body).        */
/*                                                                         */
/*  Copyright 2003, 2004, 2005, 2006, 2007, 2008 by                        */
/*  David Turner, Robert Wilhelm, and Werner Lemberg.                      */
/*                                                                         */
/*  This file is part of the FreeType project, and may only be used,       */
/*  modified, and distributed under the terms of the FreeType project      */
/*  license, LICENSE.TXT.  By continuing to use, modify, or distribute     */
/*  this file you indicate that you have read the license and              */
/*  understand and accept it fully.                                        */
/*                                                                         */
/***************************************************************************/


#include "afglobal.h"
#include "afdummy.h"
#include "aflatin.h"
#include "afcjk.h"
#include "afindic.h"

#include "aferrors.h"

#ifdef FT_OPTION_AUTOFIT2
#include "aflatin2.h"
#endif

  /* populate this list when you add new scripts */
  static AF_ScriptClass const  af_script_classes[] =
  {
    &af_dummy_script_class,
#ifdef FT_OPTION_AUTOFIT2
    &af_latin2_script_class,
#endif
    &af_latin_script_class,
    &af_cjk_script_class,
    &af_indic_script_class, 
    NULL  /* do not remove */
  };

  /* index of default script in `af_script_classes' */
#define AF_SCRIPT_LIST_DEFAULT  2
  /* indicates an uncovered glyph                   */
#define AF_SCRIPT_LIST_NONE   255


  /*
   *  Note that glyph_scripts[] is used to map each glyph into
   *  an index into the `af_script_classes' array.
   *
   */
  typedef struct  AF_FaceGlobalsRec_
  {
    FT_Face           face;
    FT_UInt           glyph_count;    /* same as face->num_glyphs */
    FT_Byte*          glyph_scripts;

    AF_ScriptMetrics  metrics[AF_SCRIPT_MAX];

  } AF_FaceGlobalsRec;


  /* Compute the script index of each glyph within a given face. */

  static FT_Error
  af_face_globals_compute_script_coverage( AF_FaceGlobals  globals )
  {
    FT_Error    error       = AF_Err_Ok;
    FT_Face     face        = globals->face;
    FT_CharMap  old_charmap = face->charmap;
    FT_Byte*    gscripts    = globals->glyph_scripts;
    FT_UInt     ss;


    /* the value 255 means `uncovered glyph' */
    FT_MEM_SET( globals->glyph_scripts,
                AF_SCRIPT_LIST_NONE,
                globals->glyph_count );

    error = FT_Select_Charmap( face, FT_ENCODING_UNICODE );
    if ( error )
    {
     /*
      *  Ignore this error; we simply use the default script.
      *  XXX: Shouldn't we rather disable hinting?
      */
      error = AF_Err_Ok;
      goto Exit;
    }

    /* scan each script in a Unicode charmap */
    for ( ss = 0; af_script_classes[ss]; ss++ )
    {
      AF_ScriptClass      clazz = af_script_classes[ss];
      AF_Script_UniRange  range;


      if ( clazz->script_uni_ranges == NULL )
        continue;

      /*
       *  Scan all unicode points in the range and set the corresponding
       *  glyph script index.
       */
      for ( range = clazz->script_uni_ranges; range->first != 0; range++ )
      {
        FT_ULong  charcode = range->first;
        FT_UInt   gindex;


        gindex = FT_Get_Char_Index( face, charcode );

        if ( gindex != 0                             &&
             gindex < globals->glyph_count           &&
             gscripts[gindex] == AF_SCRIPT_LIST_NONE )
        {
          gscripts[gindex] = (FT_Byte)ss;
        }

        for (;;)
        {
          charcode = FT_Get_Next_Char( face, charcode, &gindex );

          if ( gindex == 0 || charcode > range->last )
            break;

          if ( gindex < globals->glyph_count           &&
               gscripts[gindex] == AF_SCRIPT_LIST_NONE )
          {
            gscripts[gindex] = (FT_Byte)ss;
          }
        }
      }
    }

  Exit:
    /*
     *  By default, all uncovered glyphs are set to the latin script.
     *  XXX: Shouldn't we disable hinting or do something similar?
     */
    {
      FT_UInt  nn;


      for ( nn = 0; nn < globals->glyph_count; nn++ )
      {
        if ( gscripts[nn] == AF_SCRIPT_LIST_NONE )
          gscripts[nn] = AF_SCRIPT_LIST_DEFAULT;
      }
    }

    FT_Set_Charmap( face, old_charmap );
    return error;
  }


  FT_LOCAL_DEF( FT_Error )
  af_face_globals_new( FT_Face          face,
                       AF_FaceGlobals  *aglobals )
  {
    FT_Error        error;
    FT_Memory       memory;
    AF_FaceGlobals  globals;


    memory = face->memory;

    if ( !FT_ALLOC( globals, sizeof ( *globals ) +
                             face->num_glyphs * sizeof ( FT_Byte ) ) )
    {
      globals->face          = face;
      globals->glyph_count   = face->num_glyphs;
      globals->glyph_scripts = (FT_Byte*)( globals + 1 );

      error = af_face_globals_compute_script_coverage( globals );
      if ( error )
      {
        af_face_globals_free( globals );
        globals = NULL;
      }
    }

    *aglobals = globals;
    return error;
  }


  FT_LOCAL_DEF( void )
  af_face_globals_free( AF_FaceGlobals  globals )
  {
    if ( globals )
    {
      FT_Memory  memory = globals->face->memory;
      FT_UInt    nn;


      for ( nn = 0; nn < AF_SCRIPT_MAX; nn++ )
      {
        if ( globals->metrics[nn] )
        {
          AF_ScriptClass  clazz = af_script_classes[nn];


          FT_ASSERT( globals->metrics[nn]->clazz == clazz );

          if ( clazz->script_metrics_done )
            clazz->script_metrics_done( globals->metrics[nn] );

          FT_FREE( globals->metrics[nn] );
        }
      }

      globals->glyph_count   = 0;
      globals->glyph_scripts = NULL;  /* no need to free this one! */
      globals->face          = NULL;

      FT_FREE( globals );
    }
  }


  FT_LOCAL_DEF( FT_Error )
  af_face_globals_get_metrics( AF_FaceGlobals     globals,
                               FT_UInt            gindex,
                               FT_UInt            options,
                               AF_ScriptMetrics  *ametrics )
  {
    AF_ScriptMetrics  metrics = NULL;
    FT_UInt           gidx;
    AF_ScriptClass    clazz;
    FT_UInt           script     = options & 15;
    const FT_UInt     script_max = sizeof ( af_script_classes ) /
                                     sizeof ( af_script_classes[0] );
    FT_Error          error      = AF_Err_Ok;


    if ( gindex >= globals->glyph_count )
    {
      error = AF_Err_Invalid_Argument;
      goto Exit;
    }

    gidx = script;
    if ( gidx == 0 || gidx + 1 >= script_max )
      gidx = globals->glyph_scripts[gindex];

    clazz = af_script_classes[gidx];
    if ( script == 0 )
      script = clazz->script;

    metrics = globals->metrics[clazz->script];
    if ( metrics == NULL )
    {
      /* create the global metrics object when needed */
      FT_Memory  memory = globals->face->memory;


      if ( FT_ALLOC( metrics, clazz->script_metrics_size ) )
        goto Exit;

      metrics->clazz = clazz;

      if ( clazz->script_metrics_init )
      {
        error = clazz->script_metrics_init( metrics, globals->face );
        if ( error )
        {
          if ( clazz->script_metrics_done )
            clazz->script_metrics_done( metrics );

          FT_FREE( metrics );
          goto Exit;
        }
      }

      globals->metrics[clazz->script] = metrics;
    }

  Exit:
    *ametrics = metrics;

    return error;
  }


/* END */
