/*--------------------------------------------------------------------
 *	$Id: pslib_inc.h,v 1.52 2010/01/05 01:15:47 guru Exp $
 *
 *	Copyright (c) 1991-2010 by P. Wessel and W. H. F. Smith
 *	See LICENSE.TXT file for copying and redistribution conditions.
 *
 *	This program is free software; you can redistribute it and/or modify
 *	it under the terms of the GNU General Public License as published by
 *	the Free Software Foundation; version 2 of the License.
 *
 *	This program 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.
 *
 *	Contact info: gmt.soest.hawaii.edu
 *--------------------------------------------------------------------*/
/*
 * This include file is only included in pslib.c.  Calling programs must
 * include file pslib.h
 *
 * Author:	Paul Wessel
 * Date:	20-MAR-2008
 * Version:	4.3 [64-bit enabled edition]
 */

#ifndef _PSLIB_INC_H
#define _PSLIB_INC_H

/*  PSL is POSIX COMPLIANT  */

#define _POSIX_SOURCE 1

#define PS_LANGUAGE_LEVEL 2

/* Declaration modifiers for DLL support (MSC et al) */

#if defined(DLL_PSL)		/* define when library is a DLL */
#if defined(DLL_EXPORT)		/* define when building the library */
#define MSC_EXTRA_PSL __declspec(dllexport)
#else
#define MSC_EXTRA_PSL __declspec(dllimport)
#endif
#else
#define MSC_EXTRA_PSL
#endif				/* defined(DLL_PSL) */

#ifndef EXTERN_MSC
#define EXTERN_MSC extern MSC_EXTRA_PSL
#endif

/* So unless DLL_PSL is defined, EXTERN_MSC is simply extern */

/* 64-bit integers */

#ifdef _WIN64
typedef __int64 PS_LONG;	/* A signed 8-byte integer */
#else
typedef long PS_LONG;		/* A signed 4 (or 8-byte for 64-bit) integer */
#endif

/* Macro for printing the value of size_t */

#if defined(__STDC_VERSION__) && __STDC_VERSION__ >= 199901L
/*
 * This is a C99 compiler, so it supports %zu; no need to cast.
 */
#define PRINT_SIZE_T(fp,u) fprintf(fp, "%zu", u)
#else
/*
 * This is not a C99 compiler; assume size_t is no bigger than
 * unsigned long.
 */
#ifdef _WIN64
#define PRINT_SIZE_T(fp,u) fprintf(fp, "%lu", (unsigned long long)u)
#else
#define PRINT_SIZE_T(fp,u) fprintf(fp, "%lu", (unsigned long)u)
#endif
#endif

/*--------------------------------------------------------------------
 *			SYSTEM HEADER FILES
 *--------------------------------------------------------------------*/

#include <ctype.h>
#include <float.h>
#include <limits.h>
#include <math.h>
#include <stddef.h>
#ifdef __MACHTEN__
/* Kludge to fix a Machten POSIX bug */
#include <sys/types.h>
#endif
#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <time.h>
#include "gmt_notunix.h"
#include "gmt_math.h"

#ifndef WIN32
#include <unistd.h>
#endif

typedef int BOOLEAN;		/* BOOLEAN used for logical variables */

/*--------------------------------------------------------------------
 *		     STANDARD CONSTANTS MACRO DEFINITIONS
 *--------------------------------------------------------------------*/

#ifndef TRUE
#define TRUE 1
#endif
#ifndef FALSE
#define FALSE 0
#endif
#ifndef M_PI
#define M_PI            3.14159265358979323846
#endif
#ifndef R2D
#define R2D (180.0/M_PI)
#endif
#ifndef D2R
#define D2R (M_PI/180.0)
#endif
#ifndef M_SQRT2
#define M_SQRT2         1.41421356237309504880
#endif
#define VNULL		((void *)NULL)
#ifndef CNULL
#define CNULL (char *)NULL
#endif
#ifndef MIN
#define MIN(x, y) (((x) < (y)) ? (x) : (y))
#endif
#ifndef MAX
#define MAX(x, y) (((x) > (y)) ? (x) : (y))
#endif
#ifndef irint
#define irint(x) ((int)rint(x))
#endif

/*--------------------------------------------------------------------
 *			PSL CONSTANTS MACRO DEFINITIONS
 *--------------------------------------------------------------------*/

#define PSL_Version		"4.2"
#define PSL_SMALL		1.0e-10
#define PSL_MAX_L1_PATH		1000 	/* Max path length in Level 1 implementations */
#define PSL_INV_255		(1.0 / 255.0)
#define PSL_N_PATTERNS		91	/* Current number of predefined patterns + 1, # 91 is user-supplied */
#define PSL_PAGE_HEIGHT_IN_PTS	842	/* A4 height */
#define PSL_RGB			0
#define PSL_CMYK		1
#define PSL_HSV			2
#define PSL_GRAY		3

/*--------------------------------------------------------------------
 *			PSL FUNCTION MACRO DEFINITIONS
 *--------------------------------------------------------------------*/

#define PSL_YIQ(rgb) irint (0.299 * (rgb[0]) + 0.587 * (rgb[1]) + 0.114 * (rgb[2]))	/* How B/W TV's convert RGB to Gray */
#define PSL_iscolor(rgb) (rgb[0] != rgb[1] || rgb[1] != rgb[2])

