透明和模版(pattern) 作图



void drawing_mode(int mode, BITMAP *pattern, int x_anchor, int y_anchor);
设置图形作图模式. 这只针对几何例程有效, 就是像 putpixel, lines, rectangles, circles, polygons, floodfill, 等等, 对文字输出, blit, 或精灵作图函数无效. 这个模式必须 是以下值中的一个:

      DRAW_MODE_SOLID               - 缺省值, 实心颜色填充
      DRAW_MODE_XOR                 - 异或作图
      DRAW_MODE_COPY_PATTERN        - 多色彩模式填充
      DRAW_MODE_SOLID_PATTERN       - 单色模式填充
      DRAW_MODE_MASKED_PATTERN      - 掩式模式填充
      DRAW_MODE_TRANS               - 透明色混合

在 DRAW_MODE_XOR 里, 画向位图的点将经过异或运算 而不是简单的复制, 因此在同一位置画第二次将删除上次的. 因为它涉及到即读又写位图存储器, xor 作图比普通的覆盖模式要慢的多.

在模版模式模式下, 你需要提供一个模版位图它将被平铺在 图形表面上. Allegro 储存这个位图的指针 而不是复制它, 因此你必须在它还在做模版用途的过程中不要撤销位图. 模版的宽和高必须是 2 的次方数, 但可以相互不同, 例如, 可以是一个 64x16 的模版, 但不能是 17x3 的. 模版平铺开始于点 (x_anchor, y_anchor) 处的栅格里. 通常你应该将传入值置为零, 这让你可以画临近的图形而使得模版 精确的沿着共享边界碰在一起. 然而,零对齐在你在整个屏幕内移动模版图形使 看起来很奇特, 这是因为 图形将移动但模版对齐不会, 因此在一些 情况下你可能希望改变 anchor 位置.

当你选择 DRAW_MODE_COPY_PATTERN, 点将简单的从模版位图复制到 目标位图. 这个允许你使用 多色彩的模版, 就是说你传入绘图例程的颜色将被忽略掉. 这是最快的模版模式.

在 DRAW_MODE_SOLID_PATTERN 模式下, 模版位图里的每个点将和 掩色比较, 就是指的 256 色模式下的零或 真彩数据里的亮粉红 (红蓝值最大, 绿值为零). 如果模版点是实心的, 你传给绘图例程的点颜色将 写到目标位图上, 否则将写上零. 模版将被看作是单色位掩图, 它允许你使用一些 模版去以不同的颜色去画不同的图形, 但是要防止使用 多重色彩模版.

DRAW_MODE_MASKED_PATTERN 几乎完全和 DRAW_MODE_SOLID_PATTERN 一样, 但是被掩盖的点被忽略了而不是被写为零, 因此 背景色会透过缺口显示出来.

在 DRAW_MODE_TRANS 模式下, 全局 color_map 表或真彩混合 函数被用来最上层存在的图片上的点. 这 必须仅在你已经设置了掩色映射表 (256 色模式) 或混合映射表 (真彩模式) 后才能使用. 因为它涉及到了 读写位图内存, 半透明作图在你 直接写向显存时很慢, 因此无论什么情况你都应当 使用内存位图来替代.

void xor_mode(int xor);
这是打开关闭 xor 作图的快捷方式. 调用 xor_mode(TRUE) 等于 drawing_mode(DRAW_MODE_XOR, NULL, 0, 0);

void solid_mode();
这是选择实心作图模式的快捷方式. 它等于 调用 drawing_mode(DRAW_MODE_SOLID, NULL, 0, 0);


在调色板显示模式下, 透明和光影效果由一个 64k 查询表来实现, 它包含了混合两个颜色 c1 和 c2 的结果值. 你必须在你使用任何光影或透明例程之前设置这个表. 取决于你怎样建造这个表, 可以实现一组不同的效果. 例如, 透明可以 使用 c1 和 c2 颜色值的一半来作为混合值来实现. 光影由以许多颜色中的一个的光亮级别 (1-255) 而不是这一个颜色来处理色彩, 然后设置专用表来实现. 可以有许多指定效果, 比如将任一颜色替换成任一其他颜色 使特定的许多源色或许多目标色完全变为同一色彩或不可见的.


颜色映射表可以使用色彩映射工具预先计算好, 或者 运行时产生. COLOR_MAP 结构是这样定义:

