/* Copyright (C) 2001-2006 artofcode LLC.
   All Rights Reserved.
  
  This file is part of GNU ghostscript

  GNU ghostscript is free software; you can redistribute it and/or
  modify it under the terms of the version 2 of the GNU General Public
  License as published by the Free Software Foundation.

  GNU ghostscript is distributed in the hope that it will be useful, but WITHOUT
  ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS
  FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.

  You should have received a copy of the GNU General Public License along with
  ghostscript; see the file COPYING. If not, write to the Free Software Foundation,
  Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.

*/
/* $Id: gsnamecl.h,v 1.3 2007/08/01 14:26:09 jemarch Exp $ */
/* Global definitions for the 'Named Color' callback handling. */

#ifndef gsnamecl_INCLUDED
# define gsnamecl_INCLUDED

#include "gxfrac.h"
#include "gsccolor.h"
#include "gscsel.h"

/*
 * Enable 'named color' callback color processing.  Note:  There is a sample
 * implementation in src/gsncdemo.c.
 */
#define ENABLE_NAMED_COLOR_CALLBACK 0	/* 0 --> disabled, 1 --> enabled */

/*
 * For comments upon the client API for working with the 'named color'
 * callback logic see the section labeled:  "NAMED COLOR CALLBACK CLIENT
 * APPLICATION INTERFACE" below.
 */

/*
 * Type for holding 'named color' callback related parameters
 */
typedef struct named_color_params_s {
    /*
     * If true, then use the 'named color' callback color processing path
     * for determining colorants.
     */
    bool use_named_color_callback;
    /*
     * Storage for the 'named color' callback related parameters.
     * Note:  This storage is actually for the client.  This may be enough
     * for some clients.  It is enough for our demo example.  A more complete
     * implementation would probably include a client callback for for when
     * a color space is finished (i.e. the reference count is zero or it
     * is garbage collected).
     */
    int color_index[GS_CLIENT_COLOR_MAX_COMPONENTS];
} named_color_params_t;

#ifndef gs_color_space_DEFINED
#  define gs_color_space_DEFINED
typedef struct gs_color_space_s gs_color_space;
#endif

#ifndef gx_device_color_DEFINED
#  define gx_device_color_DEFINED
typedef struct gx_device_color_s gx_device_color;
#endif

#ifndef gs_state_DEFINED
#  define gs_state_DEFINED
typedef struct gs_state_s gs_state;
#endif

#ifndef gs_imager_state_DEFINED
#  define gs_imager_state_DEFINED
typedef struct gs_imager_state_s gs_imager_state;
#endif

#ifndef gx_device_DEFINED
#  define gx_device_DEFINED
typedef struct gx_device_s gx_device;
#endif

/* Define an opaque type for parameter lists. */
#ifndef gs_param_list_DEFINED
#  define gs_param_list_DEFINED
typedef struct gs_param_list_s gs_param_list;
#endif

/*
 * Put the 'named color' client callback parameter block pointer.  This value
 * is passed as a string type device paramter.  A string is being used since
 * PostScript does not support pointers as a type.  Note:  An integer type
 * is not being used since PS intergers are nominally 32 bits.  Thus there
 * would be a problem using integers to pass pointer values on 64 bit systems.
 */
int named_color_put_params(gx_device * dev, gs_param_list * plist);

/*
 * Get the 'named color' client callback parameter block pointer.  This value
 * is passed as a string type device paramter.  A string is being used since
 * PostScript does not support pointers as a type.  Note:  An integer type
 * is not being used since PS intergers are nominally 32 bits.  Thus there
 * would be a problem using integers to pass pointer values on 64 bit systems.
 */
int named_color_get_params(gx_device * dev, gs_param_list * plist);

/*
 * Check if we want to use the 'named color' callback processing logic for the
 * given Separation color space.
 */
bool named_color_install_Separation(gs_color_space * pcs, gs_state * pgs);

/*
 * Check if we want to use the 'named color' callback processing logic for the
 * given DeviceN color space.
 */
bool named_color_install_DeviceN(gs_color_space * pcs, gs_state * pgs);

/*
 * Convert a Separation color into device colorants using the 'named color'
 * client callback.
 */
int gx_remap_concrete_named_color_Separation(const frac * pconc,
	const gs_color_space * pcs, gx_device_color * pdc,
       	const gs_imager_state * pis, gx_device * dev, gs_color_select_t select);

/*
 * Convert a DeviceN color into device colorants using the 'named color'
 * client callback.
 */
int gx_remap_concrete_named_color_DeviceN(const frac * pconc,
	const gs_color_space * pcs, gx_device_color * pdc,
       	const gs_imager_state * pis, gx_device * dev, gs_color_select_t select);

/* "CLIENT NAMED COLOR APPLICATION INTERFACE" */
/*
 * In order to give some flexibility to the Ghostscript client API, we are
 * allowing the client to define a set of call back procedures for processing
 * color spaces with 'named colors', i.e. Separation and DeviceN.
 */
/*
 * The 'named color' call back structure definitions.  The call back structure
 * consists of a pointer to a list of client 'named color' color handling
 * procedures and a pointer to a client data structure.
 */
typedef struct client_named_color_params_s {
    struct client_named_color_procs_s * client_procs;	/* Client callback handlers */
    void * data;				/* For client data */
} client_named_color_params_t;

/*
 * Define the client 'named color' callback procedures.
 */
typedef struct client_named_color_procs_s {
    /*
     * Check if we want to use the callback color processing logic for the
     * given Separation color space.
     */
    bool (* install_Separation)(client_named_color_params_t * pparams,
	    gs_color_space * pcs, gs_state * pgs);
    /*
     * Convert a Separation color into device color.
     */
    int (* remap_Separation)(client_named_color_params_t * pparams,
	    const frac * pconc, const gs_color_space * pcs,
	    gx_device_color * pdc, const gs_imager_state * pis,
	    gx_device * dev, gs_color_select_t select);
    /*
     * Check if we want to use the callback color processing logic for the
     * given DeviceN color space.
     */
    bool (* install_DeviceN)(client_named_color_params_t * pparams,
	    gs_color_space * pcs, gs_state * pgs);
    /*
     * Convert a DeviceN color into device color.
     */
    int (* remap_DeviceN)(client_named_color_params_t * pparams, const frac * pconc,
	    const gs_color_space * pcs, gx_device_color * pdc,
       	    const gs_imager_state * pis, gx_device * dev,
	    gs_color_select_t select);

} client_named_color_procs_t;
    
#endif		/* ifndef gsnamecl_INCLUDED */