/*--------------------------------------------------------------------
 *			PSL PARAMETERS DEFINITIONS
 *--------------------------------------------------------------------*/

/* Single, global structure used internally by pslib */

struct PSL {
	struct INIT {	/* Parameters set by user via ps_plotinit() */
		char *file;			/* Name of output file (NULL means stdout)	*/
		char *encoding;			/* The encoding name. e.g. ISO-8859-1		*/
		PS_LONG overlay;		/* TRUE skips writing the PS header section	*/
		PS_LONG mode;			/* 32 bit-flags, used as follows:
			bit 0 : 0 = Landscape, 1 = Portrait,
			bit 1 : 0 = be silent, 1 = be verbose
			bit 2 : 0 = bin image, 1 = hex image
			bit 3 : 0 = rel positions, 1 = abs positions
			bit 9-10 : 0 = RGB color, 1 = CMYK color, 2 = HSV color
			bits 12-13 : 0 = no compression, 1 = RLE compression, 2 = LZW compression
			bits 14-15 : (0,1,2) sets the line cap setting
			bits 16-17 : (0,1,2) sets the line miter setting
			bits 18-25 : (8 bits) sets the miter limit
			bit 31 : 0 = write no comments, 1 = write PS comments to PS file	*/
		PS_LONG unit;			/* 0 = cm, 1 = inch, 2 = meter			*/
		PS_LONG copies;			/* Number of copies for this plot		*/
		int page_rgb[3];		/* RGB color for background paper [white]	*/
		double page_size[2];		/* Width and height of paper used in points	*/
		PS_LONG dpi;			/* Selected dots per inch			*/
		double magnify[2];		/* Global scale values [1/1]			*/
		double origin[2];		/* Origin offset [1/1]				*/
		struct EPS *eps;		/* structure with Document info			*/
	} init;
	struct CURRENT {	/* Variables and settings that changes via ps_* calls */
		char texture[512];		/* Current setdash pattern			*/
		char bw_format[8];		/* Format used for grayshade value		*/
		char rgb_format[64];		/* Same, for RGB color triplets			*/
		char hsv_format[64];		/* Same, for HSV color triplets	(HSB in PS)	*/
		char cmyk_format[64];		/* Same, for CMYK color quadruples		*/
		PS_LONG font_no;		/* Current font number				*/
		PS_LONG linewidth;		/* Current pen thickness			*/
		int rgb[3];			/* Current paint				*/
		int fill_rgb[3];		/* Current fill					*/
		PS_LONG outline;		/* Current outline				*/
		PS_LONG offset;			/* Current setdash offset			*/
	} current;
	struct INTERNAL {	/* Variables used internally only */
		char *SHAREDIR;			/* Pointer to path of directory with pslib subdirectory */
		char *USERDIR;			/* Pointer to path of directory with user definitions (~/.gmt) */
		char *user_image[PSL_N_PATTERNS];	/* Name of user patterns		*/
		BOOLEAN verbose;		/* TRUE for verbose output, FALSE remains quiet	*/
		BOOLEAN comments;		/* TRUE for writing comments to output, FALSE strips all comments */
		BOOLEAN landscape;		/* TRUE = Landscape, FALSE = Portrait		*/
		BOOLEAN text_init;		/* TRUE after PSL_text.ps has been loaded	*/
		PS_LONG ascii;			/* TRUE writes images in ascii, FALSE uses binary	*/
		PS_LONG absolute;		/* TRUE will reset origin, FALSE means relative position	*/
		PS_LONG eps_format;		/* TRUE makes EPS file, FALSE means PS file	*/
		PS_LONG N_FONTS;		/* Total no of fonts;  To add more, modify the file CUSTOM_font_info.d */
		PS_LONG compress;		/* Compresses images with (1) RLE or (2) LZW or (0) None */
		PS_LONG color_mode;		/* 0 = rgb, 1 = cmyk, 2 = hsv (only 1-2 for images)	*/
		PS_LONG line_cap;		/* 0, 1, or 2 for butt, round, or square [butt] */
		PS_LONG line_join;		/* 0, 1, or 2 for miter, arc, or bevel [miter] */
		PS_LONG miter_limit;		/* Acute angle threshold 0-180; 0 means PS default [0] */
		double bb[4];			/* Boundingbox arguments			*/
		PS_LONG ix, iy;			/* Absolute coordinates of last point		*/
		double p_width;			/* Paper width in points, set in plotinit();	*/
		double p_height;		/* Paper height in points, set in plotinit();	*/
		PS_LONG length;			/* Image row output byte counter		*/
		PS_LONG n_userimages;		/* Number of specified custom patterns		*/
		double scale;			/* Must be set through plotinit();		*/
		double points_pr_unit;		/* # of points pr measure unit (e.g., 72/inch	*/
		FILE *fp;			/* PS output file pointer. NULL = stdout	*/
		struct PSL_FONT {
			char *name;		/* Name of this font */
			double height;		/* Height of A for unit fontsize */
			BOOLEAN encoded;	/* TRUE if we never should reencode this font (e.g. symbols) */
						/* This is also changed to TRUE after we do reencode a font */
		} *font;	/* Pointer to array of font structures 		*/
		struct PSL_PATTERN {
			PS_LONG nx, ny;
			PS_LONG status, depth, dpi;
			int f_rgb[3], b_rgb[3];
		} pattern[PSL_N_PATTERNS*2];
	} internal;
} *PSL;

#endif	/* _PSLIB_INC_H */