typedef struct {
   unsigned char data[PAL_SIZE][PAL_SIZE];
} COLOR_MAP;

extern COLOR_MAP *color_map;
指向颜色映射表的全局指针. 它必须在使用 任何 256 颜色模式下的半透明或光影作图函数前设置!

void create_light_table(COLOR_MAP *table, PALETTE pal, int r, g, b, void (*callback)(int pos));
以查找数据填充指定的色彩映射表用来实现在指定的调色板下的 光影效果. 当用这个表来组合颜色 c1 和 c2 时, c1 被看作是 0-255 之间的亮度级别. 当 光亮级为 255 时表将输出不变化的颜色 c2, 在光亮级为 0 时它将输出你指定这个函数的 r,g,b 值, 在居中的光亮级上它将输出两个极端值中某处的一个颜色. 如果回叫函数不为 NULL, 它将在计算期间调用 256 次这个函数, 允许你显示一个进展指示器.


void create_trans_table(COLOR_MAP *table, PALETTE pal, int r, g, b, void (*callback)(int pos));
以查找数据填充指定的色彩映射表用来在指定的调色板下做 透明效果. 当以这个表来 组合颜色 c1 和 c2 时, 结果将是两个颜色间的某处颜色. r,g,b 参数指定了每个颜色组合中的实心成分, 范围从 0 (完全透明) 到 255 (完全实心). 如果是 50% 实心, 传入 128. 这个函数将源色 #0 作为一个特例, 将目标中的对应源图中零的位置不作改变, 因此掩式精灵将被正确的画出来. 如果回叫函数不为 NULL, 它将在计算过程中被调用 256 次, 允许你显示一个进程指示器.

void create_color_table(COLOR_MAP *table, PALETTE pal, RGB (*blend)(PALETTE pal, int x, int y), void (*callback)(int pos));
以查找数据填充指定的色彩映射表用来在指定的调色板下做 用户定义的效果, 其调用混合函数来检测 每个颜色组合的结果. 你的混合例程 将被传入一个调色板的指针和两个将被组合的颜色, 它必须返回一个 RGB (0-63) 格式的结果. Allegro 将接下来搜索调色板来求得你请求的最接近的 RGB 颜色匹配, 因此如果调色板没有准确的颜色匹配也没有关系. 如果回叫函数不为 NULL, 它将 在计算过程中被调用 256 次, 允许你来显示一个 进程指示器.


在真彩显示模式, 透明和光影由 一组混合函数形式提供:

unsigned long (*BLENDER_FUNC)(unsigned long x, unsigned long y);

这个例程有两个颜色参数, 将他们分解成红, 绿, 蓝 的组合, 将他们以合适的任何方式组合, 然后合并起来成一个返回值. 为了支持阿尔法变换 (即不同的透明量或光亮级), 混合函数有 256 个版本: 每一个针对一个阿尔法值. 这些储存在一个表里:

typedef struct {
   BLENDER_FUNC blend[256];
} BLENDER_MAP;

既然这些例程可以用在不同的颜色深度值上, 所以有三个这样的表, 一个用于 15 位 5.5.5 点, 一个用于 16 位 5.6.5 点, 一个用于 24 位 8.8.8 点 (这可以被 24 和 32 位代码共享, 因为位分配形式是一样的).

void set_trans_blender(int r, int g, int b, int a);
设置真彩混合例程的缺省集合, 它在 源色和目标色之间做了一个简单的线形填入. 当透明作图函数被调用, 被这个例程设置的 alpha 参数 被用来从表里选择一个混合器, 然后 函数调用它混合目标图上存在的颜色的每个点 (即: alpha 参数控制控制着作图的实质, 从 0 到 255). 当光影精灵作图函数被调用, 传入这个例程的 alpha 值被忽略, 取代它的是由 传入精灵函数的颜色值来选择一个阿尔法级. 混合例程将跟着用来向精灵颜色和 传入这个函数的 RGB 值 (范围 0-255) 间添入色彩.

void set_blender_mode(BLENDER_MAP *b15, *b16, *b24, int r, g, b, a);
指定一个用户设置的真彩混合例程的集合, 需要为每个可能的颜色 深度提供一个函数指针表 (如果你不打算使用某些点格式,这些参数可以 为 NULL).




返回