00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028 #ifdef HAVE_CONFIG_H
00029 #include <config.h>
00030 #endif
00031 #include <gimp-print/gimp-print.h>
00032 #include "gimp-print-internal.h"
00033 #include <gimp-print/gimp-print-intl-internal.h>
00034 #include "dither-impl.h"
00035 #include "dither-inlined-functions.h"
00036
00037 static inline void
00038 print_color_very_fast(const stpi_dither_t *d, stpi_dither_channel_t *dc,
00039 int val, int x, int y, unsigned char bit,
00040 unsigned bits, int length)
00041 {
00042 int j;
00043 if (bits && val >= ditherpoint(d, &(dc->dithermat), x))
00044 {
00045 unsigned char *tptr = dc->ptr + d->ptr_offset;
00046
00047
00048
00049
00050 set_row_ends(dc, x);
00051 for (j = 1; j <= bits; j += j, tptr += length)
00052 {
00053 if (j & bits)
00054 tptr[0] |= bit;
00055 }
00056 }
00057 }
00058
00059 void
00060 stpi_dither_very_fast(stp_vars_t *v,
00061 int row,
00062 const unsigned short *raw,
00063 int duplicate_line,
00064 int zero_mask,
00065 const unsigned char *mask)
00066 {
00067 stpi_dither_t *d = (stpi_dither_t *) stp_get_component_data(v, "Dither");
00068 int x,
00069 length;
00070 unsigned char *bit_patterns;
00071 unsigned char bit;
00072 int i;
00073 int one_bit_only = 1;
00074
00075 int xerror, xstep, xmod;
00076
00077 if ((zero_mask & ((1 << CHANNEL_COUNT(d)) - 1)) ==
00078 ((1 << CHANNEL_COUNT(d)) - 1))
00079 return;
00080
00081 length = (d->dst_width + 7) / 8;
00082
00083 bit = 128;
00084 xstep = CHANNEL_COUNT(d) * (d->src_width / d->dst_width);
00085 xmod = d->src_width % d->dst_width;
00086 xerror = 0;
00087
00088 bit_patterns = stp_zalloc(sizeof(unsigned char) * CHANNEL_COUNT(d));
00089 for (i = 0; i < CHANNEL_COUNT(d); i++)
00090 {
00091 stpi_dither_channel_t *dc = &(CHANNEL(d, i));
00092 if (dc->nlevels > 0)
00093 bit_patterns[i] = dc->ranges[dc->nlevels - 1].upper->bits;
00094 if (bit_patterns[i] != 1)
00095 one_bit_only = 0;
00096 }
00097 if (one_bit_only)
00098 {
00099 for (x = 0; x < d->dst_width; x ++)
00100 {
00101 if (!mask || (*(mask + d->ptr_offset) & bit))
00102 {
00103 for (i = 0; i < CHANNEL_COUNT(d); i++)
00104 {
00105 if (raw[i] &&
00106 raw[i] >= ditherpoint(d, &(CHANNEL(d, i).dithermat), x))
00107 {
00108 set_row_ends(&(CHANNEL(d, i)), x);
00109 CHANNEL(d, i).ptr[d->ptr_offset] |= bit;
00110 }
00111 }
00112 }
00113 ADVANCE_UNIDIRECTIONAL(d, bit, raw, CHANNEL_COUNT(d),
00114 xerror, xstep, xmod);
00115 }
00116 }
00117 else
00118 {
00119 for (x = 0; x < d->dst_width; x ++)
00120 {
00121 if (!mask || (*(mask + d->ptr_offset) & bit))
00122 {
00123 for (i = 0; i < CHANNEL_COUNT(d); i++)
00124 {
00125 if (CHANNEL(d, i).ptr && raw[i])
00126 print_color_very_fast(d, &(CHANNEL(d, i)), raw[i], x, row,
00127 bit, bit_patterns[i], length);
00128 }
00129 }
00130 ADVANCE_UNIDIRECTIONAL(d, bit, raw, CHANNEL_COUNT(d),
00131 xerror, xstep, xmod);
00132 }
00133 }
00134 stp_free(bit_patterns);
00135 }