📄 ftraster.c
字号:
/***************************************************************************/
/* */
/* ftraster.c */
/* */
/* The FreeType glyph rasterizer (body). */
/* */
/* Copyright 1996-2001, 2002, 2003, 2005, 2007 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. */
/* */
/***************************************************************************/
/*************************************************************************/
/* */
/* This file can be compiled without the rest of the FreeType engine, by */
/* defining the _STANDALONE_ macro when compiling it. You also need to */
/* put the files `ftimage.h' and `ftmisc.h' into the $(incdir) */
/* directory. Typically, you should do something like */
/* */
/* - copy `src/raster/ftraster.c' (this file) to your current directory */
/* */
/* - copy `include/freetype/ftimage.h' and `src/raster/ftmisc.h' */
/* to your current directory */
/* */
/* - compile `ftraster' with the _STANDALONE_ macro defined, as in */
/* */
/* cc -c -D_STANDALONE_ ftraster.c */
/* */
/* The renderer can be initialized with a call to */
/* `ft_standard_raster.raster_new'; a bitmap can be generated */
/* with a call to `ft_standard_raster.raster_render'. */
/* */
/* See the comments and documentation in the file `ftimage.h' for more */
/* details on how the raster works. */
/* */
/*************************************************************************/
/*************************************************************************/
/* */
/* This is a rewrite of the FreeType 1.x scan-line converter */
/* */
/*************************************************************************/
#ifdef _STANDALONE_
#include "ftmisc.h"
#include "ftimage.h"
#else /* !_STANDALONE_ */
#include <ft2build.h>
#include "ftraster.h"
#include FT_INTERNAL_CALC_H /* for FT_MulDiv only */
#endif /* !_STANDALONE_ */
/*************************************************************************/
/* */
/* A simple technical note on how the raster works */
/* ----------------------------------------------- */
/* */
/* Converting an outline into a bitmap is achieved in several steps: */
/* */
/* 1 - Decomposing the outline into successive `profiles'. Each */
/* profile is simply an array of scanline intersections on a given */
/* dimension. A profile's main attributes are */
/* */
/* o its scanline position boundaries, i.e. `Ymin' and `Ymax'. */
/* */
/* o an array of intersection coordinates for each scanline */
/* between `Ymin' and `Ymax'. */
/* */
/* o a direction, indicating whether it was built going `up' or */
/* `down', as this is very important for filling rules. */
/* */
/* 2 - Sweeping the target map's scanlines in order to compute segment */
/* `spans' which are then filled. Additionally, this pass */
/* performs drop-out control. */
/* */
/* The outline data is parsed during step 1 only. The profiles are */
/* built from the bottom of the render pool, used as a stack. The */
/* following graphics shows the profile list under construction: */
/* */
/* ____________________________________________________________ _ _ */
/* | | | | | */
/* | profile | coordinates for | profile | coordinates for |--> */
/* | 1 | profile 1 | 2 | profile 2 |--> */
/* |_________|___________________|_________|_________________|__ _ _ */
/* */
/* ^ ^ */
/* | | */
/* start of render pool top */
/* */
/* The top of the profile stack is kept in the `top' variable. */
/* */
/* As you can see, a profile record is pushed on top of the render */
/* pool, which is then followed by its coordinates/intersections. If */
/* a change of direction is detected in the outline, a new profile is */
/* generated until the end of the outline. */
/* */
/* Note that when all profiles have been generated, the function */
/* Finalize_Profile_Table() is used to record, for each profile, its */
/* bottom-most scanline as well as the scanline above its upmost */
/* boundary. These positions are called `y-turns' because they (sort */
/* of) correspond to local extrema. They are stored in a sorted list */
/* built from the top of the render pool as a downwards stack: */
/* */
/* _ _ _______________________________________ */
/* | | */
/* <--| sorted list of | */
/* <--| extrema scanlines | */
/* _ _ __________________|____________________| */
/* */
/* ^ ^ */
/* | | */
/* maxBuff sizeBuff = end of pool */
/* */
/* This list is later used during the sweep phase in order to */
/* optimize performance (see technical note on the sweep below). */
/* */
/* Of course, the raster detects whether the two stacks collide and */
/* handles the situation propertly. */
/* */
/*************************************************************************/
/*************************************************************************/
/*************************************************************************/
/** **/
/** CONFIGURATION MACROS **/
/** **/
/*************************************************************************/
/*************************************************************************/
/* define DEBUG_RASTER if you want to compile a debugging version */
#define xxxDEBUG_RASTER
/* undefine FT_RASTER_OPTION_ANTI_ALIASING if you do not want to support */
/* 5-levels anti-aliasing */
#ifdef FT_CONFIG_OPTION_5_GRAY_LEVELS
#define FT_RASTER_OPTION_ANTI_ALIASING
#endif
/* The size of the two-lines intermediate bitmap used */
/* for anti-aliasing, in bytes. */
#define RASTER_GRAY_LINES 2048
/*************************************************************************/
/*************************************************************************/
/** **/
/** OTHER MACROS (do not change) **/
/** **/
/*************************************************************************/
/*************************************************************************/
/*************************************************************************/
/* */
/* The macro FT_COMPONENT is used in trace mode. It is an implicit */
/* parameter of the FT_TRACE() and FT_ERROR() macros, used to print/log */
/* messages during execution. */
/* */
#undef FT_COMPONENT
#define FT_COMPONENT trace_raster
#ifdef _STANDALONE_
/* This macro is used to indicate that a function parameter is unused. */
/* Its purpose is simply to reduce compiler warnings. Note also that */
/* simply defining it as `(void)x' doesn't avoid warnings with certain */
/* ANSI compilers (e.g. LCC). */
#define FT_UNUSED( x ) (x) = (x)
/* Disable the tracing mechanism for simplicity -- developers can */
/* activate it easily by redefining these two macros. */
#ifndef FT_ERROR
#define FT_ERROR( x ) do ; while ( 0 ) /* nothing */
#endif
#ifndef FT_TRACE
#define FT_TRACE( x ) do ; while ( 0 ) /* nothing */
#define FT_TRACE1( x ) do ; while ( 0 ) /* nothing */
#define FT_TRACE6( x ) do ; while ( 0 ) /* nothing */
#endif
#define Raster_Err_None 0
#define Raster_Err_Not_Ini -1
#define Raster_Err_Overflow -2
#define Raster_Err_Neg_Height -3
#define Raster_Err_Invalid -4
#define Raster_Err_Unsupported -5
#define ft_memset memset
#else /* _STANDALONE_ */
#include FT_INTERNAL_OBJECTS_H
#include FT_INTERNAL_DEBUG_H /* for FT_TRACE() and FT_ERROR() */
#include "rasterrs.h"
#define Raster_Err_None Raster_Err_Ok
#define Raster_Err_Not_Ini Raster_Err_Raster_Uninitialized
#define Raster_Err_Overflow Raster_Err_Raster_Overflow
#define Raster_Err_Neg_Height Raster_Err_Raster_Negative_Height
#define Raster_Err_Invalid Raster_Err_Invalid_Outline
#define Raster_Err_Unsupported Raster_Err_Cannot_Render_Glyph
#endif /* _STANDALONE_ */
#ifndef FT_MEM_SET
#define FT_MEM_SET( d, s, c ) ft_memset( d, s, c )
#endif
#ifndef FT_MEM_ZERO
#define FT_MEM_ZERO( dest, count ) FT_MEM_SET( dest, 0, count )
#endif
/* FMulDiv means `Fast MulDiv'; it is used in case where `b' is */
/* typically a small value and the result of a*b is known to fit into */
/* 32 bits. */
#define FMulDiv( a, b, c ) ( (a) * (b) / (c) )
/* On the other hand, SMulDiv means `Slow MulDiv', and is used typically */
/* for clipping computations. It simply uses the FT_MulDiv() function */
/* defined in `ftcalc.h'. */
#define SMulDiv FT_MulDiv
/* The rasterizer is a very general purpose component; please leave */
/* the following redefinitions there (you never know your target */
/* environment). */
#ifndef TRUE
#define TRUE 1
#endif
#ifndef FALSE
#define FALSE 0
#endif
#ifndef NULL
#define NULL (void*)0
#endif
#ifndef SUCCESS
#define SUCCESS 0
#endif
#ifndef FAILURE
#define FAILURE 1
#endif
#define MaxBezier 32 /* The maximum number of stacked Bezier curves. */
/* Setting this constant to more than 32 is a */
/* pure waste of space. */
#define Pixel_Bits 6 /* fractional bits of *input* coordinates */
/*************************************************************************/
/*************************************************************************/
/** **/
/** SIMPLE TYPE DECLARATIONS **/
/** **/
/*************************************************************************/
/*************************************************************************/
typedef int Int;
typedef unsigned int UInt;
typedef short Short;
typedef unsigned short UShort, *PUShort;
typedef long Long, *PLong;
typedef unsigned long ULong;
typedef unsigned char Byte, *PByte;
typedef char Bool;
typedef union Alignment_
{
long l;
void* p;
void (*f)(void);
} Alignment, *PAlignment;
typedef struct TPoint_
{
Long x;
Long y;
} TPoint;
typedef enum TFlow_
{
Flow_None = 0,
Flow_Up = 1,
Flow_Down = -1
} TFlow;
/* States of each line, arc, and profile */
typedef enum TStates_
{
Unknown_State,
Ascending_State,
Descending_State,
Flat_State
} TStates;
typedef struct TProfile_ TProfile;
typedef TProfile* PProfile;
struct TProfile_
{
FT_F26Dot6 X; /* current coordinate during sweep */
PProfile link; /* link to next profile - various purpose */
PLong offset; /* start of profile's data in render pool */
int flow; /* Profile orientation: Asc/Descending */
long height; /* profile's height in scanlines */
long start; /* profile's starting scanline */
unsigned countL; /* number of lines to step before this */
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -