1d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann// Copyright 2017 PDFium Authors. All rights reserved.
2d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann// Use of this source code is governed by a BSD-style license that can be
3d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann// found in the LICENSE file.
4d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
5d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann// Original code copyright 2014 Foxit Software Inc. http://www.foxitsoftware.com
6d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
7d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann#include "core/fxge/dib/cfx_scanlinecompositor.h"
8d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
9d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann#include <algorithm>
10d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
11d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann#include "core/fxcodec/fx_codec.h"
12d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
13d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann#define FX_CCOLOR(val) (255 - (val))
14d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann#define FXDIB_ALPHA_UNION(dest, src) ((dest) + (src) - (dest) * (src) / 255)
15d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann#define FXARGB_COPY(dest, src)                    \
16d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  *(dest) = *(src), *((dest) + 1) = *((src) + 1), \
17d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  *((dest) + 2) = *((src) + 2), *((dest) + 3) = *((src) + 3)
18d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann#define FXARGB_RGBORDERCOPY(dest, src)                  \
19d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  *((dest) + 3) = *((src) + 3), *(dest) = *((src) + 2), \
20d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann             *((dest) + 1) = *((src) + 1), *((dest) + 2) = *((src))
21d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
22d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannnamespace {
23d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
24d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannconst uint8_t color_sqrt[256] = {
25d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    0x00, 0x03, 0x07, 0x0B, 0x0F, 0x12, 0x16, 0x19, 0x1D, 0x20, 0x23, 0x26,
26d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    0x29, 0x2C, 0x2F, 0x32, 0x35, 0x37, 0x3A, 0x3C, 0x3F, 0x41, 0x43, 0x46,
27d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    0x48, 0x4A, 0x4C, 0x4E, 0x50, 0x52, 0x54, 0x56, 0x57, 0x59, 0x5B, 0x5C,
28d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    0x5E, 0x60, 0x61, 0x63, 0x64, 0x65, 0x67, 0x68, 0x69, 0x6B, 0x6C, 0x6D,
29d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    0x6E, 0x70, 0x71, 0x72, 0x73, 0x74, 0x75, 0x76, 0x77, 0x78, 0x79, 0x7A,
30d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    0x7B, 0x7C, 0x7D, 0x7E, 0x80, 0x81, 0x82, 0x83, 0x84, 0x85, 0x86, 0x87,
31d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    0x87, 0x88, 0x89, 0x8A, 0x8B, 0x8C, 0x8D, 0x8E, 0x8F, 0x90, 0x91, 0x91,
32d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    0x92, 0x93, 0x94, 0x95, 0x96, 0x97, 0x97, 0x98, 0x99, 0x9A, 0x9B, 0x9C,
33d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    0x9C, 0x9D, 0x9E, 0x9F, 0xA0, 0xA0, 0xA1, 0xA2, 0xA3, 0xA4, 0xA4, 0xA5,
34d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    0xA6, 0xA7, 0xA7, 0xA8, 0xA9, 0xAA, 0xAA, 0xAB, 0xAC, 0xAD, 0xAD, 0xAE,
35d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    0xAF, 0xB0, 0xB0, 0xB1, 0xB2, 0xB3, 0xB3, 0xB4, 0xB5, 0xB5, 0xB6, 0xB7,
36d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    0xB7, 0xB8, 0xB9, 0xBA, 0xBA, 0xBB, 0xBC, 0xBC, 0xBD, 0xBE, 0xBE, 0xBF,
37d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    0xC0, 0xC0, 0xC1, 0xC2, 0xC2, 0xC3, 0xC4, 0xC4, 0xC5, 0xC6, 0xC6, 0xC7,
38d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    0xC7, 0xC8, 0xC9, 0xC9, 0xCA, 0xCB, 0xCB, 0xCC, 0xCC, 0xCD, 0xCE, 0xCE,
39d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    0xCF, 0xD0, 0xD0, 0xD1, 0xD1, 0xD2, 0xD3, 0xD3, 0xD4, 0xD4, 0xD5, 0xD6,
40d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    0xD6, 0xD7, 0xD7, 0xD8, 0xD9, 0xD9, 0xDA, 0xDA, 0xDB, 0xDC, 0xDC, 0xDD,
41d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    0xDD, 0xDE, 0xDE, 0xDF, 0xE0, 0xE0, 0xE1, 0xE1, 0xE2, 0xE2, 0xE3, 0xE4,
42d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    0xE4, 0xE5, 0xE5, 0xE6, 0xE6, 0xE7, 0xE7, 0xE8, 0xE9, 0xE9, 0xEA, 0xEA,
43d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    0xEB, 0xEB, 0xEC, 0xEC, 0xED, 0xED, 0xEE, 0xEE, 0xEF, 0xF0, 0xF0, 0xF1,
44d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    0xF1, 0xF2, 0xF2, 0xF3, 0xF3, 0xF4, 0xF4, 0xF5, 0xF5, 0xF6, 0xF6, 0xF7,
45d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    0xF7, 0xF8, 0xF8, 0xF9, 0xF9, 0xFA, 0xFA, 0xFB, 0xFB, 0xFC, 0xFC, 0xFD,
46d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    0xFD, 0xFE, 0xFE, 0xFF};
47d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
48d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannint Blend(int blend_mode, int back_color, int src_color) {
49d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  switch (blend_mode) {
50d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    case FXDIB_BLEND_NORMAL:
51d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      return src_color;
52d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    case FXDIB_BLEND_MULTIPLY:
53d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      return src_color * back_color / 255;
54d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    case FXDIB_BLEND_SCREEN:
55d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      return src_color + back_color - src_color * back_color / 255;
56d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    case FXDIB_BLEND_OVERLAY:
57d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      return Blend(FXDIB_BLEND_HARDLIGHT, src_color, back_color);
58d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    case FXDIB_BLEND_DARKEN:
59d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      return src_color < back_color ? src_color : back_color;
60d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    case FXDIB_BLEND_LIGHTEN:
61d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      return src_color > back_color ? src_color : back_color;
62d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    case FXDIB_BLEND_COLORDODGE: {
63d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (src_color == 255)
64d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        return src_color;
65d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
66d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      return std::min(back_color * 255 / (255 - src_color), 255);
67d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
68d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    case FXDIB_BLEND_COLORBURN: {
69d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (src_color == 0)
70d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        return src_color;
71d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
72d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      return 255 - std::min((255 - back_color) * 255 / src_color, 255);
73d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
74d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    case FXDIB_BLEND_HARDLIGHT:
75d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (src_color < 128)
76d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        return (src_color * back_color * 2) / 255;
77d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
78d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      return Blend(FXDIB_BLEND_SCREEN, back_color, 2 * src_color - 255);
79d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    case FXDIB_BLEND_SOFTLIGHT: {
80d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (src_color < 128) {
81d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        return back_color -
82d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann               (255 - 2 * src_color) * back_color * (255 - back_color) / 255 /
83d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                   255;
84d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
85d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      return back_color +
86d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann             (2 * src_color - 255) * (color_sqrt[back_color] - back_color) /
87d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                 255;
88d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
89d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    case FXDIB_BLEND_DIFFERENCE:
90d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      return back_color < src_color ? src_color - back_color
91d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                    : back_color - src_color;
92d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    case FXDIB_BLEND_EXCLUSION:
93d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      return back_color + src_color - 2 * back_color * src_color / 255;
94d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
95d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  return src_color;
96d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
97d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
98d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannstruct RGB {
99d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int red;
100d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int green;
101d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int blue;
102d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann};
103d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
104d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannint Lum(RGB color) {
105d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  return (color.red * 30 + color.green * 59 + color.blue * 11) / 100;
106d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
107d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
108d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. MoltmannRGB ClipColor(RGB color) {
109d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int l = Lum(color);
110d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int n = std::min(color.red, std::min(color.green, color.blue));
111d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int x = std::max(color.red, std::max(color.green, color.blue));
112d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  if (n < 0) {
113d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    color.red = l + ((color.red - l) * l / (l - n));
114d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    color.green = l + ((color.green - l) * l / (l - n));
115d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    color.blue = l + ((color.blue - l) * l / (l - n));
116d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
117d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  if (x > 255) {
118d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    color.red = l + ((color.red - l) * (255 - l) / (x - l));
119d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    color.green = l + ((color.green - l) * (255 - l) / (x - l));
120d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    color.blue = l + ((color.blue - l) * (255 - l) / (x - l));
121d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
122d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  return color;
123d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
124d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
125d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. MoltmannRGB SetLum(RGB color, int l) {
126d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int d = l - Lum(color);
127d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  color.red += d;
128d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  color.green += d;
129d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  color.blue += d;
130d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  return ClipColor(color);
131d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
132d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
133d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannint Sat(RGB color) {
134d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  return std::max(color.red, std::max(color.green, color.blue)) -
135d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann         std::min(color.red, std::min(color.green, color.blue));
136d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
137d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
138d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. MoltmannRGB SetSat(RGB color, int s) {
139d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int min = std::min(color.red, std::min(color.green, color.blue));
140d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int max = std::max(color.red, std::max(color.green, color.blue));
141d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  if (min == max)
142d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    return {0, 0, 0};
143d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
144d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  color.red = (color.red - min) * s / (max - min);
145d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  color.green = (color.green - min) * s / (max - min);
146d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  color.blue = (color.blue - min) * s / (max - min);
147d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  return color;
148d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
149d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
150d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid RGB_Blend(int blend_mode,
151d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann               const uint8_t* src_scan,
152d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann               const uint8_t* dest_scan,
153d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann               int results[3]) {
154d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  RGB result = {0, 0, 0};
155d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  RGB src;
156d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  src.red = src_scan[2];
157d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  src.green = src_scan[1];
158d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  src.blue = src_scan[0];
159d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  RGB back;
160d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  back.red = dest_scan[2];
161d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  back.green = dest_scan[1];
162d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  back.blue = dest_scan[0];
163d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  switch (blend_mode) {
164d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    case FXDIB_BLEND_HUE:
165d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      result = SetLum(SetSat(src, Sat(back)), Lum(back));
166d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      break;
167d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    case FXDIB_BLEND_SATURATION:
168d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      result = SetLum(SetSat(back, Sat(src)), Lum(back));
169d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      break;
170d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    case FXDIB_BLEND_COLOR:
171d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      result = SetLum(src, Lum(back));
172d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      break;
173d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    case FXDIB_BLEND_LUMINOSITY:
174d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      result = SetLum(back, Lum(src));
175d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      break;
176d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
177d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  results[0] = result.blue;
178d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  results[1] = result.green;
179d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  results[2] = result.red;
180d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
181d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
182d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannint GetAlpha(uint8_t src_alpha, const uint8_t* clip_scan, int col) {
183d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  return clip_scan ? clip_scan[col] * src_alpha / 255 : src_alpha;
184d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
185d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
186d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_AlphaToMask(uint8_t* dest_scan,
187d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                              const uint8_t* src_scan,
188d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                              int pixel_count,
189d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                              const uint8_t* clip_scan,
190d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                              uint8_t stride) {
191d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  src_scan += stride - 1;
192d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < pixel_count; ++col) {
193d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int src_alpha = GetAlpha(*src_scan, clip_scan, col);
194d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t back_alpha = *dest_scan;
195d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (!back_alpha)
196d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = src_alpha;
197d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    else if (src_alpha)
198d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = back_alpha + src_alpha - back_alpha * src_alpha / 255;
199d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    ++dest_scan;
200d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    src_scan += stride;
201d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
202d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
203d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
204d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_Rgb2Mask(uint8_t* dest_scan,
205d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                           const uint8_t* src_scan,
206d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                           int width,
207d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                           const uint8_t* clip_scan) {
208d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  if (!clip_scan) {
209d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    memset(dest_scan, 0xff, width);
210d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    return;
211d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
212d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int i = 0; i < width; ++i) {
213d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    *dest_scan = FXDIB_ALPHA_UNION(*dest_scan, *clip_scan);
214d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    ++dest_scan;
215d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    ++clip_scan;
216d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
217d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
218d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
219d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannuint8_t GetGray(const uint8_t* src_scan) {
220d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  return FXRGB2GRAY(src_scan[2], src_scan[1], *src_scan);
221d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
222d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
223d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannuint8_t GetGrayWithBlend(const uint8_t* src_scan,
224d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                         const uint8_t* dest_scan,
225d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                         int blend_type) {
226d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  uint8_t gray = GetGray(src_scan);
227d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  if (blend_type >= FXDIB_BLEND_NONSEPARABLE)
228d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    gray = blend_type == FXDIB_BLEND_LUMINOSITY ? gray : *dest_scan;
229d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  else if (blend_type)
230d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    gray = Blend(blend_type, *dest_scan, gray);
231d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  return gray;
232d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
233d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
234d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_Argb2Graya(uint8_t* dest_scan,
235d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                             const uint8_t* src_scan,
236d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                             int pixel_count,
237d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                             int blend_type,
238d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                             const uint8_t* clip_scan,
239d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                             const uint8_t* src_alpha_scan,
240d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                             uint8_t* dst_alpha_scan) {
241d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  uint8_t offset = src_alpha_scan ? 3 : 4;
242d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < pixel_count; ++col) {
243d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    const uint8_t* alpha_scan =
244d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        src_alpha_scan ? src_alpha_scan++ : &src_scan[3];
245d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t back_alpha = *dst_alpha_scan;
246d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (back_alpha == 0) {
247d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int src_alpha = GetAlpha(*alpha_scan, clip_scan, col);
248d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (src_alpha) {
249d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan = GetGray(src_scan);
250d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dst_alpha_scan = src_alpha;
251d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
252d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      ++dest_scan;
253d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      ++dst_alpha_scan;
254d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan += offset;
255d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
256d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
257d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t src_alpha = GetAlpha(*alpha_scan, clip_scan, col);
258d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (src_alpha == 0) {
259d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      ++dest_scan;
260d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      ++dst_alpha_scan;
261d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan += offset;
262d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
263d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
264d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    *dst_alpha_scan = FXDIB_ALPHA_UNION(back_alpha, src_alpha);
265d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int alpha_ratio = src_alpha * 255 / (*dst_alpha_scan);
266d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t gray = GetGray(src_scan);
267d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    // TODO(npm): Does this if really need src_alpha_scan or was that a bug?
268d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (blend_type && src_alpha_scan) {
269d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (blend_type >= FXDIB_BLEND_NONSEPARABLE)
270d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        gray = blend_type == FXDIB_BLEND_LUMINOSITY ? gray : *dest_scan;
271d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      else
272d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        gray = Blend(blend_type, *dest_scan, gray);
273d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
274d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, gray, alpha_ratio);
275d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    ++dest_scan;
276d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    ++dst_alpha_scan;
277d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    src_scan += offset;
278d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
279d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
280d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
281d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_Argb2Gray(uint8_t* dest_scan,
282d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                            const uint8_t* src_scan,
283d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                            int pixel_count,
284d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                            int blend_type,
285d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                            const uint8_t* clip_scan,
286d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                            const uint8_t* src_alpha_scan) {
287d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  uint8_t gray;
288d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  uint8_t offset = src_alpha_scan ? 3 : 4;
289d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < pixel_count; ++col) {
290d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    const uint8_t* alpha_scan =
291d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        src_alpha_scan ? src_alpha_scan++ : &src_scan[3];
292d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int src_alpha = GetAlpha(*alpha_scan, clip_scan, col);
293d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (src_alpha) {
294d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      gray = GetGrayWithBlend(src_scan, dest_scan, blend_type);
295d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, gray, src_alpha);
296d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
297d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    ++dest_scan;
298d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    src_scan += offset;
299d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
300d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
301d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
302d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_Rgb2Gray(uint8_t* dest_scan,
303d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                           const uint8_t* src_scan,
304d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                           int src_Bpp,
305d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                           int pixel_count,
306d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                           int blend_type,
307d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                           const uint8_t* clip_scan) {
308d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  uint8_t gray;
309d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < pixel_count; ++col) {
310d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    gray = GetGrayWithBlend(src_scan, dest_scan, blend_type);
311d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (clip_scan && clip_scan[col] < 255)
312d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, gray, clip_scan[col]);
313d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    else
314d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = gray;
315d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    ++dest_scan;
316d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    src_scan += src_Bpp;
317d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
318d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
319d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
320d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_Rgb2Graya(uint8_t* dest_scan,
321d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                            const uint8_t* src_scan,
322d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                            int src_Bpp,
323d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                            int pixel_count,
324d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                            int blend_type,
325d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                            const uint8_t* clip_scan,
326d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                            uint8_t* dest_alpha_scan) {
327d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < pixel_count; ++col) {
328d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (blend_type && *dest_alpha_scan == 0) {
329d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = GetGray(src_scan);
330d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      ++dest_scan;
331d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      ++dest_alpha_scan;
332d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan += src_Bpp;
333d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
334d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
335d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int src_alpha = clip_scan ? clip_scan[col] : 255;
336d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (src_alpha == 255) {
337d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = GetGrayWithBlend(src_scan, dest_scan, blend_type);
338d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      ++dest_scan;
339d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_alpha_scan = 255;
340d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      ++dest_alpha_scan;
341d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan += src_Bpp;
342d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
343d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
344d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (src_alpha == 0) {
345d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      ++dest_scan;
346d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      ++dest_alpha_scan;
347d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan += src_Bpp;
348d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
349d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
350d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int back_alpha = *dest_alpha_scan;
351d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t dest_alpha = back_alpha + src_alpha - back_alpha * src_alpha / 255;
352d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    *dest_alpha_scan = dest_alpha;
353d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    ++dest_alpha_scan;
354d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int alpha_ratio = src_alpha * 255 / dest_alpha;
355d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t gray = GetGrayWithBlend(src_scan, dest_scan, blend_type);
356d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, gray, alpha_ratio);
357d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    ++dest_scan;
358d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    src_scan += src_Bpp;
359d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
360d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
361d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
362d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_Argb2Argb(uint8_t* dest_scan,
363d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                            const uint8_t* src_scan,
364d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                            int pixel_count,
365d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                            int blend_type,
366d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                            const uint8_t* clip_scan,
367d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                            uint8_t* dest_alpha_scan,
368d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                            const uint8_t* src_alpha_scan) {
369d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int blended_colors[3];
370d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  uint8_t dest_offset = dest_alpha_scan ? 3 : 4;
371d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  uint8_t src_offset = src_alpha_scan ? 3 : 4;
372d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  bool bNonseparableBlend = blend_type >= FXDIB_BLEND_NONSEPARABLE;
373d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  bool has_src = !!src_alpha_scan;
374d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  bool has_dest = !!dest_alpha_scan;
375d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < pixel_count; ++col) {
376d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t back_alpha = has_dest ? *dest_alpha_scan : dest_scan[3];
377d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    const uint8_t* alpha_source = has_src ? src_alpha_scan++ : &src_scan[3];
378d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t src_alpha = GetAlpha(*alpha_source, clip_scan, col);
379d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (back_alpha == 0) {
380d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (!has_dest && !has_src) {
381d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        if (clip_scan) {
382d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          FXARGB_SETDIB(dest_scan, (FXARGB_GETDIB(src_scan) & 0xffffff) |
383d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                       (src_alpha << 24));
384d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        } else {
385d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          FXARGB_COPY(dest_scan, src_scan);
386d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        }
387d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      } else if (has_dest) {
388d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_alpha_scan = src_alpha;
389d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        for (int i = 0; i < 3; ++i) {
390d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          *dest_scan = *src_scan++;
391d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          ++dest_scan;
392d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        }
393d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        ++dest_alpha_scan;
394d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        if (!has_src)
395d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          ++src_scan;
396d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      } else {
397d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        FXARGB_SETDIB(dest_scan, FXARGB_MAKE((src_alpha << 24), src_scan[2],
398d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                             src_scan[1], *src_scan));
399d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
400d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (!has_dest) {
401d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan += dest_offset;
402d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        src_scan += src_offset;
403d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
404d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
405d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
406d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (src_alpha == 0) {
407d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += dest_offset;
408d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan += src_offset;
409d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (has_dest)
410d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        ++dest_alpha_scan;
411d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
412d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
413d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t dest_alpha = back_alpha + src_alpha - back_alpha * src_alpha / 255;
414d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (has_dest) {
415d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_alpha_scan = dest_alpha;
416d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      ++dest_alpha_scan;
417d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
418d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[3] = dest_alpha;
419d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
420d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int alpha_ratio = src_alpha * 255 / dest_alpha;
421d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (bNonseparableBlend)
422d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      RGB_Blend(blend_type, src_scan, dest_scan, blended_colors);
423d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    for (int color = 0; color < 3; ++color) {
424d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (blend_type) {
425d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        int blended = bNonseparableBlend
426d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                          ? blended_colors[color]
427d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                          : Blend(blend_type, *dest_scan, *src_scan);
428d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        blended = FXDIB_ALPHA_MERGE(*src_scan, blended, back_alpha);
429d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, blended, alpha_ratio);
430d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      } else {
431d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, *src_scan, alpha_ratio);
432d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
433d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      ++dest_scan;
434d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      ++src_scan;
435d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
436d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (!has_dest)
437d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      ++dest_scan;
438d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (!has_src)
439d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      ++src_scan;
440d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
441d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
442d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
443d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_Rgb2Argb_Blend_NoClip(uint8_t* dest_scan,
444d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                        const uint8_t* src_scan,
445d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                        int width,
446d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                        int blend_type,
447d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                        int src_Bpp,
448d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                        uint8_t* dest_alpha_scan) {
449d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int blended_colors[3];
450d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  bool bNonseparableBlend = blend_type >= FXDIB_BLEND_NONSEPARABLE;
451d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int src_gap = src_Bpp - 3;
452d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < width; ++col) {
453d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t* dest_alpha = dest_alpha_scan ? dest_alpha_scan : &dest_scan[3];
454d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t back_alpha = *dest_alpha;
455d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (back_alpha == 0) {
456d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (dest_alpha_scan) {
457d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        for (int i = 0; i < 3; ++i) {
458d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          *dest_scan = *src_scan++;
459d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          ++dest_scan;
460d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        }
461d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_alpha_scan = 0xff;
462d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        ++dest_alpha_scan;
463d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      } else {
464d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        if (src_Bpp == 4) {
465d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          FXARGB_SETDIB(dest_scan, 0xff000000 | FXARGB_GETDIB(src_scan));
466d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        } else {
467d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          FXARGB_SETDIB(dest_scan, FXARGB_MAKE(0xff, src_scan[2], src_scan[1],
468d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                               src_scan[0]));
469d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        }
470d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan += 4;
471d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
472d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan += src_Bpp;
473d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
474d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
475d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    *dest_alpha = 0xff;
476d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (bNonseparableBlend)
477d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      RGB_Blend(blend_type, src_scan, dest_scan, blended_colors);
478d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    for (int color = 0; color < 3; ++color) {
479d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int src_color = *src_scan;
480d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int blended = bNonseparableBlend
481d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                        ? blended_colors[color]
482d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                        : Blend(blend_type, *dest_scan, src_color);
483d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(src_color, blended, back_alpha);
484d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      ++dest_scan;
485d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      ++src_scan;
486d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
487d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (dest_alpha_scan)
488d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      ++dest_alpha_scan;
489d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    else
490d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      ++dest_scan;
491d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    src_scan += src_gap;
492d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
493d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
494d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
495d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_Rgb2Argb_Blend_Clip(uint8_t* dest_scan,
496d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                      const uint8_t* src_scan,
497d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                      int width,
498d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                      int blend_type,
499d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                      int src_Bpp,
500d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                      const uint8_t* clip_scan,
501d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                      uint8_t* dest_alpha_scan) {
502d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int blended_colors[3];
503d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  bool bNonseparableBlend = blend_type >= FXDIB_BLEND_NONSEPARABLE;
504d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int src_gap = src_Bpp - 3;
505d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  bool has_dest = !!dest_alpha_scan;
506d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < width; ++col) {
507d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int src_alpha = *clip_scan++;
508d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t back_alpha = has_dest ? *dest_alpha_scan : dest_scan[3];
509d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (back_alpha == 0) {
510d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      for (int i = 0; i < 3; ++i) {
511d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan = *src_scan++;
512d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        ++dest_scan;
513d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
514d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan += src_gap;
515d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (has_dest)
516d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_alpha_scan++;
517d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      else
518d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan++;
519d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
520d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
521d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (src_alpha == 0) {
522d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += has_dest ? 3 : 4;
523d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (has_dest)
524d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_alpha_scan++;
525d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan += src_Bpp;
526d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
527d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
528d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t dest_alpha = back_alpha + src_alpha - back_alpha * src_alpha / 255;
529d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (has_dest)
530d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_alpha_scan++ = dest_alpha;
531d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    else
532d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[3] = dest_alpha;
533d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int alpha_ratio = src_alpha * 255 / dest_alpha;
534d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (bNonseparableBlend)
535d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      RGB_Blend(blend_type, src_scan, dest_scan, blended_colors);
536d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    for (int color = 0; color < 3; color++) {
537d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int src_color = *src_scan;
538d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int blended = bNonseparableBlend
539d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                        ? blended_colors[color]
540d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                        : Blend(blend_type, *dest_scan, src_color);
541d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      blended = FXDIB_ALPHA_MERGE(src_color, blended, back_alpha);
542d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, blended, alpha_ratio);
543d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
544d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan++;
545d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
546d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    src_scan += src_gap;
547d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (!has_dest)
548d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
549d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
550d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
551d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
552d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_Rgb2Argb_NoBlend_Clip(uint8_t* dest_scan,
553d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                        const uint8_t* src_scan,
554d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                        int width,
555d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                        int src_Bpp,
556d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                        const uint8_t* clip_scan,
557d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                        uint8_t* dest_alpha_scan) {
558d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int src_gap = src_Bpp - 3;
559d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  if (dest_alpha_scan) {
560d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    for (int col = 0; col < width; col++) {
561d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int src_alpha = clip_scan[col];
562d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (src_alpha == 255) {
563d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan++ = *src_scan++;
564d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan++ = *src_scan++;
565d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan++ = *src_scan++;
566d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_alpha_scan++ = 255;
567d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        src_scan += src_gap;
568d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        continue;
569d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
570d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (src_alpha == 0) {
571d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan += 3;
572d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_alpha_scan++;
573d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        src_scan += src_Bpp;
574d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        continue;
575d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
576d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int back_alpha = *dest_alpha_scan;
577d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t dest_alpha =
578d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          back_alpha + src_alpha - back_alpha * src_alpha / 255;
579d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_alpha_scan++ = dest_alpha;
580d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int alpha_ratio = src_alpha * 255 / dest_alpha;
581d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      for (int color = 0; color < 3; color++) {
582d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, *src_scan, alpha_ratio);
583d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan++;
584d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        src_scan++;
585d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
586d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan += src_gap;
587d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
588d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  } else {
589d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    for (int col = 0; col < width; col++) {
590d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int src_alpha = clip_scan[col];
591d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (src_alpha == 255) {
592d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan++ = *src_scan++;
593d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan++ = *src_scan++;
594d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan++ = *src_scan++;
595d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan++ = 255;
596d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        src_scan += src_gap;
597d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        continue;
598d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
599d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (src_alpha == 0) {
600d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan += 4;
601d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        src_scan += src_Bpp;
602d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        continue;
603d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
604d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int back_alpha = dest_scan[3];
605d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t dest_alpha =
606d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          back_alpha + src_alpha - back_alpha * src_alpha / 255;
607d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[3] = dest_alpha;
608d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int alpha_ratio = src_alpha * 255 / dest_alpha;
609d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      for (int color = 0; color < 3; color++) {
610d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, *src_scan, alpha_ratio);
611d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan++;
612d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        src_scan++;
613d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
614d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
615d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan += src_gap;
616d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
617d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
618d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
619d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
620d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_Rgb2Argb_NoBlend_NoClip(uint8_t* dest_scan,
621d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                          const uint8_t* src_scan,
622d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                          int width,
623d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                          int src_Bpp,
624d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                          uint8_t* dest_alpha_scan) {
625d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  if (dest_alpha_scan) {
626d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int src_gap = src_Bpp - 3;
627d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    for (int col = 0; col < width; col++) {
628d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan++ = *src_scan++;
629d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan++ = *src_scan++;
630d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan++ = *src_scan++;
631d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_alpha_scan++ = 0xff;
632d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan += src_gap;
633d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
634d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  } else {
635d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    for (int col = 0; col < width; col++) {
636d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (src_Bpp == 4) {
637d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        FXARGB_SETDIB(dest_scan, 0xff000000 | FXARGB_GETDIB(src_scan));
638d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      } else {
639d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        FXARGB_SETDIB(dest_scan,
640d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                      FXARGB_MAKE(0xff, src_scan[2], src_scan[1], src_scan[0]));
641d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
642d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += 4;
643d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan += src_Bpp;
644d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
645d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
646d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
647d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
648d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_Argb2Rgb_Blend(uint8_t* dest_scan,
649d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                 const uint8_t* src_scan,
650d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                 int width,
651d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                 int blend_type,
652d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                 int dest_Bpp,
653d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                 const uint8_t* clip_scan,
654d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                 const uint8_t* src_alpha_scan) {
655d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int blended_colors[3];
656d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  bool bNonseparableBlend = blend_type >= FXDIB_BLEND_NONSEPARABLE;
657d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int dest_gap = dest_Bpp - 3;
658d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  if (src_alpha_scan) {
659d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    for (int col = 0; col < width; col++) {
660d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t src_alpha;
661d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (clip_scan) {
662d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        src_alpha = (*src_alpha_scan++) * (*clip_scan++) / 255;
663d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      } else {
664d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        src_alpha = *src_alpha_scan++;
665d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
666d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (src_alpha == 0) {
667d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan += dest_Bpp;
668d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        src_scan += 3;
669d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        continue;
670d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
671d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (bNonseparableBlend) {
672d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        RGB_Blend(blend_type, src_scan, dest_scan, blended_colors);
673d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
674d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      for (int color = 0; color < 3; color++) {
675d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        int back_color = *dest_scan;
676d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        int blended = bNonseparableBlend
677d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                          ? blended_colors[color]
678d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                          : Blend(blend_type, back_color, *src_scan);
679d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan = FXDIB_ALPHA_MERGE(back_color, blended, src_alpha);
680d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan++;
681d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        src_scan++;
682d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
683d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += dest_gap;
684d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
685d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  } else {
686d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    for (int col = 0; col < width; col++) {
687d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t src_alpha;
688d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (clip_scan) {
689d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        src_alpha = src_scan[3] * (*clip_scan++) / 255;
690d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      } else {
691d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        src_alpha = src_scan[3];
692d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
693d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (src_alpha == 0) {
694d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan += dest_Bpp;
695d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        src_scan += 4;
696d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        continue;
697d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
698d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (bNonseparableBlend) {
699d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        RGB_Blend(blend_type, src_scan, dest_scan, blended_colors);
700d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
701d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      for (int color = 0; color < 3; color++) {
702d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        int back_color = *dest_scan;
703d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        int blended = bNonseparableBlend
704d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                          ? blended_colors[color]
705d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                          : Blend(blend_type, back_color, *src_scan);
706d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan = FXDIB_ALPHA_MERGE(back_color, blended, src_alpha);
707d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan++;
708d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        src_scan++;
709d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
710d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += dest_gap;
711d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan++;
712d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
713d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
714d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
715d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
716d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_Argb2Rgb_NoBlend(uint8_t* dest_scan,
717d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                   const uint8_t* src_scan,
718d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                   int width,
719d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                   int dest_Bpp,
720d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                   const uint8_t* clip_scan,
721d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                   const uint8_t* src_alpha_scan) {
722d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int dest_gap = dest_Bpp - 3;
723d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  if (src_alpha_scan) {
724d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    for (int col = 0; col < width; col++) {
725d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t src_alpha;
726d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (clip_scan) {
727d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        src_alpha = (*src_alpha_scan++) * (*clip_scan++) / 255;
728d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      } else {
729d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        src_alpha = *src_alpha_scan++;
730d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
731d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (src_alpha == 255) {
732d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan++ = *src_scan++;
733d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan++ = *src_scan++;
734d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan++ = *src_scan++;
735d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan += dest_gap;
736d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        continue;
737d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
738d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (src_alpha == 0) {
739d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan += dest_Bpp;
740d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        src_scan += 3;
741d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        continue;
742d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
743d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      for (int color = 0; color < 3; color++) {
744d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, *src_scan, src_alpha);
745d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan++;
746d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        src_scan++;
747d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
748d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += dest_gap;
749d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
750d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  } else {
751d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    for (int col = 0; col < width; col++) {
752d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t src_alpha;
753d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (clip_scan) {
754d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        src_alpha = src_scan[3] * (*clip_scan++) / 255;
755d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      } else {
756d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        src_alpha = src_scan[3];
757d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
758d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (src_alpha == 255) {
759d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan++ = *src_scan++;
760d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan++ = *src_scan++;
761d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan++ = *src_scan++;
762d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan += dest_gap;
763d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        src_scan++;
764d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        continue;
765d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
766d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (src_alpha == 0) {
767d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan += dest_Bpp;
768d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        src_scan += 4;
769d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        continue;
770d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
771d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      for (int color = 0; color < 3; color++) {
772d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, *src_scan, src_alpha);
773d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan++;
774d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        src_scan++;
775d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
776d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += dest_gap;
777d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan++;
778d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
779d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
780d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
781d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
782d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_Rgb2Rgb_Blend_NoClip(uint8_t* dest_scan,
783d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                       const uint8_t* src_scan,
784d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                       int width,
785d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                       int blend_type,
786d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                       int dest_Bpp,
787d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                       int src_Bpp) {
788d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int blended_colors[3];
789d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  bool bNonseparableBlend = blend_type >= FXDIB_BLEND_NONSEPARABLE;
790d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int dest_gap = dest_Bpp - 3;
791d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int src_gap = src_Bpp - 3;
792d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < width; col++) {
793d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (bNonseparableBlend) {
794d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      RGB_Blend(blend_type, src_scan, dest_scan, blended_colors);
795d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
796d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    for (int color = 0; color < 3; color++) {
797d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int back_color = *dest_scan;
798d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int src_color = *src_scan;
799d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int blended = bNonseparableBlend
800d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                        ? blended_colors[color]
801d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                        : Blend(blend_type, back_color, src_color);
802d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = blended;
803d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
804d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan++;
805d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
806d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan += dest_gap;
807d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    src_scan += src_gap;
808d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
809d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
810d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
811d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_Rgb2Rgb_Blend_Clip(uint8_t* dest_scan,
812d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                     const uint8_t* src_scan,
813d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                     int width,
814d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                     int blend_type,
815d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                     int dest_Bpp,
816d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                     int src_Bpp,
817d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                     const uint8_t* clip_scan) {
818d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int blended_colors[3];
819d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  bool bNonseparableBlend = blend_type >= FXDIB_BLEND_NONSEPARABLE;
820d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int dest_gap = dest_Bpp - 3;
821d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int src_gap = src_Bpp - 3;
822d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < width; col++) {
823d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t src_alpha = *clip_scan++;
824d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (src_alpha == 0) {
825d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += dest_Bpp;
826d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan += src_Bpp;
827d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
828d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
829d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (bNonseparableBlend) {
830d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      RGB_Blend(blend_type, src_scan, dest_scan, blended_colors);
831d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
832d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    for (int color = 0; color < 3; color++) {
833d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int src_color = *src_scan;
834d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int back_color = *dest_scan;
835d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int blended = bNonseparableBlend
836d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                        ? blended_colors[color]
837d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                        : Blend(blend_type, back_color, src_color);
838d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(back_color, blended, src_alpha);
839d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
840d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan++;
841d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
842d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan += dest_gap;
843d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    src_scan += src_gap;
844d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
845d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
846d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
847d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_Rgb2Rgb_NoBlend_NoClip(uint8_t* dest_scan,
848d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                         const uint8_t* src_scan,
849d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                         int width,
850d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                         int dest_Bpp,
851d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                         int src_Bpp) {
852d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  if (dest_Bpp == src_Bpp) {
853d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    memcpy(dest_scan, src_scan, width * dest_Bpp);
854d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    return;
855d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
856d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < width; col++) {
857d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan[0] = src_scan[0];
858d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan[1] = src_scan[1];
859d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan[2] = src_scan[2];
860d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan += dest_Bpp;
861d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    src_scan += src_Bpp;
862d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
863d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
864d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
865d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_Rgb2Rgb_NoBlend_Clip(uint8_t* dest_scan,
866d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                       const uint8_t* src_scan,
867d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                       int width,
868d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                       int dest_Bpp,
869d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                       int src_Bpp,
870d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                       const uint8_t* clip_scan) {
871d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < width; col++) {
872d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int src_alpha = clip_scan[col];
873d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (src_alpha == 255) {
874d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[0] = src_scan[0];
875d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[1] = src_scan[1];
876d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[2] = src_scan[2];
877d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else if (src_alpha) {
878d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, *src_scan, src_alpha);
879d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
880d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan++;
881d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, *src_scan, src_alpha);
882d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
883d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan++;
884d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, *src_scan, src_alpha);
885d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += dest_Bpp - 2;
886d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan += src_Bpp - 2;
887d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
888d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
889d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan += dest_Bpp;
890d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    src_scan += src_Bpp;
891d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
892d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
893d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
894d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_8bppPal2Gray(uint8_t* dest_scan,
895d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               const uint8_t* src_scan,
896d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               const uint8_t* pPalette,
897d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               int pixel_count,
898d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               int blend_type,
899d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               const uint8_t* clip_scan,
900d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               const uint8_t* src_alpha_scan) {
901d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  if (src_alpha_scan) {
902d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (blend_type) {
903d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      bool bNonseparableBlend = blend_type >= FXDIB_BLEND_NONSEPARABLE;
904d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      for (int col = 0; col < pixel_count; col++) {
905d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        uint8_t gray = pPalette[*src_scan];
906d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        int src_alpha = GetAlpha(*src_alpha_scan++, clip_scan, col);
907d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        if (bNonseparableBlend)
908d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          gray = blend_type == FXDIB_BLEND_LUMINOSITY ? gray : *dest_scan;
909d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        else
910d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          gray = Blend(blend_type, *dest_scan, gray);
911d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        if (src_alpha)
912d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, gray, src_alpha);
913d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        else
914d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          *dest_scan = gray;
915d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan++;
916d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        src_scan++;
917d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
918d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      return;
919d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
920d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    for (int col = 0; col < pixel_count; col++) {
921d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t gray = pPalette[*src_scan];
922d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int src_alpha = GetAlpha(*src_alpha_scan++, clip_scan, col);
923d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (src_alpha)
924d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, gray, src_alpha);
925d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      else
926d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan = gray;
927d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
928d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan++;
929d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
930d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  } else {
931d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (blend_type) {
932d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      bool bNonseparableBlend = blend_type >= FXDIB_BLEND_NONSEPARABLE;
933d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      for (int col = 0; col < pixel_count; col++) {
934d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        uint8_t gray = pPalette[*src_scan];
935d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        if (bNonseparableBlend)
936d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          gray = blend_type == FXDIB_BLEND_LUMINOSITY ? gray : *dest_scan;
937d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        else
938d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          gray = Blend(blend_type, *dest_scan, gray);
939d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        if (clip_scan && clip_scan[col] < 255)
940d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, gray, clip_scan[col]);
941d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        else
942d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          *dest_scan = gray;
943d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan++;
944d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        src_scan++;
945d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
946d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      return;
947d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
948d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    for (int col = 0; col < pixel_count; col++) {
949d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t gray = pPalette[*src_scan];
950d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (clip_scan && clip_scan[col] < 255)
951d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, gray, clip_scan[col]);
952d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      else
953d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan = gray;
954d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
955d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan++;
956d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
957d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
958d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
959d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
960d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_8bppPal2Graya(uint8_t* dest_scan,
961d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                const uint8_t* src_scan,
962d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                const uint8_t* pPalette,
963d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                int pixel_count,
964d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                int blend_type,
965d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                const uint8_t* clip_scan,
966d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                uint8_t* dest_alpha_scan,
967d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                const uint8_t* src_alpha_scan) {
968d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  if (src_alpha_scan) {
969d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (blend_type) {
970d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      bool bNonseparableBlend = blend_type >= FXDIB_BLEND_NONSEPARABLE;
971d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      for (int col = 0; col < pixel_count; col++) {
972d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        uint8_t gray = pPalette[*src_scan];
973d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        src_scan++;
974d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        uint8_t back_alpha = *dest_alpha_scan;
975d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        if (back_alpha == 0) {
976d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          int src_alpha = GetAlpha(*src_alpha_scan++, clip_scan, col);
977d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          if (src_alpha) {
978d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            *dest_scan = gray;
979d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            *dest_alpha_scan = src_alpha;
980d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          }
981d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          dest_scan++;
982d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          dest_alpha_scan++;
983d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          continue;
984d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        }
985d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        uint8_t src_alpha = GetAlpha(*src_alpha_scan++, clip_scan, col);
986d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        if (src_alpha == 0) {
987d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          dest_scan++;
988d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          dest_alpha_scan++;
989d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          continue;
990d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        }
991d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_alpha_scan =
992d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            back_alpha + src_alpha - back_alpha * src_alpha / 255;
993d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        int alpha_ratio = src_alpha * 255 / (*dest_alpha_scan);
994d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        if (bNonseparableBlend)
995d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          gray = blend_type == FXDIB_BLEND_LUMINOSITY ? gray : *dest_scan;
996d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        else
997d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          gray = Blend(blend_type, *dest_scan, gray);
998d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, gray, alpha_ratio);
999d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_alpha_scan++;
1000d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan++;
1001d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
1002d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      return;
1003d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1004d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    for (int col = 0; col < pixel_count; col++) {
1005d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t gray = pPalette[*src_scan];
1006d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan++;
1007d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t back_alpha = *dest_alpha_scan;
1008d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (back_alpha == 0) {
1009d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        int src_alpha = GetAlpha(*src_alpha_scan++, clip_scan, col);
1010d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        if (src_alpha) {
1011d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          *dest_scan = gray;
1012d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          *dest_alpha_scan = src_alpha;
1013d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        }
1014d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan++;
1015d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_alpha_scan++;
1016d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        continue;
1017d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
1018d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t src_alpha = GetAlpha(*src_alpha_scan++, clip_scan, col);
1019d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (src_alpha == 0) {
1020d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan++;
1021d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_alpha_scan++;
1022d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        continue;
1023d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
1024d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_alpha_scan = back_alpha + src_alpha - back_alpha * src_alpha / 255;
1025d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int alpha_ratio = src_alpha * 255 / (*dest_alpha_scan);
1026d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_alpha_scan++;
1027d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, gray, alpha_ratio);
1028d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1029d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1030d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  } else {
1031d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (blend_type) {
1032d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      bool bNonseparableBlend = blend_type >= FXDIB_BLEND_NONSEPARABLE;
1033d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      for (int col = 0; col < pixel_count; col++) {
1034d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        uint8_t gray = pPalette[*src_scan];
1035d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        src_scan++;
1036d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        if (!clip_scan || clip_scan[col] == 255) {
1037d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          *dest_scan++ = gray;
1038d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          *dest_alpha_scan++ = 255;
1039d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          continue;
1040d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        }
1041d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        int src_alpha = clip_scan[col];
1042d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        if (src_alpha == 0) {
1043d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          dest_scan++;
1044d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          dest_alpha_scan++;
1045d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          continue;
1046d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        }
1047d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        int back_alpha = *dest_alpha_scan;
1048d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        uint8_t dest_alpha =
1049d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            back_alpha + src_alpha - back_alpha * src_alpha / 255;
1050d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_alpha_scan++ = dest_alpha;
1051d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        int alpha_ratio = src_alpha * 255 / dest_alpha;
1052d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        if (bNonseparableBlend)
1053d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          gray = blend_type == FXDIB_BLEND_LUMINOSITY ? gray : *dest_scan;
1054d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        else
1055d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          gray = Blend(blend_type, *dest_scan, gray);
1056d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, gray, alpha_ratio);
1057d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan++;
1058d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
1059d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      return;
1060d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1061d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    for (int col = 0; col < pixel_count; col++) {
1062d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t gray = pPalette[*src_scan];
1063d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan++;
1064d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (!clip_scan || clip_scan[col] == 255) {
1065d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan++ = gray;
1066d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_alpha_scan++ = 255;
1067d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        continue;
1068d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
1069d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int src_alpha = clip_scan[col];
1070d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (src_alpha == 0) {
1071d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan++;
1072d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_alpha_scan++;
1073d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        continue;
1074d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
1075d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int back_alpha = *dest_alpha_scan;
1076d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t dest_alpha =
1077d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          back_alpha + src_alpha - back_alpha * src_alpha / 255;
1078d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_alpha_scan++ = dest_alpha;
1079d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int alpha_ratio = src_alpha * 255 / dest_alpha;
1080d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, gray, alpha_ratio);
1081d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1082d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1083d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
1084d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
1085d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
1086d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_1bppPal2Gray(uint8_t* dest_scan,
1087d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               const uint8_t* src_scan,
1088d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               int src_left,
1089d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               const uint8_t* pPalette,
1090d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               int pixel_count,
1091d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               int blend_type,
1092d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               const uint8_t* clip_scan) {
1093d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int reset_gray = pPalette[0];
1094d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int set_gray = pPalette[1];
1095d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  if (blend_type) {
1096d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    bool bNonseparableBlend = blend_type >= FXDIB_BLEND_NONSEPARABLE;
1097d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    for (int col = 0; col < pixel_count; col++) {
1098d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t gray =
1099d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          (src_scan[(col + src_left) / 8] & (1 << (7 - (col + src_left) % 8)))
1100d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann              ? set_gray
1101d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann              : reset_gray;
1102d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (bNonseparableBlend)
1103d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        gray = blend_type == FXDIB_BLEND_LUMINOSITY ? gray : *dest_scan;
1104d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      else
1105d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        gray = Blend(blend_type, *dest_scan, gray);
1106d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (clip_scan && clip_scan[col] < 255) {
1107d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, gray, clip_scan[col]);
1108d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      } else {
1109d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan = gray;
1110d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
1111d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1112d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1113d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    return;
1114d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
1115d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < pixel_count; col++) {
1116d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t gray =
1117d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        (src_scan[(col + src_left) / 8] & (1 << (7 - (col + src_left) % 8)))
1118d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            ? set_gray
1119d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            : reset_gray;
1120d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (clip_scan && clip_scan[col] < 255) {
1121d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, gray, clip_scan[col]);
1122d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
1123d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = gray;
1124d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1125d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan++;
1126d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
1127d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
1128d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
1129d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_1bppPal2Graya(uint8_t* dest_scan,
1130d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                const uint8_t* src_scan,
1131d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                int src_left,
1132d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                const uint8_t* pPalette,
1133d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                int pixel_count,
1134d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                int blend_type,
1135d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                const uint8_t* clip_scan,
1136d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                uint8_t* dest_alpha_scan) {
1137d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int reset_gray = pPalette[0];
1138d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int set_gray = pPalette[1];
1139d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  if (blend_type) {
1140d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    bool bNonseparableBlend = blend_type >= FXDIB_BLEND_NONSEPARABLE;
1141d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    for (int col = 0; col < pixel_count; col++) {
1142d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t gray =
1143d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          (src_scan[(col + src_left) / 8] & (1 << (7 - (col + src_left) % 8)))
1144d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann              ? set_gray
1145d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann              : reset_gray;
1146d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (!clip_scan || clip_scan[col] == 255) {
1147d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan++ = gray;
1148d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_alpha_scan++ = 255;
1149d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        continue;
1150d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
1151d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int src_alpha = clip_scan[col];
1152d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (src_alpha == 0) {
1153d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan++;
1154d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_alpha_scan++;
1155d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        continue;
1156d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
1157d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int back_alpha = *dest_alpha_scan;
1158d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t dest_alpha =
1159d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          back_alpha + src_alpha - back_alpha * src_alpha / 255;
1160d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_alpha_scan++ = dest_alpha;
1161d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int alpha_ratio = src_alpha * 255 / dest_alpha;
1162d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (bNonseparableBlend)
1163d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        gray = blend_type == FXDIB_BLEND_LUMINOSITY ? gray : *dest_scan;
1164d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      else
1165d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        gray = Blend(blend_type, *dest_scan, gray);
1166d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, gray, alpha_ratio);
1167d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1168d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1169d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    return;
1170d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
1171d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < pixel_count; col++) {
1172d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t gray =
1173d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        (src_scan[(col + src_left) / 8] & (1 << (7 - (col + src_left) % 8)))
1174d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            ? set_gray
1175d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            : reset_gray;
1176d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (!clip_scan || clip_scan[col] == 255) {
1177d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan++ = gray;
1178d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_alpha_scan++ = 255;
1179d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
1180d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1181d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int src_alpha = clip_scan[col];
1182d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (src_alpha == 0) {
1183d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1184d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_alpha_scan++;
1185d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
1186d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1187d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int back_alpha = *dest_alpha_scan;
1188d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t dest_alpha = back_alpha + src_alpha - back_alpha * src_alpha / 255;
1189d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    *dest_alpha_scan++ = dest_alpha;
1190d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int alpha_ratio = src_alpha * 255 / dest_alpha;
1191d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, gray, alpha_ratio);
1192d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan++;
1193d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
1194d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
1195d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
1196d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_8bppRgb2Rgb_NoBlend(uint8_t* dest_scan,
1197d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                      const uint8_t* src_scan,
1198d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                      uint32_t* pPalette,
1199d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                      int pixel_count,
1200d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                      int DestBpp,
1201d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                      const uint8_t* clip_scan,
1202d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                      const uint8_t* src_alpha_scan) {
1203d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  if (src_alpha_scan) {
1204d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int dest_gap = DestBpp - 3;
1205d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    FX_ARGB argb = 0;
1206d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    for (int col = 0; col < pixel_count; col++) {
1207d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      argb = pPalette[*src_scan];
1208d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int src_r = FXARGB_R(argb);
1209d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int src_g = FXARGB_G(argb);
1210d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int src_b = FXARGB_B(argb);
1211d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan++;
1212d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t src_alpha = 0;
1213d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (clip_scan) {
1214d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        src_alpha = (*src_alpha_scan++) * (*clip_scan++) / 255;
1215d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      } else {
1216d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        src_alpha = *src_alpha_scan++;
1217d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
1218d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (src_alpha == 255) {
1219d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan++ = src_b;
1220d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan++ = src_g;
1221d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan++ = src_r;
1222d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan += dest_gap;
1223d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        continue;
1224d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
1225d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (src_alpha == 0) {
1226d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan += DestBpp;
1227d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        continue;
1228d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
1229d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, src_b, src_alpha);
1230d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1231d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, src_g, src_alpha);
1232d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1233d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, src_r, src_alpha);
1234d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1235d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += dest_gap;
1236d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1237d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  } else {
1238d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    FX_ARGB argb = 0;
1239d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    for (int col = 0; col < pixel_count; col++) {
1240d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      argb = pPalette[*src_scan];
1241d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int src_r = FXARGB_R(argb);
1242d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int src_g = FXARGB_G(argb);
1243d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int src_b = FXARGB_B(argb);
1244d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (clip_scan && clip_scan[col] < 255) {
1245d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, src_b, clip_scan[col]);
1246d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan++;
1247d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, src_g, clip_scan[col]);
1248d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan++;
1249d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, src_r, clip_scan[col]);
1250d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan++;
1251d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      } else {
1252d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan++ = src_b;
1253d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan++ = src_g;
1254d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan++ = src_r;
1255d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
1256d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (DestBpp == 4) {
1257d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan++;
1258d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
1259d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan++;
1260d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1261d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
1262d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
1263d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
1264d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_1bppRgb2Rgb_NoBlend(uint8_t* dest_scan,
1265d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                      const uint8_t* src_scan,
1266d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                      int src_left,
1267d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                      uint32_t* pPalette,
1268d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                      int pixel_count,
1269d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                      int DestBpp,
1270d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                      const uint8_t* clip_scan) {
1271d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int reset_r, reset_g, reset_b;
1272d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int set_r, set_g, set_b;
1273d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  reset_r = FXARGB_R(pPalette[0]);
1274d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  reset_g = FXARGB_G(pPalette[0]);
1275d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  reset_b = FXARGB_B(pPalette[0]);
1276d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  set_r = FXARGB_R(pPalette[1]);
1277d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  set_g = FXARGB_G(pPalette[1]);
1278d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  set_b = FXARGB_B(pPalette[1]);
1279d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < pixel_count; col++) {
1280d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int src_r, src_g, src_b;
1281d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (src_scan[(col + src_left) / 8] & (1 << (7 - (col + src_left) % 8))) {
1282d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_r = set_r;
1283d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_g = set_g;
1284d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_b = set_b;
1285d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
1286d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_r = reset_r;
1287d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_g = reset_g;
1288d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_b = reset_b;
1289d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1290d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (clip_scan && clip_scan[col] < 255) {
1291d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, src_b, clip_scan[col]);
1292d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1293d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, src_g, clip_scan[col]);
1294d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1295d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, src_r, clip_scan[col]);
1296d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1297d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
1298d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan++ = src_b;
1299d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan++ = src_g;
1300d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan++ = src_r;
1301d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1302d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (DestBpp == 4) {
1303d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1304d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1305d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
1306d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
1307d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
1308d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_8bppRgb2Argb_NoBlend(uint8_t* dest_scan,
1309d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                       const uint8_t* src_scan,
1310d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                       int width,
1311d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                       uint32_t* pPalette,
1312d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                       const uint8_t* clip_scan,
1313d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                       const uint8_t* src_alpha_scan) {
1314d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  if (src_alpha_scan) {
1315d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    for (int col = 0; col < width; col++) {
1316d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      FX_ARGB argb = pPalette[*src_scan];
1317d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan++;
1318d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int src_r = FXARGB_R(argb);
1319d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int src_g = FXARGB_G(argb);
1320d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int src_b = FXARGB_B(argb);
1321d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t back_alpha = dest_scan[3];
1322d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (back_alpha == 0) {
1323d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        if (clip_scan) {
1324d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          int src_alpha = clip_scan[col] * (*src_alpha_scan) / 255;
1325d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          FXARGB_SETDIB(dest_scan, FXARGB_MAKE(src_alpha, src_r, src_g, src_b));
1326d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        } else {
1327d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          FXARGB_SETDIB(dest_scan,
1328d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                        FXARGB_MAKE(*src_alpha_scan, src_r, src_g, src_b));
1329d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        }
1330d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan += 4;
1331d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        src_alpha_scan++;
1332d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        continue;
1333d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
1334d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t src_alpha;
1335d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (clip_scan) {
1336d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        src_alpha = clip_scan[col] * (*src_alpha_scan++) / 255;
1337d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      } else {
1338d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        src_alpha = *src_alpha_scan++;
1339d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
1340d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (src_alpha == 0) {
1341d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan += 4;
1342d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        continue;
1343d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
1344d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t dest_alpha =
1345d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          back_alpha + src_alpha - back_alpha * src_alpha / 255;
1346d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[3] = dest_alpha;
1347d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int alpha_ratio = src_alpha * 255 / dest_alpha;
1348d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, src_b, alpha_ratio);
1349d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1350d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, src_g, alpha_ratio);
1351d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1352d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, src_r, alpha_ratio);
1353d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1354d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1355d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1356d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  } else {
1357d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    for (int col = 0; col < width; col++) {
1358d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      FX_ARGB argb = pPalette[*src_scan];
1359d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int src_r = FXARGB_R(argb);
1360d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int src_g = FXARGB_G(argb);
1361d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int src_b = FXARGB_B(argb);
1362d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (!clip_scan || clip_scan[col] == 255) {
1363d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan++ = src_b;
1364d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan++ = src_g;
1365d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan++ = src_r;
1366d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan++ = 255;
1367d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        src_scan++;
1368d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        continue;
1369d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
1370d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int src_alpha = clip_scan[col];
1371d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (src_alpha == 0) {
1372d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan += 4;
1373d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        src_scan++;
1374d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        continue;
1375d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
1376d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int back_alpha = dest_scan[3];
1377d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t dest_alpha =
1378d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          back_alpha + src_alpha - back_alpha * src_alpha / 255;
1379d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[3] = dest_alpha;
1380d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int alpha_ratio = src_alpha * 255 / dest_alpha;
1381d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, src_b, alpha_ratio);
1382d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1383d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, src_g, alpha_ratio);
1384d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1385d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, src_r, alpha_ratio);
1386d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1387d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1388d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan++;
1389d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1390d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
1391d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
1392d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
1393d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_1bppRgb2Argb_NoBlend(uint8_t* dest_scan,
1394d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                       const uint8_t* src_scan,
1395d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                       int src_left,
1396d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                       int width,
1397d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                       uint32_t* pPalette,
1398d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                       const uint8_t* clip_scan) {
1399d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int reset_r, reset_g, reset_b;
1400d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int set_r, set_g, set_b;
1401d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  reset_r = FXARGB_R(pPalette[0]);
1402d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  reset_g = FXARGB_G(pPalette[0]);
1403d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  reset_b = FXARGB_B(pPalette[0]);
1404d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  set_r = FXARGB_R(pPalette[1]);
1405d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  set_g = FXARGB_G(pPalette[1]);
1406d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  set_b = FXARGB_B(pPalette[1]);
1407d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < width; col++) {
1408d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int src_r, src_g, src_b;
1409d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (src_scan[(col + src_left) / 8] & (1 << (7 - (col + src_left) % 8))) {
1410d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_r = set_r;
1411d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_g = set_g;
1412d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_b = set_b;
1413d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
1414d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_r = reset_r;
1415d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_g = reset_g;
1416d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_b = reset_b;
1417d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1418d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (!clip_scan || clip_scan[col] == 255) {
1419d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan++ = src_b;
1420d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan++ = src_g;
1421d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan++ = src_r;
1422d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan++ = 255;
1423d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
1424d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1425d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int src_alpha = clip_scan[col];
1426d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (src_alpha == 0) {
1427d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += 4;
1428d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
1429d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1430d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int back_alpha = dest_scan[3];
1431d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t dest_alpha = back_alpha + src_alpha - back_alpha * src_alpha / 255;
1432d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan[3] = dest_alpha;
1433d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int alpha_ratio = src_alpha * 255 / dest_alpha;
1434d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, src_b, alpha_ratio);
1435d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan++;
1436d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, src_g, alpha_ratio);
1437d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan++;
1438d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, src_r, alpha_ratio);
1439d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan++;
1440d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan++;
1441d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
1442d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
1443d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
1444d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_1bppRgb2Rgba_NoBlend(uint8_t* dest_scan,
1445d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                       const uint8_t* src_scan,
1446d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                       int src_left,
1447d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                       int width,
1448d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                       uint32_t* pPalette,
1449d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                       const uint8_t* clip_scan,
1450d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                       uint8_t* dest_alpha_scan) {
1451d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int reset_r, reset_g, reset_b;
1452d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int set_r, set_g, set_b;
1453d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  reset_r = FXARGB_R(pPalette[0]);
1454d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  reset_g = FXARGB_G(pPalette[0]);
1455d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  reset_b = FXARGB_B(pPalette[0]);
1456d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  set_r = FXARGB_R(pPalette[1]);
1457d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  set_g = FXARGB_G(pPalette[1]);
1458d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  set_b = FXARGB_B(pPalette[1]);
1459d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < width; col++) {
1460d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int src_r, src_g, src_b;
1461d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (src_scan[(col + src_left) / 8] & (1 << (7 - (col + src_left) % 8))) {
1462d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_r = set_r;
1463d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_g = set_g;
1464d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_b = set_b;
1465d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
1466d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_r = reset_r;
1467d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_g = reset_g;
1468d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_b = reset_b;
1469d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1470d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (!clip_scan || clip_scan[col] == 255) {
1471d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan++ = src_b;
1472d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan++ = src_g;
1473d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan++ = src_r;
1474d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_alpha_scan++ = 255;
1475d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
1476d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1477d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int src_alpha = clip_scan[col];
1478d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (src_alpha == 0) {
1479d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += 3;
1480d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_alpha_scan++;
1481d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
1482d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1483d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int back_alpha = *dest_alpha_scan;
1484d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t dest_alpha = back_alpha + src_alpha - back_alpha * src_alpha / 255;
1485d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    *dest_alpha_scan++ = dest_alpha;
1486d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int alpha_ratio = src_alpha * 255 / dest_alpha;
1487d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, src_b, alpha_ratio);
1488d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan++;
1489d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, src_g, alpha_ratio);
1490d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan++;
1491d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, src_r, alpha_ratio);
1492d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan++;
1493d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
1494d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
1495d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
1496d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_ByteMask2Argb(uint8_t* dest_scan,
1497d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                const uint8_t* src_scan,
1498d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                int mask_alpha,
1499d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                int src_r,
1500d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                int src_g,
1501d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                int src_b,
1502d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                int pixel_count,
1503d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                int blend_type,
1504d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                const uint8_t* clip_scan) {
1505d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < pixel_count; col++) {
1506d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int src_alpha;
1507d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (clip_scan) {
1508d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_alpha = mask_alpha * clip_scan[col] * src_scan[col] / 255 / 255;
1509d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
1510d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_alpha = mask_alpha * src_scan[col] / 255;
1511d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1512d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t back_alpha = dest_scan[3];
1513d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (back_alpha == 0) {
1514d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      FXARGB_SETDIB(dest_scan, FXARGB_MAKE(src_alpha, src_r, src_g, src_b));
1515d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += 4;
1516d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
1517d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1518d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (src_alpha == 0) {
1519d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += 4;
1520d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
1521d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1522d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t dest_alpha = back_alpha + src_alpha - back_alpha * src_alpha / 255;
1523d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan[3] = dest_alpha;
1524d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int alpha_ratio = src_alpha * 255 / dest_alpha;
1525d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (blend_type >= FXDIB_BLEND_NONSEPARABLE) {
1526d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int blended_colors[3];
1527d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t scan[3] = {static_cast<uint8_t>(src_b),
1528d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                         static_cast<uint8_t>(src_g),
1529d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                         static_cast<uint8_t>(src_r)};
1530d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      RGB_Blend(blend_type, scan, dest_scan, blended_colors);
1531d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan =
1532d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          FXDIB_ALPHA_MERGE(*dest_scan, blended_colors[0], alpha_ratio);
1533d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1534d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan =
1535d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          FXDIB_ALPHA_MERGE(*dest_scan, blended_colors[1], alpha_ratio);
1536d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1537d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan =
1538d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          FXDIB_ALPHA_MERGE(*dest_scan, blended_colors[2], alpha_ratio);
1539d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else if (blend_type) {
1540d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int blended = Blend(blend_type, *dest_scan, src_b);
1541d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      blended = FXDIB_ALPHA_MERGE(src_b, blended, back_alpha);
1542d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, blended, alpha_ratio);
1543d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1544d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      blended = Blend(blend_type, *dest_scan, src_g);
1545d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      blended = FXDIB_ALPHA_MERGE(src_g, blended, back_alpha);
1546d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, blended, alpha_ratio);
1547d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1548d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      blended = Blend(blend_type, *dest_scan, src_r);
1549d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      blended = FXDIB_ALPHA_MERGE(src_r, blended, back_alpha);
1550d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, blended, alpha_ratio);
1551d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
1552d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, src_b, alpha_ratio);
1553d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1554d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, src_g, alpha_ratio);
1555d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1556d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, src_r, alpha_ratio);
1557d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1558d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan += 2;
1559d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
1560d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
1561d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
1562d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_ByteMask2Rgba(uint8_t* dest_scan,
1563d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                const uint8_t* src_scan,
1564d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                int mask_alpha,
1565d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                int src_r,
1566d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                int src_g,
1567d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                int src_b,
1568d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                int pixel_count,
1569d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                int blend_type,
1570d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                const uint8_t* clip_scan,
1571d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                uint8_t* dest_alpha_scan) {
1572d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < pixel_count; col++) {
1573d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int src_alpha;
1574d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (clip_scan) {
1575d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_alpha = mask_alpha * clip_scan[col] * src_scan[col] / 255 / 255;
1576d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
1577d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_alpha = mask_alpha * src_scan[col] / 255;
1578d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1579d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t back_alpha = *dest_alpha_scan;
1580d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (back_alpha == 0) {
1581d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan++ = src_b;
1582d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan++ = src_g;
1583d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan++ = src_r;
1584d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_alpha_scan++ = src_alpha;
1585d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
1586d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1587d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (src_alpha == 0) {
1588d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += 3;
1589d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_alpha_scan++;
1590d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
1591d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1592d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t dest_alpha = back_alpha + src_alpha - back_alpha * src_alpha / 255;
1593d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    *dest_alpha_scan++ = dest_alpha;
1594d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int alpha_ratio = src_alpha * 255 / dest_alpha;
1595d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (blend_type >= FXDIB_BLEND_NONSEPARABLE) {
1596d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int blended_colors[3];
1597d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t scan[3] = {static_cast<uint8_t>(src_b),
1598d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                         static_cast<uint8_t>(src_g),
1599d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                         static_cast<uint8_t>(src_r)};
1600d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      RGB_Blend(blend_type, scan, dest_scan, blended_colors);
1601d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan =
1602d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          FXDIB_ALPHA_MERGE(*dest_scan, blended_colors[0], alpha_ratio);
1603d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1604d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan =
1605d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          FXDIB_ALPHA_MERGE(*dest_scan, blended_colors[1], alpha_ratio);
1606d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1607d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan =
1608d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          FXDIB_ALPHA_MERGE(*dest_scan, blended_colors[2], alpha_ratio);
1609d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1610d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else if (blend_type) {
1611d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int blended = Blend(blend_type, *dest_scan, src_b);
1612d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      blended = FXDIB_ALPHA_MERGE(src_b, blended, back_alpha);
1613d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, blended, alpha_ratio);
1614d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1615d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      blended = Blend(blend_type, *dest_scan, src_g);
1616d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      blended = FXDIB_ALPHA_MERGE(src_g, blended, back_alpha);
1617d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, blended, alpha_ratio);
1618d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1619d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      blended = Blend(blend_type, *dest_scan, src_r);
1620d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      blended = FXDIB_ALPHA_MERGE(src_r, blended, back_alpha);
1621d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, blended, alpha_ratio);
1622d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1623d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
1624d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, src_b, alpha_ratio);
1625d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1626d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, src_g, alpha_ratio);
1627d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1628d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, src_r, alpha_ratio);
1629d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1630d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1631d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
1632d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
1633d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
1634d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_ByteMask2Rgb(uint8_t* dest_scan,
1635d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               const uint8_t* src_scan,
1636d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               int mask_alpha,
1637d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               int src_r,
1638d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               int src_g,
1639d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               int src_b,
1640d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               int pixel_count,
1641d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               int blend_type,
1642d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               int Bpp,
1643d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               const uint8_t* clip_scan) {
1644d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < pixel_count; col++) {
1645d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int src_alpha;
1646d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (clip_scan) {
1647d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_alpha = mask_alpha * clip_scan[col] * src_scan[col] / 255 / 255;
1648d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
1649d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_alpha = mask_alpha * src_scan[col] / 255;
1650d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1651d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (src_alpha == 0) {
1652d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += Bpp;
1653d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
1654d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1655d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (blend_type >= FXDIB_BLEND_NONSEPARABLE) {
1656d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int blended_colors[3];
1657d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t scan[3] = {static_cast<uint8_t>(src_b),
1658d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                         static_cast<uint8_t>(src_g),
1659d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                         static_cast<uint8_t>(src_r)};
1660d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      RGB_Blend(blend_type, scan, dest_scan, blended_colors);
1661d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, blended_colors[0], src_alpha);
1662d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1663d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, blended_colors[1], src_alpha);
1664d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1665d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, blended_colors[2], src_alpha);
1666d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else if (blend_type) {
1667d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int blended = Blend(blend_type, *dest_scan, src_b);
1668d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, blended, src_alpha);
1669d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1670d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      blended = Blend(blend_type, *dest_scan, src_g);
1671d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, blended, src_alpha);
1672d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1673d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      blended = Blend(blend_type, *dest_scan, src_r);
1674d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, blended, src_alpha);
1675d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
1676d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, src_b, src_alpha);
1677d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1678d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, src_g, src_alpha);
1679d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1680d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, src_r, src_alpha);
1681d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1682d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan += Bpp - 2;
1683d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
1684d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
1685d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
1686d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_ByteMask2Mask(uint8_t* dest_scan,
1687d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                const uint8_t* src_scan,
1688d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                int mask_alpha,
1689d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                int pixel_count,
1690d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                const uint8_t* clip_scan) {
1691d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < pixel_count; col++) {
1692d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int src_alpha;
1693d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (clip_scan) {
1694d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_alpha = mask_alpha * clip_scan[col] * src_scan[col] / 255 / 255;
1695d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
1696d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_alpha = mask_alpha * src_scan[col] / 255;
1697d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1698d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t back_alpha = *dest_scan;
1699d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (!back_alpha) {
1700d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = src_alpha;
1701d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else if (src_alpha) {
1702d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = back_alpha + src_alpha - back_alpha * src_alpha / 255;
1703d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1704d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan++;
1705d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
1706d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
1707d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
1708d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_ByteMask2Gray(uint8_t* dest_scan,
1709d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                const uint8_t* src_scan,
1710d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                int mask_alpha,
1711d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                int src_gray,
1712d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                int pixel_count,
1713d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                const uint8_t* clip_scan) {
1714d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < pixel_count; col++) {
1715d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int src_alpha;
1716d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (clip_scan) {
1717d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_alpha = mask_alpha * clip_scan[col] * src_scan[col] / 255 / 255;
1718d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
1719d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_alpha = mask_alpha * src_scan[col] / 255;
1720d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1721d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (src_alpha) {
1722d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, src_gray, src_alpha);
1723d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1724d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan++;
1725d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
1726d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
1727d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
1728d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_ByteMask2Graya(uint8_t* dest_scan,
1729d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                 const uint8_t* src_scan,
1730d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                 int mask_alpha,
1731d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                 int src_gray,
1732d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                 int pixel_count,
1733d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                 const uint8_t* clip_scan,
1734d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                 uint8_t* dest_alpha_scan) {
1735d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < pixel_count; col++) {
1736d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int src_alpha;
1737d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (clip_scan) {
1738d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_alpha = mask_alpha * clip_scan[col] * src_scan[col] / 255 / 255;
1739d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
1740d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_alpha = mask_alpha * src_scan[col] / 255;
1741d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1742d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t back_alpha = *dest_alpha_scan;
1743d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (back_alpha == 0) {
1744d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan++ = src_gray;
1745d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_alpha_scan++ = src_alpha;
1746d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
1747d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1748d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (src_alpha == 0) {
1749d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1750d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_alpha_scan++;
1751d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
1752d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1753d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t dest_alpha = back_alpha + src_alpha - back_alpha * src_alpha / 255;
1754d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    *dest_alpha_scan++ = dest_alpha;
1755d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int alpha_ratio = src_alpha * 255 / dest_alpha;
1756d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, src_gray, alpha_ratio);
1757d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan++;
1758d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
1759d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
1760d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
1761d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_BitMask2Argb(uint8_t* dest_scan,
1762d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               const uint8_t* src_scan,
1763d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               int mask_alpha,
1764d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               int src_r,
1765d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               int src_g,
1766d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               int src_b,
1767d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               int src_left,
1768d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               int pixel_count,
1769d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               int blend_type,
1770d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               const uint8_t* clip_scan) {
1771d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  if (blend_type == FXDIB_BLEND_NORMAL && !clip_scan && mask_alpha == 255) {
1772d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    FX_ARGB argb = FXARGB_MAKE(0xff, src_r, src_g, src_b);
1773d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    for (int col = 0; col < pixel_count; col++) {
1774d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (src_scan[(src_left + col) / 8] & (1 << (7 - (src_left + col) % 8))) {
1775d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        FXARGB_SETDIB(dest_scan, argb);
1776d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
1777d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += 4;
1778d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1779d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    return;
1780d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
1781d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < pixel_count; col++) {
1782d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (!(src_scan[(src_left + col) / 8] & (1 << (7 - (src_left + col) % 8)))) {
1783d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += 4;
1784d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
1785d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1786d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int src_alpha;
1787d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (clip_scan) {
1788d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_alpha = mask_alpha * clip_scan[col] / 255;
1789d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
1790d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_alpha = mask_alpha;
1791d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1792d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t back_alpha = dest_scan[3];
1793d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (back_alpha == 0) {
1794d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      FXARGB_SETDIB(dest_scan, FXARGB_MAKE(src_alpha, src_r, src_g, src_b));
1795d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += 4;
1796d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
1797d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1798d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t dest_alpha = back_alpha + src_alpha - back_alpha * src_alpha / 255;
1799d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan[3] = dest_alpha;
1800d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int alpha_ratio = src_alpha * 255 / dest_alpha;
1801d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (blend_type >= FXDIB_BLEND_NONSEPARABLE) {
1802d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int blended_colors[3];
1803d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t scan[3] = {static_cast<uint8_t>(src_b),
1804d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                         static_cast<uint8_t>(src_g),
1805d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                         static_cast<uint8_t>(src_r)};
1806d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      RGB_Blend(blend_type, scan, dest_scan, blended_colors);
1807d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan =
1808d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          FXDIB_ALPHA_MERGE(*dest_scan, blended_colors[0], alpha_ratio);
1809d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1810d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan =
1811d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          FXDIB_ALPHA_MERGE(*dest_scan, blended_colors[1], alpha_ratio);
1812d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1813d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan =
1814d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          FXDIB_ALPHA_MERGE(*dest_scan, blended_colors[2], alpha_ratio);
1815d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else if (blend_type) {
1816d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int blended = Blend(blend_type, *dest_scan, src_b);
1817d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      blended = FXDIB_ALPHA_MERGE(src_b, blended, back_alpha);
1818d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, blended, alpha_ratio);
1819d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1820d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      blended = Blend(blend_type, *dest_scan, src_g);
1821d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      blended = FXDIB_ALPHA_MERGE(src_g, blended, back_alpha);
1822d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, blended, alpha_ratio);
1823d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1824d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      blended = Blend(blend_type, *dest_scan, src_r);
1825d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      blended = FXDIB_ALPHA_MERGE(src_r, blended, back_alpha);
1826d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, blended, alpha_ratio);
1827d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
1828d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, src_b, alpha_ratio);
1829d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1830d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, src_g, alpha_ratio);
1831d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1832d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, src_r, alpha_ratio);
1833d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1834d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan += 2;
1835d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
1836d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
1837d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
1838d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_BitMask2Rgb(uint8_t* dest_scan,
1839d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                              const uint8_t* src_scan,
1840d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                              int mask_alpha,
1841d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                              int src_r,
1842d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                              int src_g,
1843d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                              int src_b,
1844d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                              int src_left,
1845d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                              int pixel_count,
1846d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                              int blend_type,
1847d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                              int Bpp,
1848d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                              const uint8_t* clip_scan) {
1849d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  if (blend_type == FXDIB_BLEND_NORMAL && !clip_scan && mask_alpha == 255) {
1850d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    for (int col = 0; col < pixel_count; col++) {
1851d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (src_scan[(src_left + col) / 8] & (1 << (7 - (src_left + col) % 8))) {
1852d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan[2] = src_r;
1853d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan[1] = src_g;
1854d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan[0] = src_b;
1855d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
1856d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += Bpp;
1857d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1858d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    return;
1859d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
1860d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < pixel_count; col++) {
1861d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (!(src_scan[(src_left + col) / 8] & (1 << (7 - (src_left + col) % 8)))) {
1862d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += Bpp;
1863d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
1864d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1865d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int src_alpha;
1866d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (clip_scan) {
1867d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_alpha = mask_alpha * clip_scan[col] / 255;
1868d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
1869d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_alpha = mask_alpha;
1870d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1871d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (src_alpha == 0) {
1872d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += Bpp;
1873d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
1874d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1875d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (blend_type >= FXDIB_BLEND_NONSEPARABLE) {
1876d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int blended_colors[3];
1877d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t scan[3] = {static_cast<uint8_t>(src_b),
1878d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                         static_cast<uint8_t>(src_g),
1879d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                         static_cast<uint8_t>(src_r)};
1880d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      RGB_Blend(blend_type, scan, dest_scan, blended_colors);
1881d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, blended_colors[0], src_alpha);
1882d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1883d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, blended_colors[1], src_alpha);
1884d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1885d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, blended_colors[2], src_alpha);
1886d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else if (blend_type) {
1887d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int blended = Blend(blend_type, *dest_scan, src_b);
1888d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, blended, src_alpha);
1889d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1890d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      blended = Blend(blend_type, *dest_scan, src_g);
1891d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, blended, src_alpha);
1892d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1893d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      blended = Blend(blend_type, *dest_scan, src_r);
1894d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, blended, src_alpha);
1895d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
1896d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, src_b, src_alpha);
1897d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1898d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, src_g, src_alpha);
1899d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1900d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, src_r, src_alpha);
1901d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1902d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan += Bpp - 2;
1903d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
1904d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
1905d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
1906d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_BitMask2Mask(uint8_t* dest_scan,
1907d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               const uint8_t* src_scan,
1908d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               int mask_alpha,
1909d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               int src_left,
1910d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               int pixel_count,
1911d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               const uint8_t* clip_scan) {
1912d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < pixel_count; col++) {
1913d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (!(src_scan[(src_left + col) / 8] & (1 << (7 - (src_left + col) % 8)))) {
1914d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1915d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
1916d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1917d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int src_alpha;
1918d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (clip_scan) {
1919d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_alpha = mask_alpha * clip_scan[col] / 255;
1920d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
1921d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_alpha = mask_alpha;
1922d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1923d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t back_alpha = *dest_scan;
1924d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (!back_alpha) {
1925d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = src_alpha;
1926d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else if (src_alpha) {
1927d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = back_alpha + src_alpha - back_alpha * src_alpha / 255;
1928d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1929d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan++;
1930d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
1931d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
1932d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
1933d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_BitMask2Gray(uint8_t* dest_scan,
1934d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               const uint8_t* src_scan,
1935d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               int mask_alpha,
1936d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               int src_gray,
1937d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               int src_left,
1938d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               int pixel_count,
1939d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               const uint8_t* clip_scan) {
1940d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < pixel_count; col++) {
1941d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (!(src_scan[(src_left + col) / 8] & (1 << (7 - (src_left + col) % 8)))) {
1942d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1943d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
1944d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1945d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int src_alpha;
1946d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (clip_scan) {
1947d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_alpha = mask_alpha * clip_scan[col] / 255;
1948d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
1949d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_alpha = mask_alpha;
1950d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1951d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (src_alpha) {
1952d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, src_gray, src_alpha);
1953d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1954d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan++;
1955d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
1956d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
1957d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
1958d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_BitMask2Graya(uint8_t* dest_scan,
1959d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                const uint8_t* src_scan,
1960d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                int mask_alpha,
1961d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                int src_gray,
1962d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                int src_left,
1963d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                int pixel_count,
1964d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                const uint8_t* clip_scan,
1965d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                uint8_t* dest_alpha_scan) {
1966d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < pixel_count; col++) {
1967d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (!(src_scan[(src_left + col) / 8] & (1 << (7 - (src_left + col) % 8)))) {
1968d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1969d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_alpha_scan++;
1970d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
1971d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1972d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int src_alpha;
1973d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (clip_scan) {
1974d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_alpha = mask_alpha * clip_scan[col] / 255;
1975d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
1976d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_alpha = mask_alpha;
1977d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1978d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t back_alpha = *dest_alpha_scan;
1979d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (back_alpha == 0) {
1980d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_scan++ = src_gray;
1981d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      *dest_alpha_scan++ = src_alpha;
1982d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
1983d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1984d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (src_alpha == 0) {
1985d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan++;
1986d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_alpha_scan++;
1987d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
1988d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
1989d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t dest_alpha = back_alpha + src_alpha - back_alpha * src_alpha / 255;
1990d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    *dest_alpha_scan++ = dest_alpha;
1991d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int alpha_ratio = src_alpha * 255 / dest_alpha;
1992d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    *dest_scan = FXDIB_ALPHA_MERGE(*dest_scan, src_gray, alpha_ratio);
1993d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan++;
1994d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
1995d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
1996d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
1997d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_Argb2Argb_RgbByteOrder(uint8_t* dest_scan,
1998d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                         const uint8_t* src_scan,
1999d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                         int pixel_count,
2000d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                         int blend_type,
2001d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                         const uint8_t* clip_scan) {
2002d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int blended_colors[3];
2003d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  bool bNonseparableBlend = blend_type >= FXDIB_BLEND_NONSEPARABLE;
2004d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < pixel_count; col++) {
2005d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t back_alpha = dest_scan[3];
2006d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (back_alpha == 0) {
2007d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (clip_scan) {
2008d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        int src_alpha = clip_scan[col] * src_scan[3] / 255;
2009d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan[3] = src_alpha;
2010d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan[0] = src_scan[2];
2011d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan[1] = src_scan[1];
2012d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan[2] = src_scan[0];
2013d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      } else {
2014d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        FXARGB_RGBORDERCOPY(dest_scan, src_scan);
2015d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
2016d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += 4;
2017d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan += 4;
2018d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
2019d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2020d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t src_alpha;
2021d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (clip_scan) {
2022d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_alpha = clip_scan[col] * src_scan[3] / 255;
2023d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
2024d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_alpha = src_scan[3];
2025d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2026d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (src_alpha == 0) {
2027d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += 4;
2028d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan += 4;
2029d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
2030d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2031d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t dest_alpha = back_alpha + src_alpha - back_alpha * src_alpha / 255;
2032d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan[3] = dest_alpha;
2033d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int alpha_ratio = src_alpha * 255 / dest_alpha;
2034d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (bNonseparableBlend) {
2035d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t dest_scan_o[3];
2036d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan_o[0] = dest_scan[2];
2037d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan_o[1] = dest_scan[1];
2038d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan_o[2] = dest_scan[0];
2039d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      RGB_Blend(blend_type, src_scan, dest_scan_o, blended_colors);
2040d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2041d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    for (int color = 0; color < 3; color++) {
2042d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int index = 2 - color;
2043d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (blend_type) {
2044d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        int blended = bNonseparableBlend
2045d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                          ? blended_colors[color]
2046d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                          : Blend(blend_type, dest_scan[index], *src_scan);
2047d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        blended = FXDIB_ALPHA_MERGE(*src_scan, blended, back_alpha);
2048d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan[index] =
2049d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            FXDIB_ALPHA_MERGE(dest_scan[index], blended, alpha_ratio);
2050d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      } else {
2051d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan[index] =
2052d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            FXDIB_ALPHA_MERGE(dest_scan[index], *src_scan, alpha_ratio);
2053d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
2054d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan++;
2055d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2056d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan += 4;
2057d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    src_scan++;
2058d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
2059d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
2060d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
2061d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_Rgb2Argb_Blend_NoClip_RgbByteOrder(uint8_t* dest_scan,
2062d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                     const uint8_t* src_scan,
2063d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                     int width,
2064d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                     int blend_type,
2065d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                     int src_Bpp) {
2066d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int blended_colors[3];
2067d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  bool bNonseparableBlend = blend_type >= FXDIB_BLEND_NONSEPARABLE;
2068d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int src_gap = src_Bpp - 3;
2069d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < width; col++) {
2070d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t back_alpha = dest_scan[3];
2071d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (back_alpha == 0) {
2072d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (src_Bpp == 4) {
2073d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        FXARGB_SETRGBORDERDIB(dest_scan, 0xff000000 | FXARGB_GETDIB(src_scan));
2074d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      } else {
2075d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        FXARGB_SETRGBORDERDIB(dest_scan, FXARGB_MAKE(0xff, src_scan[2],
2076d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                     src_scan[1], src_scan[0]));
2077d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
2078d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += 4;
2079d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan += src_Bpp;
2080d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
2081d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2082d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan[3] = 0xff;
2083d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (bNonseparableBlend) {
2084d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t dest_scan_o[3];
2085d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan_o[0] = dest_scan[2];
2086d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan_o[1] = dest_scan[1];
2087d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan_o[2] = dest_scan[0];
2088d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      RGB_Blend(blend_type, src_scan, dest_scan_o, blended_colors);
2089d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2090d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    for (int color = 0; color < 3; color++) {
2091d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int index = 2 - color;
2092d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int src_color = *src_scan;
2093d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int blended = bNonseparableBlend
2094d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                        ? blended_colors[color]
2095d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                        : Blend(blend_type, dest_scan[index], src_color);
2096d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[index] = FXDIB_ALPHA_MERGE(src_color, blended, back_alpha);
2097d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan++;
2098d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2099d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan += 4;
2100d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    src_scan += src_gap;
2101d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
2102d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
2103d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
2104d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_Argb2Rgb_Blend_RgbByteOrder(uint8_t* dest_scan,
2105d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                              const uint8_t* src_scan,
2106d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                              int width,
2107d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                              int blend_type,
2108d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                              int dest_Bpp,
2109d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                              const uint8_t* clip_scan) {
2110d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int blended_colors[3];
2111d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  bool bNonseparableBlend = blend_type >= FXDIB_BLEND_NONSEPARABLE;
2112d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < width; col++) {
2113d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t src_alpha;
2114d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (clip_scan) {
2115d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_alpha = src_scan[3] * (*clip_scan++) / 255;
2116d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
2117d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_alpha = src_scan[3];
2118d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2119d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (src_alpha == 0) {
2120d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += dest_Bpp;
2121d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan += 4;
2122d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
2123d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2124d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (bNonseparableBlend) {
2125d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t dest_scan_o[3];
2126d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan_o[0] = dest_scan[2];
2127d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan_o[1] = dest_scan[1];
2128d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan_o[2] = dest_scan[0];
2129d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      RGB_Blend(blend_type, src_scan, dest_scan_o, blended_colors);
2130d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2131d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    for (int color = 0; color < 3; color++) {
2132d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int index = 2 - color;
2133d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int back_color = dest_scan[index];
2134d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int blended = bNonseparableBlend
2135d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                        ? blended_colors[color]
2136d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                        : Blend(blend_type, back_color, *src_scan);
2137d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[index] = FXDIB_ALPHA_MERGE(back_color, blended, src_alpha);
2138d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan++;
2139d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2140d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan += dest_Bpp;
2141d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    src_scan++;
2142d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
2143d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
2144d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
2145d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_Rgb2Argb_NoBlend_NoClip_RgbByteOrder(uint8_t* dest_scan,
2146d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                       const uint8_t* src_scan,
2147d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                       int width,
2148d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                       int src_Bpp) {
2149d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < width; col++) {
2150d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (src_Bpp == 4) {
2151d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      FXARGB_SETRGBORDERDIB(dest_scan, 0xff000000 | FXARGB_GETDIB(src_scan));
2152d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
2153d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      FXARGB_SETRGBORDERDIB(
2154d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          dest_scan, FXARGB_MAKE(0xff, src_scan[2], src_scan[1], src_scan[0]));
2155d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2156d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan += 4;
2157d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    src_scan += src_Bpp;
2158d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
2159d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
2160d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
2161d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_Rgb2Rgb_Blend_NoClip_RgbByteOrder(uint8_t* dest_scan,
2162d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                    const uint8_t* src_scan,
2163d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                    int width,
2164d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                    int blend_type,
2165d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                    int dest_Bpp,
2166d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                    int src_Bpp) {
2167d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int blended_colors[3];
2168d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  bool bNonseparableBlend = blend_type >= FXDIB_BLEND_NONSEPARABLE;
2169d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int src_gap = src_Bpp - 3;
2170d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < width; col++) {
2171d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (bNonseparableBlend) {
2172d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t dest_scan_o[3];
2173d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan_o[0] = dest_scan[2];
2174d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan_o[1] = dest_scan[1];
2175d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan_o[2] = dest_scan[0];
2176d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      RGB_Blend(blend_type, src_scan, dest_scan_o, blended_colors);
2177d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2178d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    for (int color = 0; color < 3; color++) {
2179d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int index = 2 - color;
2180d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int back_color = dest_scan[index];
2181d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int src_color = *src_scan;
2182d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int blended = bNonseparableBlend
2183d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                        ? blended_colors[color]
2184d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                        : Blend(blend_type, back_color, src_color);
2185d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[index] = blended;
2186d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan++;
2187d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2188d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan += dest_Bpp;
2189d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    src_scan += src_gap;
2190d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
2191d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
2192d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
2193d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_Argb2Rgb_NoBlend_RgbByteOrder(uint8_t* dest_scan,
2194d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                const uint8_t* src_scan,
2195d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                int width,
2196d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                int dest_Bpp,
2197d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                const uint8_t* clip_scan) {
2198d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < width; col++) {
2199d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t src_alpha;
2200d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (clip_scan) {
2201d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_alpha = src_scan[3] * (*clip_scan++) / 255;
2202d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
2203d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_alpha = src_scan[3];
2204d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2205d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (src_alpha == 255) {
2206d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[2] = *src_scan++;
2207d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[1] = *src_scan++;
2208d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[0] = *src_scan++;
2209d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += dest_Bpp;
2210d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan++;
2211d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
2212d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2213d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (src_alpha == 0) {
2214d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += dest_Bpp;
2215d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan += 4;
2216d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
2217d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2218d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    for (int color = 0; color < 3; color++) {
2219d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int index = 2 - color;
2220d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[index] =
2221d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          FXDIB_ALPHA_MERGE(dest_scan[index], *src_scan, src_alpha);
2222d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan++;
2223d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2224d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan += dest_Bpp;
2225d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    src_scan++;
2226d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
2227d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
2228d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
2229d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_Rgb2Rgb_NoBlend_NoClip_RgbByteOrder(uint8_t* dest_scan,
2230d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                      const uint8_t* src_scan,
2231d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                      int width,
2232d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                      int dest_Bpp,
2233d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                      int src_Bpp) {
2234d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < width; col++) {
2235d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan[2] = src_scan[0];
2236d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan[1] = src_scan[1];
2237d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan[0] = src_scan[2];
2238d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan += dest_Bpp;
2239d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    src_scan += src_Bpp;
2240d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
2241d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
2242d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
2243d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_Rgb2Argb_Blend_Clip_RgbByteOrder(uint8_t* dest_scan,
2244d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                   const uint8_t* src_scan,
2245d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                   int width,
2246d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                   int blend_type,
2247d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                   int src_Bpp,
2248d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                   const uint8_t* clip_scan) {
2249d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int blended_colors[3];
2250d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  bool bNonseparableBlend = blend_type >= FXDIB_BLEND_NONSEPARABLE;
2251d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int src_gap = src_Bpp - 3;
2252d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < width; col++) {
2253d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int src_alpha = *clip_scan++;
2254d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t back_alpha = dest_scan[3];
2255d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (back_alpha == 0) {
2256d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[2] = *src_scan++;
2257d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[1] = *src_scan++;
2258d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[0] = *src_scan++;
2259d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan += src_gap;
2260d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += 4;
2261d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
2262d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2263d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (src_alpha == 0) {
2264d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += 4;
2265d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan += src_Bpp;
2266d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
2267d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2268d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t dest_alpha = back_alpha + src_alpha - back_alpha * src_alpha / 255;
2269d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan[3] = dest_alpha;
2270d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int alpha_ratio = src_alpha * 255 / dest_alpha;
2271d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (bNonseparableBlend) {
2272d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t dest_scan_o[3];
2273d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan_o[0] = dest_scan[2];
2274d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan_o[1] = dest_scan[1];
2275d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan_o[2] = dest_scan[0];
2276d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      RGB_Blend(blend_type, src_scan, dest_scan_o, blended_colors);
2277d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2278d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    for (int color = 0; color < 3; color++) {
2279d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int index = 2 - color;
2280d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int src_color = *src_scan;
2281d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int blended = bNonseparableBlend
2282d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                        ? blended_colors[color]
2283d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                        : Blend(blend_type, dest_scan[index], src_color);
2284d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      blended = FXDIB_ALPHA_MERGE(src_color, blended, back_alpha);
2285d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[index] =
2286d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          FXDIB_ALPHA_MERGE(dest_scan[index], blended, alpha_ratio);
2287d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan++;
2288d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2289d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan += 4;
2290d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    src_scan += src_gap;
2291d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
2292d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
2293d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
2294d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_Rgb2Rgb_Blend_Clip_RgbByteOrder(uint8_t* dest_scan,
2295d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                  const uint8_t* src_scan,
2296d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                  int width,
2297d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                  int blend_type,
2298d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                  int dest_Bpp,
2299d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                  int src_Bpp,
2300d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                  const uint8_t* clip_scan) {
2301d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int blended_colors[3];
2302d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  bool bNonseparableBlend = blend_type >= FXDIB_BLEND_NONSEPARABLE;
2303d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int src_gap = src_Bpp - 3;
2304d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < width; col++) {
2305d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t src_alpha = *clip_scan++;
2306d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (src_alpha == 0) {
2307d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += dest_Bpp;
2308d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan += src_Bpp;
2309d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
2310d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2311d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (bNonseparableBlend) {
2312d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t dest_scan_o[3];
2313d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan_o[0] = dest_scan[2];
2314d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan_o[1] = dest_scan[1];
2315d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan_o[2] = dest_scan[0];
2316d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      RGB_Blend(blend_type, src_scan, dest_scan_o, blended_colors);
2317d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2318d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    for (int color = 0; color < 3; color++) {
2319d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int index = 2 - color;
2320d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int src_color = *src_scan;
2321d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int back_color = dest_scan[index];
2322d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int blended = bNonseparableBlend
2323d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                        ? blended_colors[color]
2324d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                        : Blend(blend_type, back_color, src_color);
2325d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[index] = FXDIB_ALPHA_MERGE(back_color, blended, src_alpha);
2326d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan++;
2327d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2328d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan += dest_Bpp;
2329d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    src_scan += src_gap;
2330d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
2331d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
2332d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
2333d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_Rgb2Argb_NoBlend_Clip_RgbByteOrder(uint8_t* dest_scan,
2334d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                     const uint8_t* src_scan,
2335d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                     int width,
2336d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                     int src_Bpp,
2337d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                     const uint8_t* clip_scan) {
2338d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int src_gap = src_Bpp - 3;
2339d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < width; col++) {
2340d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int src_alpha = clip_scan[col];
2341d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (src_alpha == 255) {
2342d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[2] = *src_scan++;
2343d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[1] = *src_scan++;
2344d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[0] = *src_scan++;
2345d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[3] = 255;
2346d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += 4;
2347d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan += src_gap;
2348d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
2349d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2350d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (src_alpha == 0) {
2351d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += 4;
2352d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan += src_Bpp;
2353d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
2354d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2355d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int back_alpha = dest_scan[3];
2356d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t dest_alpha = back_alpha + src_alpha - back_alpha * src_alpha / 255;
2357d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan[3] = dest_alpha;
2358d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int alpha_ratio = src_alpha * 255 / dest_alpha;
2359d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    for (int color = 0; color < 3; color++) {
2360d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int index = 2 - color;
2361d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[index] =
2362d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          FXDIB_ALPHA_MERGE(dest_scan[index], *src_scan, alpha_ratio);
2363d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan++;
2364d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2365d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan += 4;
2366d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    src_scan += src_gap;
2367d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
2368d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
2369d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
2370d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_Rgb2Rgb_NoBlend_Clip_RgbByteOrder(uint8_t* dest_scan,
2371d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                    const uint8_t* src_scan,
2372d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                    int width,
2373d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                    int dest_Bpp,
2374d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                    int src_Bpp,
2375d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                    const uint8_t* clip_scan) {
2376d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < width; col++) {
2377d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int src_alpha = clip_scan[col];
2378d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (src_alpha == 255) {
2379d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[2] = src_scan[0];
2380d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[1] = src_scan[1];
2381d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[0] = src_scan[2];
2382d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else if (src_alpha) {
2383d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[2] = FXDIB_ALPHA_MERGE(dest_scan[2], *src_scan, src_alpha);
2384d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan++;
2385d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[1] = FXDIB_ALPHA_MERGE(dest_scan[1], *src_scan, src_alpha);
2386d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan++;
2387d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[0] = FXDIB_ALPHA_MERGE(dest_scan[0], *src_scan, src_alpha);
2388d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += dest_Bpp;
2389d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan += src_Bpp - 2;
2390d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
2391d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2392d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan += dest_Bpp;
2393d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    src_scan += src_Bpp;
2394d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
2395d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
2396d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
2397d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_8bppRgb2Rgb_NoBlend_RgbByteOrder(uint8_t* dest_scan,
2398d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                   const uint8_t* src_scan,
2399d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                   FX_ARGB* pPalette,
2400d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                   int pixel_count,
2401d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                   int DestBpp,
2402d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                   const uint8_t* clip_scan) {
2403d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < pixel_count; col++) {
2404d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    FX_ARGB argb = pPalette ? pPalette[*src_scan] : (*src_scan) * 0x010101;
2405d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int src_r = FXARGB_R(argb);
2406d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int src_g = FXARGB_G(argb);
2407d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int src_b = FXARGB_B(argb);
2408d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (clip_scan && clip_scan[col] < 255) {
2409d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[2] = FXDIB_ALPHA_MERGE(dest_scan[2], src_b, clip_scan[col]);
2410d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[1] = FXDIB_ALPHA_MERGE(dest_scan[1], src_g, clip_scan[col]);
2411d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[0] = FXDIB_ALPHA_MERGE(dest_scan[0], src_r, clip_scan[col]);
2412d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
2413d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[2] = src_b;
2414d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[1] = src_g;
2415d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[0] = src_r;
2416d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2417d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan += DestBpp;
2418d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    src_scan++;
2419d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
2420d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
2421d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
2422d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_1bppRgb2Rgb_NoBlend_RgbByteOrder(uint8_t* dest_scan,
2423d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                   const uint8_t* src_scan,
2424d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                   int src_left,
2425d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                   FX_ARGB* pPalette,
2426d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                   int pixel_count,
2427d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                   int DestBpp,
2428d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                   const uint8_t* clip_scan) {
2429d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int reset_r, reset_g, reset_b;
2430d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int set_r, set_g, set_b;
2431d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  if (pPalette) {
2432d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    reset_r = FXARGB_R(pPalette[0]);
2433d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    reset_g = FXARGB_G(pPalette[0]);
2434d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    reset_b = FXARGB_B(pPalette[0]);
2435d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    set_r = FXARGB_R(pPalette[1]);
2436d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    set_g = FXARGB_G(pPalette[1]);
2437d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    set_b = FXARGB_B(pPalette[1]);
2438d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  } else {
2439d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    reset_r = reset_g = reset_b = 0;
2440d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    set_r = set_g = set_b = 255;
2441d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
2442d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < pixel_count; col++) {
2443d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int src_r, src_g, src_b;
2444d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (src_scan[(col + src_left) / 8] & (1 << (7 - (col + src_left) % 8))) {
2445d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_r = set_r;
2446d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_g = set_g;
2447d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_b = set_b;
2448d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
2449d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_r = reset_r;
2450d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_g = reset_g;
2451d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_b = reset_b;
2452d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2453d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (clip_scan && clip_scan[col] < 255) {
2454d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[2] = FXDIB_ALPHA_MERGE(dest_scan[2], src_b, clip_scan[col]);
2455d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[1] = FXDIB_ALPHA_MERGE(dest_scan[1], src_g, clip_scan[col]);
2456d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[0] = FXDIB_ALPHA_MERGE(dest_scan[0], src_r, clip_scan[col]);
2457d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
2458d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[2] = src_b;
2459d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[1] = src_g;
2460d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[0] = src_r;
2461d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2462d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan += DestBpp;
2463d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
2464d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
2465d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
2466d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_8bppRgb2Argb_NoBlend_RgbByteOrder(uint8_t* dest_scan,
2467d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                    const uint8_t* src_scan,
2468d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                    int width,
2469d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                    FX_ARGB* pPalette,
2470d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                    const uint8_t* clip_scan) {
2471d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < width; col++) {
2472d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int src_r, src_g, src_b;
2473d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (pPalette) {
2474d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      FX_ARGB argb = pPalette[*src_scan];
2475d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_r = FXARGB_R(argb);
2476d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_g = FXARGB_G(argb);
2477d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_b = FXARGB_B(argb);
2478d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
2479d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_r = src_g = src_b = *src_scan;
2480d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2481d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (!clip_scan || clip_scan[col] == 255) {
2482d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[2] = src_b;
2483d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[1] = src_g;
2484d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[0] = src_r;
2485d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[3] = 255;
2486d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan++;
2487d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += 4;
2488d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
2489d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2490d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int src_alpha = clip_scan[col];
2491d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (src_alpha == 0) {
2492d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += 4;
2493d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_scan++;
2494d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
2495d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2496d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int back_alpha = dest_scan[3];
2497d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t dest_alpha = back_alpha + src_alpha - back_alpha * src_alpha / 255;
2498d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan[3] = dest_alpha;
2499d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int alpha_ratio = src_alpha * 255 / dest_alpha;
2500d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan[2] = FXDIB_ALPHA_MERGE(dest_scan[2], src_b, alpha_ratio);
2501d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan[1] = FXDIB_ALPHA_MERGE(dest_scan[1], src_g, alpha_ratio);
2502d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan[0] = FXDIB_ALPHA_MERGE(dest_scan[0], src_r, alpha_ratio);
2503d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan += 4;
2504d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    src_scan++;
2505d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
2506d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
2507d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
2508d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_1bppRgb2Argb_NoBlend_RgbByteOrder(uint8_t* dest_scan,
2509d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                    const uint8_t* src_scan,
2510d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                    int src_left,
2511d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                    int width,
2512d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                    FX_ARGB* pPalette,
2513d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                    const uint8_t* clip_scan) {
2514d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int reset_r, reset_g, reset_b;
2515d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int set_r, set_g, set_b;
2516d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  if (pPalette) {
2517d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    reset_r = FXARGB_R(pPalette[0]);
2518d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    reset_g = FXARGB_G(pPalette[0]);
2519d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    reset_b = FXARGB_B(pPalette[0]);
2520d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    set_r = FXARGB_R(pPalette[1]);
2521d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    set_g = FXARGB_G(pPalette[1]);
2522d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    set_b = FXARGB_B(pPalette[1]);
2523d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  } else {
2524d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    reset_r = reset_g = reset_b = 0;
2525d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    set_r = set_g = set_b = 255;
2526d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
2527d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < width; col++) {
2528d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int src_r, src_g, src_b;
2529d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (src_scan[(col + src_left) / 8] & (1 << (7 - (col + src_left) % 8))) {
2530d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_r = set_r;
2531d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_g = set_g;
2532d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_b = set_b;
2533d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
2534d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_r = reset_r;
2535d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_g = reset_g;
2536d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_b = reset_b;
2537d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2538d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (!clip_scan || clip_scan[col] == 255) {
2539d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[2] = src_b;
2540d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[1] = src_g;
2541d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[0] = src_r;
2542d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[3] = 255;
2543d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += 4;
2544d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
2545d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2546d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int src_alpha = clip_scan[col];
2547d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (src_alpha == 0) {
2548d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += 4;
2549d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
2550d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2551d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int back_alpha = dest_scan[3];
2552d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t dest_alpha = back_alpha + src_alpha - back_alpha * src_alpha / 255;
2553d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan[3] = dest_alpha;
2554d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int alpha_ratio = src_alpha * 255 / dest_alpha;
2555d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan[2] = FXDIB_ALPHA_MERGE(dest_scan[2], src_b, alpha_ratio);
2556d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan[1] = FXDIB_ALPHA_MERGE(dest_scan[1], src_g, alpha_ratio);
2557d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan[0] = FXDIB_ALPHA_MERGE(dest_scan[0], src_r, alpha_ratio);
2558d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan += 4;
2559d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
2560d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
2561d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
2562d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_ByteMask2Argb_RgbByteOrder(uint8_t* dest_scan,
2563d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                             const uint8_t* src_scan,
2564d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                             int mask_alpha,
2565d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                             int src_r,
2566d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                             int src_g,
2567d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                             int src_b,
2568d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                             int pixel_count,
2569d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                             int blend_type,
2570d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                             const uint8_t* clip_scan) {
2571d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < pixel_count; col++) {
2572d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int src_alpha;
2573d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (clip_scan) {
2574d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_alpha = mask_alpha * clip_scan[col] * src_scan[col] / 255 / 255;
2575d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
2576d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_alpha = mask_alpha * src_scan[col] / 255;
2577d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2578d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t back_alpha = dest_scan[3];
2579d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (back_alpha == 0) {
2580d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      FXARGB_SETRGBORDERDIB(dest_scan,
2581d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                            FXARGB_MAKE(src_alpha, src_r, src_g, src_b));
2582d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += 4;
2583d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
2584d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2585d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (src_alpha == 0) {
2586d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += 4;
2587d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
2588d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2589d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t dest_alpha = back_alpha + src_alpha - back_alpha * src_alpha / 255;
2590d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan[3] = dest_alpha;
2591d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int alpha_ratio = src_alpha * 255 / dest_alpha;
2592d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (blend_type >= FXDIB_BLEND_NONSEPARABLE) {
2593d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int blended_colors[3];
2594d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t scan[3] = {static_cast<uint8_t>(src_b),
2595d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                         static_cast<uint8_t>(src_g),
2596d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                         static_cast<uint8_t>(src_r)};
2597d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t dest_scan_o[3] = {dest_scan[2], dest_scan[1], dest_scan[0]};
2598d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      RGB_Blend(blend_type, scan, dest_scan_o, blended_colors);
2599d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[2] =
2600d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          FXDIB_ALPHA_MERGE(dest_scan[2], blended_colors[0], alpha_ratio);
2601d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[1] =
2602d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          FXDIB_ALPHA_MERGE(dest_scan[1], blended_colors[1], alpha_ratio);
2603d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[0] =
2604d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          FXDIB_ALPHA_MERGE(dest_scan[0], blended_colors[2], alpha_ratio);
2605d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else if (blend_type) {
2606d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int blended = Blend(blend_type, dest_scan[2], src_b);
2607d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      blended = FXDIB_ALPHA_MERGE(src_b, blended, back_alpha);
2608d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[2] = FXDIB_ALPHA_MERGE(dest_scan[2], blended, alpha_ratio);
2609d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      blended = Blend(blend_type, dest_scan[1], src_g);
2610d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      blended = FXDIB_ALPHA_MERGE(src_g, blended, back_alpha);
2611d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[1] = FXDIB_ALPHA_MERGE(dest_scan[1], blended, alpha_ratio);
2612d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      blended = Blend(blend_type, dest_scan[0], src_r);
2613d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      blended = FXDIB_ALPHA_MERGE(src_r, blended, back_alpha);
2614d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[0] = FXDIB_ALPHA_MERGE(dest_scan[0], blended, alpha_ratio);
2615d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
2616d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[2] = FXDIB_ALPHA_MERGE(dest_scan[2], src_b, alpha_ratio);
2617d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[1] = FXDIB_ALPHA_MERGE(dest_scan[1], src_g, alpha_ratio);
2618d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[0] = FXDIB_ALPHA_MERGE(dest_scan[0], src_r, alpha_ratio);
2619d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2620d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan += 4;
2621d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
2622d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
2623d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
2624d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_ByteMask2Rgb_RgbByteOrder(uint8_t* dest_scan,
2625d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                            const uint8_t* src_scan,
2626d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                            int mask_alpha,
2627d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                            int src_r,
2628d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                            int src_g,
2629d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                            int src_b,
2630d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                            int pixel_count,
2631d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                            int blend_type,
2632d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                            int Bpp,
2633d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                            const uint8_t* clip_scan) {
2634d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < pixel_count; col++) {
2635d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int src_alpha;
2636d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (clip_scan) {
2637d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_alpha = mask_alpha * clip_scan[col] * src_scan[col] / 255 / 255;
2638d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
2639d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_alpha = mask_alpha * src_scan[col] / 255;
2640d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2641d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (src_alpha == 0) {
2642d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += Bpp;
2643d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
2644d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2645d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (blend_type >= FXDIB_BLEND_NONSEPARABLE) {
2646d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int blended_colors[3];
2647d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t scan[3] = {static_cast<uint8_t>(src_b),
2648d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                         static_cast<uint8_t>(src_g),
2649d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                         static_cast<uint8_t>(src_r)};
2650d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t dest_scan_o[3] = {dest_scan[2], dest_scan[1], dest_scan[0]};
2651d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      RGB_Blend(blend_type, scan, dest_scan_o, blended_colors);
2652d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[2] =
2653d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          FXDIB_ALPHA_MERGE(dest_scan[2], blended_colors[0], src_alpha);
2654d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[1] =
2655d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          FXDIB_ALPHA_MERGE(dest_scan[1], blended_colors[1], src_alpha);
2656d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[0] =
2657d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          FXDIB_ALPHA_MERGE(dest_scan[0], blended_colors[2], src_alpha);
2658d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else if (blend_type) {
2659d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int blended = Blend(blend_type, dest_scan[2], src_b);
2660d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[2] = FXDIB_ALPHA_MERGE(dest_scan[2], blended, src_alpha);
2661d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      blended = Blend(blend_type, dest_scan[1], src_g);
2662d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[1] = FXDIB_ALPHA_MERGE(dest_scan[1], blended, src_alpha);
2663d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      blended = Blend(blend_type, dest_scan[0], src_r);
2664d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[0] = FXDIB_ALPHA_MERGE(dest_scan[0], blended, src_alpha);
2665d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
2666d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[2] = FXDIB_ALPHA_MERGE(dest_scan[2], src_b, src_alpha);
2667d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[1] = FXDIB_ALPHA_MERGE(dest_scan[1], src_g, src_alpha);
2668d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[0] = FXDIB_ALPHA_MERGE(dest_scan[0], src_r, src_alpha);
2669d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2670d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan += Bpp;
2671d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
2672d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
2673d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
2674d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_BitMask2Argb_RgbByteOrder(uint8_t* dest_scan,
2675d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                            const uint8_t* src_scan,
2676d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                            int mask_alpha,
2677d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                            int src_r,
2678d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                            int src_g,
2679d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                            int src_b,
2680d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                            int src_left,
2681d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                            int pixel_count,
2682d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                            int blend_type,
2683d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                            const uint8_t* clip_scan) {
2684d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  if (blend_type == FXDIB_BLEND_NORMAL && !clip_scan && mask_alpha == 255) {
2685d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    FX_ARGB argb = FXARGB_MAKE(0xff, src_r, src_g, src_b);
2686d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    for (int col = 0; col < pixel_count; col++) {
2687d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (src_scan[(src_left + col) / 8] & (1 << (7 - (src_left + col) % 8))) {
2688d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        FXARGB_SETRGBORDERDIB(dest_scan, argb);
2689d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
2690d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += 4;
2691d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2692d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    return;
2693d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
2694d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < pixel_count; col++) {
2695d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (!(src_scan[(src_left + col) / 8] & (1 << (7 - (src_left + col) % 8)))) {
2696d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += 4;
2697d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
2698d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2699d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int src_alpha;
2700d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (clip_scan) {
2701d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_alpha = mask_alpha * clip_scan[col] / 255;
2702d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
2703d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_alpha = mask_alpha;
2704d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2705d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t back_alpha = dest_scan[3];
2706d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (back_alpha == 0) {
2707d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      FXARGB_SETRGBORDERDIB(dest_scan,
2708d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                            FXARGB_MAKE(src_alpha, src_r, src_g, src_b));
2709d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += 4;
2710d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
2711d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2712d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t dest_alpha = back_alpha + src_alpha - back_alpha * src_alpha / 255;
2713d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan[3] = dest_alpha;
2714d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int alpha_ratio = src_alpha * 255 / dest_alpha;
2715d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (blend_type >= FXDIB_BLEND_NONSEPARABLE) {
2716d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int blended_colors[3];
2717d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t scan[3] = {static_cast<uint8_t>(src_b),
2718d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                         static_cast<uint8_t>(src_g),
2719d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                         static_cast<uint8_t>(src_r)};
2720d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t dest_scan_o[3] = {dest_scan[2], dest_scan[1], dest_scan[0]};
2721d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      RGB_Blend(blend_type, scan, dest_scan_o, blended_colors);
2722d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[2] =
2723d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          FXDIB_ALPHA_MERGE(dest_scan[2], blended_colors[0], alpha_ratio);
2724d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[1] =
2725d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          FXDIB_ALPHA_MERGE(dest_scan[1], blended_colors[1], alpha_ratio);
2726d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[0] =
2727d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          FXDIB_ALPHA_MERGE(dest_scan[0], blended_colors[2], alpha_ratio);
2728d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else if (blend_type) {
2729d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int blended = Blend(blend_type, dest_scan[2], src_b);
2730d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      blended = FXDIB_ALPHA_MERGE(src_b, blended, back_alpha);
2731d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[2] = FXDIB_ALPHA_MERGE(dest_scan[2], blended, alpha_ratio);
2732d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      blended = Blend(blend_type, dest_scan[1], src_g);
2733d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      blended = FXDIB_ALPHA_MERGE(src_g, blended, back_alpha);
2734d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[1] = FXDIB_ALPHA_MERGE(dest_scan[1], blended, alpha_ratio);
2735d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      blended = Blend(blend_type, dest_scan[0], src_r);
2736d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      blended = FXDIB_ALPHA_MERGE(src_r, blended, back_alpha);
2737d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[0] = FXDIB_ALPHA_MERGE(dest_scan[0], blended, alpha_ratio);
2738d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
2739d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[2] = FXDIB_ALPHA_MERGE(dest_scan[2], src_b, alpha_ratio);
2740d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[1] = FXDIB_ALPHA_MERGE(dest_scan[1], src_g, alpha_ratio);
2741d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[0] = FXDIB_ALPHA_MERGE(dest_scan[0], src_r, alpha_ratio);
2742d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2743d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan += 4;
2744d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
2745d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
2746d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
2747d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CompositeRow_BitMask2Rgb_RgbByteOrder(uint8_t* dest_scan,
2748d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                           const uint8_t* src_scan,
2749d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                           int mask_alpha,
2750d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                           int src_r,
2751d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                           int src_g,
2752d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                           int src_b,
2753d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                           int src_left,
2754d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                           int pixel_count,
2755d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                           int blend_type,
2756d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                           int Bpp,
2757d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                           const uint8_t* clip_scan) {
2758d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  if (blend_type == FXDIB_BLEND_NORMAL && !clip_scan && mask_alpha == 255) {
2759d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    for (int col = 0; col < pixel_count; col++) {
2760d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (src_scan[(src_left + col) / 8] & (1 << (7 - (src_left + col) % 8))) {
2761d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan[2] = src_b;
2762d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan[1] = src_g;
2763d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan[0] = src_r;
2764d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
2765d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += Bpp;
2766d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2767d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    return;
2768d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
2769d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  for (int col = 0; col < pixel_count; col++) {
2770d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (!(src_scan[(src_left + col) / 8] & (1 << (7 - (src_left + col) % 8)))) {
2771d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += Bpp;
2772d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
2773d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2774d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int src_alpha;
2775d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (clip_scan) {
2776d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_alpha = mask_alpha * clip_scan[col] / 255;
2777d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
2778d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      src_alpha = mask_alpha;
2779d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2780d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (src_alpha == 0) {
2781d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan += Bpp;
2782d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      continue;
2783d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2784d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (blend_type >= FXDIB_BLEND_NONSEPARABLE) {
2785d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int blended_colors[3];
2786d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t scan[3] = {static_cast<uint8_t>(src_b),
2787d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                         static_cast<uint8_t>(src_g),
2788d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                         static_cast<uint8_t>(src_r)};
2789d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t dest_scan_o[3] = {dest_scan[2], dest_scan[1], dest_scan[0]};
2790d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      RGB_Blend(blend_type, scan, dest_scan_o, blended_colors);
2791d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[2] =
2792d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          FXDIB_ALPHA_MERGE(dest_scan[2], blended_colors[0], src_alpha);
2793d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[1] =
2794d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          FXDIB_ALPHA_MERGE(dest_scan[1], blended_colors[1], src_alpha);
2795d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[0] =
2796d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          FXDIB_ALPHA_MERGE(dest_scan[0], blended_colors[2], src_alpha);
2797d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else if (blend_type) {
2798d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int back_color = dest_scan[2];
2799d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int blended = Blend(blend_type, back_color, src_b);
2800d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[2] = FXDIB_ALPHA_MERGE(back_color, blended, src_alpha);
2801d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      back_color = dest_scan[1];
2802d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      blended = Blend(blend_type, back_color, src_g);
2803d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[1] = FXDIB_ALPHA_MERGE(back_color, blended, src_alpha);
2804d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      back_color = dest_scan[0];
2805d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      blended = Blend(blend_type, back_color, src_r);
2806d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[0] = FXDIB_ALPHA_MERGE(back_color, blended, src_alpha);
2807d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
2808d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[2] = FXDIB_ALPHA_MERGE(dest_scan[2], src_b, src_alpha);
2809d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[1] = FXDIB_ALPHA_MERGE(dest_scan[1], src_g, src_alpha);
2810d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      dest_scan[0] = FXDIB_ALPHA_MERGE(dest_scan[0], src_r, src_alpha);
2811d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2812d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    dest_scan += Bpp;
2813d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
2814d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
2815d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
2816d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}  // namespace
2817d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
2818d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. MoltmannCFX_ScanlineCompositor::CFX_ScanlineCompositor()
2819d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    : m_BlendType(FXDIB_BLEND_NORMAL), m_bRgbByteOrder(false) {}
2820d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
2821d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. MoltmannCFX_ScanlineCompositor::~CFX_ScanlineCompositor() {}
2822d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
2823d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannbool CFX_ScanlineCompositor::Init(FXDIB_Format dest_format,
2824d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                  FXDIB_Format src_format,
2825d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                  int32_t width,
2826d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                  uint32_t* pSrcPalette,
2827d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                  uint32_t mask_color,
2828d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                  int blend_type,
2829d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                  bool bClip,
2830d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                  bool bRgbByteOrder,
2831d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                  int alpha_flag) {
2832d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  m_SrcFormat = src_format;
2833d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  m_DestFormat = dest_format;
2834d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  m_BlendType = blend_type;
2835d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  m_bRgbByteOrder = bRgbByteOrder;
2836d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  if ((dest_format & 0xff) == 1)
2837d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    return false;
2838d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  if (m_SrcFormat == FXDIB_1bppMask || m_SrcFormat == FXDIB_8bppMask) {
2839d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    InitSourceMask(alpha_flag, mask_color);
2840d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    return true;
2841d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
2842d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  if ((~src_format & 0x0400) && (dest_format & 0x0400))
2843d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    return false;
2844d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  if ((m_SrcFormat & 0xff) <= 8) {
2845d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (dest_format == FXDIB_8bppMask)
2846d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      return true;
2847d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
2848d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    InitSourcePalette(src_format, dest_format, pSrcPalette);
2849d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    m_iTransparency =
2850d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        (dest_format == FXDIB_Argb ? 1 : 0) + (dest_format & 0x0200 ? 2 : 0) +
2851d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        (dest_format & 0x0400 ? 4 : 0) + ((src_format & 0xff) == 1 ? 8 : 0);
2852d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    return true;
2853d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
2854d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  m_iTransparency =
2855d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      (src_format & 0x0200 ? 0 : 1) + (dest_format & 0x0200 ? 0 : 2) +
2856d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      (blend_type == FXDIB_BLEND_NORMAL ? 4 : 0) + (bClip ? 8 : 0) +
2857d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      (src_format & 0x0400 ? 16 : 0) + (dest_format & 0x0400 ? 32 : 0);
2858d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  return true;
2859d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
2860d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
2861d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CFX_ScanlineCompositor::InitSourceMask(int alpha_flag,
2862d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                            uint32_t mask_color) {
2863d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int mask_black = 0;
2864d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  if (alpha_flag >> 8) {
2865d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    m_MaskAlpha = alpha_flag & 0xff;
2866d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    m_MaskRed = FXSYS_GetCValue(mask_color);
2867d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    m_MaskGreen = FXSYS_GetMValue(mask_color);
2868d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    m_MaskBlue = FXSYS_GetYValue(mask_color);
2869d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    mask_black = FXSYS_GetKValue(mask_color);
2870d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  } else {
2871d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    m_MaskAlpha = FXARGB_A(mask_color);
2872d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    m_MaskRed = FXARGB_R(mask_color);
2873d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    m_MaskGreen = FXARGB_G(mask_color);
2874d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    m_MaskBlue = FXARGB_B(mask_color);
2875d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
2876d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  if (m_DestFormat == FXDIB_8bppMask)
2877d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    return;
2878d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
2879d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  if ((m_DestFormat & 0xff) == 8) {
2880d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (alpha_flag >> 8) {
2881d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t r;
2882d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t g;
2883d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t b;
2884d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      std::tie(r, g, b) =
2885d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          AdobeCMYK_to_sRGB1(m_MaskRed, m_MaskGreen, m_MaskBlue, mask_black);
2886d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      m_MaskRed = FXRGB2GRAY(r, g, b);
2887d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
2888d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      m_MaskRed = FXRGB2GRAY(m_MaskRed, m_MaskGreen, m_MaskBlue);
2889d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2890d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (m_DestFormat & 0x0400)
2891d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      m_MaskRed = FX_CCOLOR(m_MaskRed);
2892d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    return;
2893d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
2894d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  uint8_t* mask_color_p = (uint8_t*)&mask_color;
2895d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  mask_color =
2896d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      (alpha_flag >> 8) ? FXCMYK_TODIB(mask_color) : FXARGB_TODIB(mask_color);
2897d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  if (alpha_flag >> 8) {
2898d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    std::tie(mask_color_p[2], mask_color_p[1], mask_color_p[0]) =
2899d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        AdobeCMYK_to_sRGB1(mask_color_p[0], mask_color_p[1], mask_color_p[2],
2900d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                           mask_color_p[3]);
2901d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    m_MaskRed = mask_color_p[2];
2902d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    m_MaskGreen = mask_color_p[1];
2903d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    m_MaskBlue = mask_color_p[0];
2904d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
2905d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
2906d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
2907d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CFX_ScanlineCompositor::InitSourcePalette(FXDIB_Format src_format,
2908d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                               FXDIB_Format dest_format,
2909d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                               const uint32_t* pSrcPalette) {
2910d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  bool isSrcCmyk = !!(src_format & 0x0400);
2911d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  bool isDstCmyk = !!(dest_format & 0x0400);
2912d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  m_pSrcPalette = nullptr;
2913d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  if (pSrcPalette) {
2914d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if ((dest_format & 0xff) == 8) {
2915d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      int pal_count = 1 << (src_format & 0xff);
2916d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t* gray_pal = FX_Alloc(uint8_t, pal_count);
2917d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      m_pSrcPalette.reset(reinterpret_cast<uint32_t*>(gray_pal));
2918d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (isSrcCmyk) {
2919d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        for (int i = 0; i < pal_count; ++i) {
2920d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          FX_CMYK cmyk = pSrcPalette[i];
2921d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          uint8_t r;
2922d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          uint8_t g;
2923d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          uint8_t b;
2924d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          std::tie(r, g, b) =
2925d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann              AdobeCMYK_to_sRGB1(FXSYS_GetCValue(cmyk), FXSYS_GetMValue(cmyk),
2926d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                 FXSYS_GetYValue(cmyk), FXSYS_GetKValue(cmyk));
2927d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          *gray_pal++ = FXRGB2GRAY(r, g, b);
2928d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        }
2929d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      } else {
2930d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        for (int i = 0; i < pal_count; ++i) {
2931d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          FX_ARGB argb = pSrcPalette[i];
2932d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          *gray_pal++ =
2933d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann              FXRGB2GRAY(FXARGB_R(argb), FXARGB_G(argb), FXARGB_B(argb));
2934d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        }
2935d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
2936d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      return;
2937d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2938d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int palsize = 1 << (src_format & 0xff);
2939d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    m_pSrcPalette.reset(FX_Alloc(uint32_t, palsize));
2940d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint32_t* pPalette = m_pSrcPalette.get();
2941d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (isDstCmyk == isSrcCmyk) {
2942d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      memcpy(pPalette, pSrcPalette, palsize * sizeof(uint32_t));
2943d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
2944d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      for (int i = 0; i < palsize; ++i) {
2945d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        FX_CMYK cmyk = pSrcPalette[i];
2946d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        uint8_t r;
2947d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        uint8_t g;
2948d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        uint8_t b;
2949d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        std::tie(r, g, b) =
2950d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            AdobeCMYK_to_sRGB1(FXSYS_GetCValue(cmyk), FXSYS_GetMValue(cmyk),
2951d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               FXSYS_GetYValue(cmyk), FXSYS_GetKValue(cmyk));
2952d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        pPalette[i] = FXARGB_MAKE(0xff, r, g, b);
2953d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
2954d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2955d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    return;
2956d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
2957d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  if ((dest_format & 0xff) == 8) {
2958d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int pal_count = 1 << (src_format & 0xff);
2959d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t* gray_pal = FX_Alloc(uint8_t, pal_count);
2960d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (pal_count == 2) {
2961d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      gray_pal[0] = 0;
2962d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      gray_pal[1] = 255;
2963d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
2964d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      for (int i = 0; i < pal_count; ++i)
2965d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        gray_pal[i] = i;
2966d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2967d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    m_pSrcPalette.reset(reinterpret_cast<uint32_t*>(gray_pal));
2968d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    return;
2969d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
2970d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int palsize = 1 << (src_format & 0xff);
2971d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  m_pSrcPalette.reset(FX_Alloc(uint32_t, palsize));
2972d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  uint32_t* pPalette = m_pSrcPalette.get();
2973d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  if (palsize == 2) {
2974d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    pPalette[0] = isSrcCmyk ? 255 : 0xff000000;
2975d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    pPalette[1] = isSrcCmyk ? 0 : 0xffffffff;
2976d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  } else {
2977d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    for (int i = 0; i < palsize; ++i)
2978d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      pPalette[i] = isSrcCmyk ? FX_CCOLOR(i) : (i * 0x10101);
2979d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
2980d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  if (isSrcCmyk != isDstCmyk) {
2981d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    for (int i = 0; i < palsize; ++i) {
2982d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      FX_CMYK cmyk = pPalette[i];
2983d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t r;
2984d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t g;
2985d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      uint8_t b;
2986d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      std::tie(r, g, b) =
2987d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          AdobeCMYK_to_sRGB1(FXSYS_GetCValue(cmyk), FXSYS_GetMValue(cmyk),
2988d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                             FXSYS_GetYValue(cmyk), FXSYS_GetKValue(cmyk));
2989d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      pPalette[i] = FXARGB_MAKE(0xff, r, g, b);
2990d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
2991d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
2992d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
2993d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
2994d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CFX_ScanlineCompositor::CompositeRgbBitmapLine(
2995d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t* dest_scan,
2996d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    const uint8_t* src_scan,
2997d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int width,
2998d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    const uint8_t* clip_scan,
2999d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    const uint8_t* src_extra_alpha,
3000d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t* dst_extra_alpha) {
3001d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int src_Bpp = (m_SrcFormat & 0xff) >> 3;
3002d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  int dest_Bpp = (m_DestFormat & 0xff) >> 3;
3003d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  if (m_bRgbByteOrder) {
3004d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    switch (m_iTransparency) {
3005d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      case 0:
3006d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      case 4:
3007d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      case 8:
3008d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      case 12:
3009d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_Argb2Argb_RgbByteOrder(dest_scan, src_scan, width,
3010d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                            m_BlendType, clip_scan);
3011d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        break;
3012d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      case 1:
3013d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_Rgb2Argb_Blend_NoClip_RgbByteOrder(
3014d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            dest_scan, src_scan, width, m_BlendType, src_Bpp);
3015d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        break;
3016d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      case 2:
3017d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      case 10:
3018d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_Argb2Rgb_Blend_RgbByteOrder(
3019d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            dest_scan, src_scan, width, m_BlendType, dest_Bpp, clip_scan);
3020d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        break;
3021d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      case 3:
3022d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_Rgb2Rgb_Blend_NoClip_RgbByteOrder(
3023d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            dest_scan, src_scan, width, m_BlendType, dest_Bpp, src_Bpp);
3024d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        break;
3025d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      case 5:
3026d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_Rgb2Argb_NoBlend_NoClip_RgbByteOrder(dest_scan, src_scan,
3027d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                          width, src_Bpp);
3028d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        break;
3029d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      case 6:
3030d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      case 14:
3031d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_Argb2Rgb_NoBlend_RgbByteOrder(dest_scan, src_scan, width,
3032d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                   dest_Bpp, clip_scan);
3033d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        break;
3034d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      case 7:
3035d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_Rgb2Rgb_NoBlend_NoClip_RgbByteOrder(
3036d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            dest_scan, src_scan, width, dest_Bpp, src_Bpp);
3037d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        break;
3038d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      case 9:
3039d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_Rgb2Argb_Blend_Clip_RgbByteOrder(
3040d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            dest_scan, src_scan, width, m_BlendType, src_Bpp, clip_scan);
3041d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        break;
3042d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      case 11:
3043d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_Rgb2Rgb_Blend_Clip_RgbByteOrder(dest_scan, src_scan, width,
3044d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                     m_BlendType, dest_Bpp,
3045d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                     src_Bpp, clip_scan);
3046d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        break;
3047d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      case 13:
3048d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_Rgb2Argb_NoBlend_Clip_RgbByteOrder(
3049d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            dest_scan, src_scan, width, src_Bpp, clip_scan);
3050d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        break;
3051d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      case 15:
3052d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_Rgb2Rgb_NoBlend_Clip_RgbByteOrder(
3053d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            dest_scan, src_scan, width, dest_Bpp, src_Bpp, clip_scan);
3054d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        break;
3055d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
3056d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    return;
3057d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
3058d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  if (m_DestFormat == FXDIB_8bppMask) {
3059d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (m_SrcFormat & 0x0200) {
3060d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (m_SrcFormat == FXDIB_Argb) {
3061d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_AlphaToMask(dest_scan, src_scan, width, clip_scan, 4);
3062d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      } else {
3063d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_AlphaToMask(dest_scan, src_extra_alpha, width, clip_scan,
3064d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                 1);
3065d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
3066d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
3067d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      CompositeRow_Rgb2Mask(dest_scan, src_scan, width, clip_scan);
3068d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
3069d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  } else if ((m_DestFormat & 0xff) == 8) {
3070d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (m_DestFormat & 0x0400) {
3071d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      for (int i = 0; i < width; ++i) {
3072d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan = ~*dest_scan;
3073d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan++;
3074d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
3075d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
3076d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (m_SrcFormat & 0x0200) {
3077d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (m_DestFormat & 0x0200) {
3078d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_Argb2Graya(dest_scan, src_scan, width, m_BlendType,
3079d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                clip_scan, src_extra_alpha, dst_extra_alpha);
3080d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      } else {
3081d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_Argb2Gray(dest_scan, src_scan, width, m_BlendType,
3082d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               clip_scan, src_extra_alpha);
3083d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
3084d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
3085d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (m_DestFormat & 0x0200) {
3086d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_Rgb2Graya(dest_scan, src_scan, src_Bpp, width, m_BlendType,
3087d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               clip_scan, dst_extra_alpha);
3088d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      } else {
3089d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_Rgb2Gray(dest_scan, src_scan, src_Bpp, width, m_BlendType,
3090d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                              clip_scan);
3091d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
3092d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
3093d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (m_DestFormat & 0x0400) {
3094d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      for (int i = 0; i < width; ++i) {
3095d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        *dest_scan = ~*dest_scan;
3096d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan++;
3097d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
3098d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
3099d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  } else {
3100d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    switch (m_iTransparency) {
3101d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      case 0:
3102d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      case 4:
3103d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      case 8:
3104d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      case 4 + 8: {
3105d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_Argb2Argb(dest_scan, src_scan, width, m_BlendType,
3106d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               clip_scan, dst_extra_alpha, src_extra_alpha);
3107d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      } break;
3108d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      case 1:
3109d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_Rgb2Argb_Blend_NoClip(
3110d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            dest_scan, src_scan, width, m_BlendType, src_Bpp, dst_extra_alpha);
3111d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        break;
3112d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      case 1 + 8:
3113d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_Rgb2Argb_Blend_Clip(dest_scan, src_scan, width,
3114d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                         m_BlendType, src_Bpp, clip_scan,
3115d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                         dst_extra_alpha);
3116d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        break;
3117d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      case 1 + 4:
3118d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_Rgb2Argb_NoBlend_NoClip(dest_scan, src_scan, width,
3119d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                             src_Bpp, dst_extra_alpha);
3120d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        break;
3121d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      case 1 + 4 + 8:
3122d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_Rgb2Argb_NoBlend_Clip(dest_scan, src_scan, width, src_Bpp,
3123d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                           clip_scan, dst_extra_alpha);
3124d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        break;
3125d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      case 2:
3126d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      case 2 + 8:
3127d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_Argb2Rgb_Blend(dest_scan, src_scan, width, m_BlendType,
3128d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                    dest_Bpp, clip_scan, src_extra_alpha);
3129d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        break;
3130d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      case 2 + 4:
3131d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      case 2 + 4 + 8:
3132d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_Argb2Rgb_NoBlend(dest_scan, src_scan, width, dest_Bpp,
3133d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                      clip_scan, src_extra_alpha);
3134d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        break;
3135d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      case 1 + 2:
3136d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_Rgb2Rgb_Blend_NoClip(dest_scan, src_scan, width,
3137d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                          m_BlendType, dest_Bpp, src_Bpp);
3138d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        break;
3139d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      case 1 + 2 + 8:
3140d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_Rgb2Rgb_Blend_Clip(dest_scan, src_scan, width, m_BlendType,
3141d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                        dest_Bpp, src_Bpp, clip_scan);
3142d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        break;
3143d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      case 1 + 2 + 4:
3144d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_Rgb2Rgb_NoBlend_NoClip(dest_scan, src_scan, width,
3145d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                            dest_Bpp, src_Bpp);
3146d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        break;
3147d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      case 1 + 2 + 4 + 8:
3148d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_Rgb2Rgb_NoBlend_Clip(dest_scan, src_scan, width, dest_Bpp,
3149d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                          src_Bpp, clip_scan);
3150d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        break;
3151d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
3152d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
3153d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
3154d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
3155d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CFX_ScanlineCompositor::CompositePalBitmapLine(
3156d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t* dest_scan,
3157d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    const uint8_t* src_scan,
3158d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int src_left,
3159d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    int width,
3160d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    const uint8_t* clip_scan,
3161d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    const uint8_t* src_extra_alpha,
3162d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    uint8_t* dst_extra_alpha) {
3163d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  if (m_bRgbByteOrder) {
3164d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (m_SrcFormat == FXDIB_1bppRgb) {
3165d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (m_DestFormat == FXDIB_8bppRgb) {
3166d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        return;
3167d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
3168d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (m_DestFormat == FXDIB_Argb) {
3169d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_1bppRgb2Argb_NoBlend_RgbByteOrder(
3170d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            dest_scan, src_scan, src_left, width, m_pSrcPalette.get(),
3171d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            clip_scan);
3172d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      } else {
3173d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_1bppRgb2Rgb_NoBlend_RgbByteOrder(
3174d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            dest_scan, src_scan, src_left, m_pSrcPalette.get(), width,
3175d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            (m_DestFormat & 0xff) >> 3, clip_scan);
3176d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
3177d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
3178d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (m_DestFormat == FXDIB_8bppRgb) {
3179d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        return;
3180d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
3181d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (m_DestFormat == FXDIB_Argb) {
3182d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_8bppRgb2Argb_NoBlend_RgbByteOrder(
3183d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            dest_scan, src_scan, width, m_pSrcPalette.get(), clip_scan);
3184d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      } else {
3185d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_8bppRgb2Rgb_NoBlend_RgbByteOrder(
3186d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            dest_scan, src_scan, m_pSrcPalette.get(), width,
3187d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            (m_DestFormat & 0xff) >> 3, clip_scan);
3188d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
3189d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
3190d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    return;
3191d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
3192d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  if (m_DestFormat == FXDIB_8bppMask) {
3193d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    CompositeRow_Rgb2Mask(dest_scan, src_scan, width, clip_scan);
3194d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    return;
3195d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
3196d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  if ((m_DestFormat & 0xff) == 8) {
3197d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (m_iTransparency & 8) {
3198d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (m_DestFormat & 0x0200) {
3199d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_1bppPal2Graya(
3200d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            dest_scan, src_scan, src_left,
3201d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            reinterpret_cast<const uint8_t*>(m_pSrcPalette.get()), width,
3202d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            m_BlendType, clip_scan, dst_extra_alpha);
3203d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      } else {
3204d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_1bppPal2Gray(
3205d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            dest_scan, src_scan, src_left,
3206d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            reinterpret_cast<const uint8_t*>(m_pSrcPalette.get()), width,
3207d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            m_BlendType, clip_scan);
3208d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      }
3209d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
3210d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      if (m_DestFormat & 0x0200)
3211d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_8bppPal2Graya(
3212d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            dest_scan, src_scan,
3213d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            reinterpret_cast<const uint8_t*>(m_pSrcPalette.get()), width,
3214d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            m_BlendType, clip_scan, dst_extra_alpha, src_extra_alpha);
3215d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      else
3216d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_8bppPal2Gray(
3217d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            dest_scan, src_scan,
3218d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            reinterpret_cast<const uint8_t*>(m_pSrcPalette.get()), width,
3219d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            m_BlendType, clip_scan, src_extra_alpha);
3220d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
3221d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  } else {
3222d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    switch (m_iTransparency) {
3223d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      case 1 + 2:
3224d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_8bppRgb2Argb_NoBlend(dest_scan, src_scan, width,
3225d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                          m_pSrcPalette.get(), clip_scan,
3226d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                          src_extra_alpha);
3227d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        break;
3228d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      case 1 + 2 + 8:
3229d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_1bppRgb2Argb_NoBlend(dest_scan, src_scan, src_left, width,
3230d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                          m_pSrcPalette.get(), clip_scan);
3231d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        break;
3232d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      case 0:
3233d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_8bppRgb2Rgb_NoBlend(
3234d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            dest_scan, src_scan, m_pSrcPalette.get(), width,
3235d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            (m_DestFormat & 0xff) >> 3, clip_scan, src_extra_alpha);
3236d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        break;
3237d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      case 0 + 8:
3238d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_1bppRgb2Rgb_NoBlend(dest_scan, src_scan, src_left,
3239d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                         m_pSrcPalette.get(), width,
3240d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                         (m_DestFormat & 0xff) >> 3, clip_scan);
3241d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        break;
3242d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      case 0 + 2:
3243d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_8bppRgb2Rgb_NoBlend(
3244d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            dest_scan, src_scan, m_pSrcPalette.get(), width,
3245d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann            (m_DestFormat & 0xff) >> 3, clip_scan, src_extra_alpha);
3246d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        break;
3247d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      case 0 + 2 + 8:
3248d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        CompositeRow_1bppRgb2Rgba_NoBlend(dest_scan, src_scan, src_left, width,
3249d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                          m_pSrcPalette.get(), clip_scan,
3250d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                          dst_extra_alpha);
3251d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        break;
3252d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        break;
3253d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
3254d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
3255d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
3256d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
3257d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CFX_ScanlineCompositor::CompositeByteMaskLine(uint8_t* dest_scan,
3258d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                   const uint8_t* src_scan,
3259d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                   int width,
3260d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                   const uint8_t* clip_scan,
3261d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                   uint8_t* dst_extra_alpha) {
3262d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  if (m_DestFormat == FXDIB_8bppMask) {
3263d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    CompositeRow_ByteMask2Mask(dest_scan, src_scan, m_MaskAlpha, width,
3264d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               clip_scan);
3265d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  } else if ((m_DestFormat & 0xff) == 8) {
3266d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (m_DestFormat & 0x0200) {
3267d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      CompositeRow_ByteMask2Graya(dest_scan, src_scan, m_MaskAlpha, m_MaskRed,
3268d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                  width, clip_scan, dst_extra_alpha);
3269d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
3270d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      CompositeRow_ByteMask2Gray(dest_scan, src_scan, m_MaskAlpha, m_MaskRed,
3271d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                 width, clip_scan);
3272d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
3273d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  } else if (m_bRgbByteOrder) {
3274d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (m_DestFormat == FXDIB_Argb) {
3275d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      CompositeRow_ByteMask2Argb_RgbByteOrder(
3276d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          dest_scan, src_scan, m_MaskAlpha, m_MaskRed, m_MaskGreen, m_MaskBlue,
3277d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          width, m_BlendType, clip_scan);
3278d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
3279d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      CompositeRow_ByteMask2Rgb_RgbByteOrder(
3280d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          dest_scan, src_scan, m_MaskAlpha, m_MaskRed, m_MaskGreen, m_MaskBlue,
3281d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          width, m_BlendType, (m_DestFormat & 0xff) >> 3, clip_scan);
3282d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
3283d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    return;
3284d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  } else if (m_DestFormat == FXDIB_Argb) {
3285d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    CompositeRow_ByteMask2Argb(dest_scan, src_scan, m_MaskAlpha, m_MaskRed,
3286d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               m_MaskGreen, m_MaskBlue, width, m_BlendType,
3287d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               clip_scan);
3288d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  } else if (m_DestFormat == FXDIB_Rgb || m_DestFormat == FXDIB_Rgb32) {
3289d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    CompositeRow_ByteMask2Rgb(dest_scan, src_scan, m_MaskAlpha, m_MaskRed,
3290d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                              m_MaskGreen, m_MaskBlue, width, m_BlendType,
3291d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                              (m_DestFormat & 0xff) >> 3, clip_scan);
3292d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  } else if (m_DestFormat == FXDIB_Rgba) {
3293d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    CompositeRow_ByteMask2Rgba(dest_scan, src_scan, m_MaskAlpha, m_MaskRed,
3294d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               m_MaskGreen, m_MaskBlue, width, m_BlendType,
3295d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                               clip_scan, dst_extra_alpha);
3296d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
3297d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
3298d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann
3299d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmannvoid CFX_ScanlineCompositor::CompositeBitMaskLine(uint8_t* dest_scan,
3300d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                  const uint8_t* src_scan,
3301d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                  int src_left,
3302d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                  int width,
3303d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                  const uint8_t* clip_scan,
3304d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                                  uint8_t* dst_extra_alpha) {
3305d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  if (m_DestFormat == FXDIB_8bppMask) {
3306d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    CompositeRow_BitMask2Mask(dest_scan, src_scan, m_MaskAlpha, src_left, width,
3307d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                              clip_scan);
3308d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  } else if ((m_DestFormat & 0xff) == 8) {
3309d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (m_DestFormat & 0x0200) {
3310d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      CompositeRow_BitMask2Graya(dest_scan, src_scan, m_MaskAlpha, m_MaskRed,
3311d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                 src_left, width, clip_scan, dst_extra_alpha);
3312d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
3313d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      CompositeRow_BitMask2Gray(dest_scan, src_scan, m_MaskAlpha, m_MaskRed,
3314d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                                src_left, width, clip_scan);
3315d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
3316d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  } else if (m_bRgbByteOrder) {
3317d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    if (m_DestFormat == FXDIB_Argb) {
3318d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      CompositeRow_BitMask2Argb_RgbByteOrder(
3319d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          dest_scan, src_scan, m_MaskAlpha, m_MaskRed, m_MaskGreen, m_MaskBlue,
3320d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          src_left, width, m_BlendType, clip_scan);
3321d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    } else {
3322d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann      CompositeRow_BitMask2Rgb_RgbByteOrder(
3323d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          dest_scan, src_scan, m_MaskAlpha, m_MaskRed, m_MaskGreen, m_MaskBlue,
3324d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann          src_left, width, m_BlendType, (m_DestFormat & 0xff) >> 3, clip_scan);
3325d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    }
3326d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    return;
3327d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  } else if (m_DestFormat == FXDIB_Argb) {
3328d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    CompositeRow_BitMask2Argb(dest_scan, src_scan, m_MaskAlpha, m_MaskRed,
3329d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                              m_MaskGreen, m_MaskBlue, src_left, width,
3330d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann                              m_BlendType, clip_scan);
3331d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  } else if (m_DestFormat == FXDIB_Rgb || m_DestFormat == FXDIB_Rgb32) {
3332d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann    CompositeRow_BitMask2Rgb(
3333d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        dest_scan, src_scan, m_MaskAlpha, m_MaskRed, m_MaskGreen, m_MaskBlue,
3334d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann        src_left, width, m_BlendType, (m_DestFormat & 0xff) >> 3, clip_scan);
3335d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann  }
3336d904c1ec7e8d1d86ed56f0dd252435d12cd345aePhilip P. Moltmann}
3337