/////////////////////////////////////////////////////////////////
// rasterop.cpp
#include <string.h>
#include "rasterop.h"
static unsigned long lbits[32] =
{
0xFFFFFFFF, 0xFFFFFF7F, 0xFFFFFF3F, 0xFFFFFF1F,
0xFFFFFF0F, 0xFFFFFF07, 0xFFFFFF03, 0xFFFFFF01,
0xFFFFFF00, 0xFFFF7F00, 0xFFFF3F00, 0xFFFF1F00,
0xFFFF0F00, 0xFFFF0700, 0xFFFF0300, 0xFFFF0100,
0xFFFF0000, 0xFF7F0000, 0xFF3F0000, 0xFF1F0000,
0xFF0F0000, 0xFF070000, 0xFF030000, 0xFF010000,
0xFF000000, 0x7F000000, 0x3F000000, 0x1F000000,
0x0F000000, 0x07000000, 0x03000000, 0x01000000
};
static unsigned long rbits[32] =
{
0xFFFFFFFF, 0xFEFFFFFF, 0xFCFFFFFF, 0xF8FFFFFF,
0xF0FFFFFF, 0xE0FFFFFF, 0xC0FFFFFF, 0x80FFFFFF,
0x00FFFFFF, 0x00FEFFFF, 0x00FCFFFF, 0x00F8FFFF,
0x00F0FFFF, 0x00E0FFFF, 0x00C0FFFF, 0x0080FFFF,
0x0000FFFF, 0x0000FEFF, 0x0000FCFF, 0x0000F8FF,
0x0000F0FF, 0x0000E0FF, 0x0000C0FF, 0x000080FF,
0x000000FF, 0x000000FE, 0x000000FC, 0x000000F8,
0x000000F0, 0x000000E0, 0x000000C0, 0x00000080
};
int bit_set( unsigned char bits[3300][300], int x1, int y1, int x2, int y2 )
{
#if 0
// make p1 top-left, p2 bottom right
if( x1 > x2 )
swap(int, x1, x2);
if( y1 > y2 )
swap(int, y1, y2);
#endif
int li = x1 / 32; // index of leftmost long
int lj = x1 % 32; // bit index of leftmost long
int ri = x2 / 32; // index of rightmost long
int rj = x2 % 32; // bit index of rightmost long
unsigned long lmask, rmask;
int n = ri - li + 1; // number of affected long words
// calculate number of wholly affecte long words (n)
// and left and right masks
if( lj ) // leftmost partialy affected
{
lmask = lbits[lj];
n--;
}
if( rj != 31 ) // rightmost partialy affected
{
rmask = rbits[31-rj];
n--;
}
if( n < 0 )
{ // single long word masked on both sides
lmask &= rmask;
}
unsigned long (*longbits)[75];
longbits = (unsigned long(*)[75])bits;
int v = y1;
for( int y = y1; y <= y2; y++, v++ )
{
int i = li;
if( lj )
longbits[v][i++] |= lmask;
for( int c = 0; c < n; c++ )
longbits[v][i++] |= 0xFFFFFFFF;
if( rj != 31 && n >= 0 )
longbits[v][i] |= rmask;
}
return 0;
}
int bit_blt( unsigned char d[3300][300], int x, int y, unsigned char *s, int w, int h )
{
int j = x % 8, v = y;
x = x / 8;
w = (w + 7) / 8;
while( h-- > 0 )
{
if( v >= 0 && v < 3300 )
{
int i = x;
for( int k = w; k; k--, s++ )
{
if( i >= 0 && i < 300 )
{
if( j )
{
d[v][i++] |= *s >> j;
if( i < 300 )
d[v][i] |= *s << (8-j);
}
else
d[v][i++] |= *s;
}
else
i++;
}
}
else
s += w;
v++;
}
return 0;
}
int bit_neg( unsigned char *d, int n )
{
unsigned long *p = (unsigned long *)d;
for( int i = n/4; i--; p++ )
*p = ~*p;
d = (unsigned char *)p;
for( n = n%4; n--; d++ )
*d = ~*d;
return 0;
}
int bit_res( unsigned char *d, int w1, int h1, int w2, int h2 )
{
int sx = (w1 + w2 - 1)/w2;
int sy = (h1 + h2 - 1)/h2;
int bpl = (w1+7)/8;
if( sy > 1 )
{
unsigned char *p = d;
unsigned char *q = p;
unsigned char *r0 = new unsigned char[bpl];
unsigned char *r = r0;
memset( r0, 0, bpl );
int j = 0;
for( int y = 0; y < h1; y++ )
{
for( int i = 0; i < bpl; i++ )
{
unsigned char data = *p;
if( !j )
*q = *r;
for( unsigned char mask = 0x80; mask; mask = mask >> 1 )
{
if( *r & mask )
{
if( !(data & mask) )
*q &= ~mask;
}
else
{
if( data & mask )
*q |= mask;
}
}
p++;
q++;
r++;
}
j++;
if( j == sy )
{
j = 0;
r = q - bpl;
}
else
{
q -= bpl;
r -= bpl;
}
}
delete r0;
}
if( sx > 1 )
{
for( int y = 0; y < h1; y++ )
{
unsigned char smask = 0x80;
unsigned char dmask = 0x80;
unsigned char *p = d + y * bpl;
unsigned char *q = p;
int j = sx;
unsigned char ddata = 0;
unsigned char sdata = *p++;
unsigned char f = 0;
for( int x = 0; x < w1; x++ )
{
if( f )
{
if( !(sdata & smask) )
ddata &= ~dmask;
}
else
{
if( sdata & smask )
ddata |= dmask;
}
smask = smask >> 1;
if( !smask )
{
sdata = *p++;
smask = 0x80;
}
if( !--j )
{
f = ddata & dmask;
dmask = dmask >> 1;
if( !dmask )
{
dmask = 0x80;
*q++ = ddata;
ddata = 0;
}
if( f )
ddata |= dmask;
j = sx;
}
}
}
}
return 0;
}