all repos — fluxbox @ da452116d38cc8854914e90d384042f703742d52

custom fork of the fluxbox windowmanager

changed name to ImageControl
fluxgen fluxgen
commit

da452116d38cc8854914e90d384042f703742d52

parent

7efd955b432332c74e765e5eb4ee6fc7e165001d

2 files changed, 0 insertions(+), 2559 deletions(-)

jump to
D src/Image.cc

@@ -1,2372 +0,0 @@

-// Image.cc for Fluxbox Window Manager -// Copyright (c) 2001 - 2002 Henrik Kinnunen (fluxbox@linuxmail.org) -// -// Image.cc for Blackbox - an X11 Window manager -// Copyright (c) 1997 - 2000 Brad Hughes (bhughes@tcac.net) -// -// Permission is hereby granted, free of charge, to any person obtaining a -// copy of this software and associated documentation files (the "Software"), -// to deal in the Software without restriction, including without limitation -// the rights to use, copy, modify, merge, publish, distribute, sublicense, -// and/or sell copies of the Software, and to permit persons to whom the -// Software is furnished to do so, subject to the following conditions: -// -// The above copyright notice and this permission notice shall be included in -// all copies or substantial portions of the Software. -// -// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR -// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, -// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL -// THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER -// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING -// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER -// DEALINGS IN THE SOFTWARE. - -// $Id: Image.cc,v 1.19 2002/11/27 22:04:02 fluxgen Exp $ - -#include "Image.hh" - -//use GNU extensions -#ifndef _GNU_SOURCE -#define _GNU_SOURCE -#endif // _GNU_SOURCE - -#ifdef HAVE_CONFIG_H -#include "config.h" -#endif // HAVE_CONFIG_H - -#include "i18n.hh" -#include "BaseDisplay.hh" - -#ifdef HAVE_SYS_TYPES_H -#include <sys/types.h> -#endif // HAVE_SYS_TYPES_H - -#include <cstdlib> -#include <cstring> -#include <cstdio> - -#ifdef HAVE_CTYPE_H -#include <ctype.h> -#endif // HAVE_CTYPE_H - -#include <iostream> - -using namespace std; - -// lookup table for texture -unsigned long *BImageControl::sqrt_table = 0; - -namespace { // anonymous - -unsigned long bsqrt(unsigned long x) { - if (x <= 0) return 0; - if (x == 1) return 1; - - unsigned long r = x >> 1; - unsigned long q; - - while (1) { - q = x / r; - if (q >= r) return r; - r = (r + q) >> 1; - } -} - -}; - -BImage::BImage(BImageControl *c, unsigned int w, unsigned int h) { - control = c; - - width = ((signed) w > 0) ? w : 1; - height = ((signed) h > 0) ? h : 1; - - red = new unsigned char[width * height]; - green = new unsigned char[width * height]; - blue = new unsigned char[width * height]; - - xtable = ytable = (unsigned int *) 0; - - cpc = control->colorsPerChannel(); - cpccpc = cpc * cpc; - - control->colorTables(&red_table, &green_table, &blue_table, - &red_offset, &green_offset, &blue_offset, - &red_bits, &green_bits, &blue_bits); - - if (control->visual()->c_class != TrueColor) - control->getXColorTable(&colors, &ncolors); -} - - -BImage::~BImage() { - if (red) delete [] red; - if (green) delete [] green; - if (blue) delete [] blue; -} - - -Pixmap BImage::render(const FbTk::Texture &texture) { - - if (texture.type() & FbTk::Texture::PARENTRELATIVE) - return ParentRelative; - else if (texture.type() & FbTk::Texture::SOLID) - return renderSolid(texture); - else if (texture.type() & FbTk::Texture::GRADIENT) - return renderGradient(texture); - - return None; -} - - -Pixmap BImage::renderSolid(const FbTk::Texture &texture) { - - Display *disp = BaseDisplay::instance()->getXDisplay(); - - Pixmap pixmap = XCreatePixmap(disp, - control->drawable(), width, - height, control->depth()); - if (pixmap == None) { - fprintf(stderr, - I18n::instance()->getMessage( - FBNLS::ImageSet, FBNLS::ImageErrorCreatingSolidPixmap, - "BImage::render_solid: error creating pixmap\n")); - return None; - } - - XGCValues gcv; - GC gc, hgc, lgc; - - gcv.foreground = texture.color().pixel(); - gcv.fill_style = FillSolid; - gc = XCreateGC(disp, pixmap, - GCForeground | GCFillStyle, &gcv); - - gcv.foreground = texture.hiColor().pixel(); - hgc = XCreateGC(disp, pixmap, - GCForeground, &gcv); - - gcv.foreground = texture.loColor().pixel(); - lgc = XCreateGC(disp, pixmap, - GCForeground, &gcv); - - XFillRectangle(disp, pixmap, gc, 0, 0, width, height); - - using namespace FbTk; - - if (texture.type() & Texture::INTERLACED) { - gcv.foreground = texture.colorTo().pixel(); - GC igc = XCreateGC(disp, pixmap, - GCForeground, &gcv); - - register unsigned int i = 0; - for (; i < height; i += 2) - XDrawLine(disp, pixmap, igc, 0, i, width, i); - - XFreeGC(disp, igc); - } - - if (texture.type() & Texture::BEVEL1) { - if (texture.type() & Texture::RAISED) { - XDrawLine(disp, pixmap, lgc, - 0, height - 1, width - 1, height - 1); - XDrawLine(disp, pixmap, lgc, - width - 1, height - 1, width - 1, 0); - - XDrawLine(disp, pixmap, hgc, - 0, 0, width - 1, 0); - XDrawLine(disp, pixmap, hgc, - 0, height - 1, 0, 0); - } else if (texture.type() & Texture::SUNKEN) { - XDrawLine(disp, pixmap, hgc, - 0, height - 1, width - 1, height - 1); - XDrawLine(disp, pixmap, hgc, - width - 1, height - 1, width - 1, 0); - - XDrawLine(disp, pixmap, lgc, - 0, 0, width - 1, 0); - XDrawLine(disp, pixmap, lgc, - 0, height - 1, 0, 0); - } - } else if (texture.type() & Texture::BEVEL2) { - if (texture.type() & Texture::RAISED) { - XDrawLine(disp, pixmap, lgc, - 1, height - 3, width - 3, height - 3); - XDrawLine(disp, pixmap, lgc, - width - 3, height - 3, width - 3, 1); - - XDrawLine(disp, pixmap, hgc, - 1, 1, width - 3, 1); - XDrawLine(disp, pixmap, hgc, - 1, height - 3, 1, 1); - } else if (texture.type() & Texture::SUNKEN) { - XDrawLine(disp, pixmap, hgc, - 1, height - 3, width - 3, height - 3); - XDrawLine(disp, pixmap, hgc, - width - 3, height - 3, width - 3, 1); - - XDrawLine(disp, pixmap, lgc, - 1, 1, width - 3, 1); - XDrawLine(disp, pixmap, lgc, - 1, height - 3, 1, 1); - } - } - - XFreeGC(disp, gc); - XFreeGC(disp, hgc); - XFreeGC(disp, lgc); - - return pixmap; -} - - -Pixmap BImage::renderGradient(const FbTk::Texture &texture) { - - bool inverted = false; - - using namespace FbTk; - - interlaced = texture.type() & Texture::INTERLACED; - - if (texture.type() & Texture::SUNKEN) { - from = &(texture.colorTo()); - to = &(texture.color()); - - if (! (texture.type() & Texture::INVERT)) - inverted = true; - } else { - from = &(texture.color()); - to = &(texture.colorTo()); - - if (texture.type() & Texture::INVERT) - inverted = true; - } - - control->getGradientBuffers(width, height, &xtable, &ytable); - - if (texture.type() & Texture::DIAGONAL) - dgradient(); - else if (texture.type() & Texture::ELLIPTIC) - egradient(); - else if (texture.type() & Texture::HORIZONTAL) - hgradient(); - else if (texture.type() & Texture::PYRAMID) - pgradient(); - else if (texture.type() & Texture::RECTANGLE) - rgradient(); - else if (texture.type() & Texture::VERTICAL) - vgradient(); - else if (texture.type() & Texture::CROSSDIAGONAL) - cdgradient(); - else if (texture.type() & Texture::PIPECROSS) - pcgradient(); - - if (texture.type() & Texture::BEVEL1) - bevel1(); - else if (texture.type() & Texture::BEVEL2) - bevel2(); - - if (inverted) - invert(); - - return renderPixmap(); - -} - - -XImage *BImage::renderXImage() { - I18n *i18n = I18n::instance(); - XImage *image = - XCreateImage(BaseDisplay::getXDisplay(), - control->visual(), control->depth(), ZPixmap, 0, 0, - width, height, 32, 0); - - if (! image) { - fprintf(stderr, - i18n-> - getMessage( - FBNLS::ImageSet, FBNLS::ImageErrorCreatingXImage, - "BImage::renderXImage: error creating XImage\n")); - return (XImage *) 0; - } - - // insurance policy - image->data = (char *) 0; - - unsigned char *d = new unsigned char[image->bytes_per_line * (height + 1)]; - register unsigned int x, y, dithx, dithy, r, g, b, o, er, eg, eb, offset; - - unsigned char *pixel_data = d, *ppixel_data = d; - unsigned long pixel; - - o = image->bits_per_pixel + ((image->byte_order == MSBFirst) ? 1 : 0); - - if (control->doDither() && width > 1 && height > 1) { - unsigned char dither4[4][4] = { - {0, 4, 1, 5}, - {6, 2, 7, 3}, - {1, 5, 0, 4}, - {7, 3, 6, 2} }; - -#ifdef ORDEREDPSEUDO - unsigned char dither8[8][8] = { - { 0, 32, 8, 40, 2, 34, 10, 42 }, - { 48, 16, 56, 24, 50, 18, 58, 26 }, - { 12, 44, 4, 36, 14, 46, 6, 38 }, - { 60, 28, 52, 20, 62, 30, 54, 22 }, - { 3, 35, 11, 43, 1, 33, 9, 41 }, - { 51, 19, 59, 27, 49, 17, 57, 25 }, - { 15, 47, 7, 39, 13, 45, 5, 37 }, - { 63, 31, 55, 23, 61, 29, 53, 21 } }; -#endif // ORDEREDPSEUDO - - switch (control->visual()->c_class) { - case TrueColor: - // algorithm: ordered dithering... many many thanks to rasterman - // (raster@rasterman.com) for telling me about this... portions of this - // code is based off of his code in Imlib - for (y = 0, offset = 0; y < height; y++) { - dithy = y & 0x3; - - for (x = 0; x < width; x++, offset++) { - dithx = x & 0x3; - r = red[offset]; - g = green[offset]; - b = blue[offset]; - - er = r & (red_bits - 1); - eg = g & (green_bits - 1); - eb = b & (blue_bits - 1); - - r = red_table[r]; - g = green_table[g]; - b = blue_table[b]; - - if ((dither4[dithy][dithx] < er) && (r < red_table[255])) r++; - if ((dither4[dithy][dithx] < eg) && (g < green_table[255])) g++; - if ((dither4[dithy][dithx] < eb) && (b < blue_table[255])) b++; - - pixel = (r << red_offset) | (g << green_offset) | (b << blue_offset); - - switch (o) { - case 8: // 8bpp - *pixel_data++ = pixel; - break; - - case 16: // 16bpp LSB - *pixel_data++ = pixel; - *pixel_data++ = pixel >> 8; - break; - - case 17: // 16bpp MSB - *pixel_data++ = pixel >> 8; - *pixel_data++ = pixel; - break; - - case 24: // 24bpp LSB - *pixel_data++ = pixel; - *pixel_data++ = pixel >> 8; - *pixel_data++ = pixel >> 16; - break; - - case 25: // 24bpp MSB - *pixel_data++ = pixel >> 16; - *pixel_data++ = pixel >> 8; - *pixel_data++ = pixel; - break; - - case 32: // 32bpp LSB - *pixel_data++ = pixel; - *pixel_data++ = pixel >> 8; - *pixel_data++ = pixel >> 16; - *pixel_data++ = pixel >> 24; - break; - - case 33: // 32bpp MSB - *pixel_data++ = pixel >> 24; - *pixel_data++ = pixel >> 16; - *pixel_data++ = pixel >> 8; - *pixel_data++ = pixel; - break; - } - } - - pixel_data = (ppixel_data += image->bytes_per_line); - } - - break; - - case StaticColor: - case PseudoColor: { -#ifndef ORDEREDPSEUDO - short *terr, - *rerr = new short[width + 2], - *gerr = new short[width + 2], - *berr = new short[width + 2], - *nrerr = new short[width + 2], - *ngerr = new short[width + 2], - *nberr = new short[width + 2]; - int rr, gg, bb, rer, ger, ber; - int dd = 255 / control->colorsPerChannel(); - - for (x = 0; x < width; x++) { - *(rerr + x) = *(red + x); - *(gerr + x) = *(green + x); - *(berr + x) = *(blue + x); - } - - *(rerr + x) = *(gerr + x) = *(berr + x) = 0; -#endif // ORDEREDPSEUDO - - for (y = 0, offset = 0; y < height; y++) { -#ifdef ORDEREDPSEUDO - dithy = y & 7; - - for (x = 0; x < width; x++, offset++) { - dithx = x & 7; - - r = red[offset]; - g = green[offset]; - b = blue[offset]; - - er = r & (red_bits - 1); - eg = g & (green_bits - 1); - eb = b & (blue_bits - 1); - - r = red_table[r]; - g = green_table[g]; - b = blue_table[b]; - - if ((dither8[dithy][dithx] < er) && (r < red_table[255])) r++; - if ((dither8[dithy][dithx] < eg) && (g < green_table[255])) g++; - if ((dither8[dithy][dithx] < eb) && (b < blue_table[255])) b++; - - pixel = (r * cpccpc) + (g * cpc) + b; - *(pixel_data++) = colors[pixel].pixel; - } - - pixel_data = (ppixel_data += image->bytes_per_line); - } -#else // !ORDEREDPSEUDO - if (y < (height - 1)) { - int i = offset + width; - for (x = 0; x < width; x++, i++) { - *(nrerr + x) = *(red + i); - *(ngerr + x) = *(green + i); - *(nberr + x) = *(blue + i); - } - - *(nrerr + x) = *(red + (--i)); - *(ngerr + x) = *(green + i); - *(nberr + x) = *(blue + i); - } - - for (x = 0; x < width; x++) { - rr = rerr[x]; - gg = gerr[x]; - bb = berr[x]; - - if (rr > 255) rr = 255; else if (rr < 0) rr = 0; - if (gg > 255) gg = 255; else if (gg < 0) gg = 0; - if (bb > 255) bb = 255; else if (bb < 0) bb = 0; - - r = red_table[rr]; - g = green_table[gg]; - b = blue_table[bb]; - - rer = rerr[x] - r*dd; - ger = gerr[x] - g*dd; - ber = berr[x] - b*dd; - - pixel = (r * cpccpc) + (g * cpc) + b; - *pixel_data++ = colors[pixel].pixel; - - r = rer >> 1; - g = ger >> 1; - b = ber >> 1; - rerr[x+1] += r; - gerr[x+1] += g; - berr[x+1] += b; - nrerr[x] += r; - ngerr[x] += g; - nberr[x] += b; - } - - offset += width; - - pixel_data = (ppixel_data += image->bytes_per_line); - - terr = rerr; - rerr = nrerr; - nrerr = terr; - - terr = gerr; - gerr = ngerr; - ngerr = terr; - - terr = berr; - berr = nberr; - nberr = terr; - } - - delete [] rerr; - delete [] gerr; - delete [] berr; - delete [] nrerr; - delete [] ngerr; - delete [] nberr; -#endif // ORDEREDPSUEDO - - } break; - - /* - case StaticGray: - case GrayScale: - for (y = 0, offset = 0; y < height; y++) { - dithy = y & 0x3; - - for (x = 0; x < width; x++, offset++) { - dithx = x & 0x3; - - r = *(red + offset); - g = *(green + offset); - b = *(blue + offset); - - er = r & 0x7; - eg = g & 0x7; - eb = b & 0x7; - - if ((dither[dithy][dithx] < er) && (r < (256 - 8))) - r += 8; - if ((dither[dithy][dithx] < (eg << 1)) && (g < (256 - 4))) - g += 4; - if ((dither[dithy][dithx] < eb) && (b < (256 - 8))) - b += 8; - - r = *(red_table + r); - g = *(green_table + g); - b = *(blue_table + b); - - g = ((r * 30) + (g * 59) + (b * 11)) / 100; - *pixel_data++ = colors[g].pixel; - } - - pixel_data = (ppixel_data += image->bytes_per_line); - } - - break; - */ - - default: - fprintf(stderr, - i18n-> - getMessage( - FBNLS::ImageSet, FBNLS::ImageUnsupVisual, - "BImage::renderXImage: unsupported visual\n")); - delete [] d; - XDestroyImage(image); - return (XImage *) 0; - } - } else { - switch (control->visual()->c_class) { - case StaticColor: - case PseudoColor: - for (y = 0, offset = 0; y < height; y++) { - for (x = 0; x < width; x++, offset++) { - r = red_table[red[offset]]; - g = green_table[green[offset]]; - b = blue_table[blue[offset]]; - - pixel = (r * cpccpc) + (g * cpc) + b; - *pixel_data++ = colors[pixel].pixel; - } - - pixel_data = (ppixel_data += image->bytes_per_line); - } - - break; - - case TrueColor: - for (y = 0, offset = 0; y < height; y++) { - for (x = 0; x < width; x++, offset++) { - r = red_table[red[offset]]; - g = green_table[green[offset]]; - b = blue_table[blue[offset]]; - - pixel = (r << red_offset) | (g << green_offset) | (b << blue_offset); - - switch (o) { - case 8: // 8bpp - *pixel_data++ = pixel; - break; - - case 16: // 16bpp LSB - *pixel_data++ = pixel; - *pixel_data++ = pixel >> 8; - break; - - case 17: // 16bpp MSB - *pixel_data++ = pixel >> 8; - *pixel_data++ = pixel; - break; - - case 24: // 24bpp LSB - *pixel_data++ = pixel; - *pixel_data++ = pixel >> 8; - *pixel_data++ = pixel >> 16; - break; - - case 25: // 24bpp MSB - *pixel_data++ = pixel >> 16; - *pixel_data++ = pixel >> 8; - *pixel_data++ = pixel; - break; - - case 32: // 32bpp LSB - *pixel_data++ = pixel; - *pixel_data++ = pixel >> 8; - *pixel_data++ = pixel >> 16; - *pixel_data++ = pixel >> 24; - break; - - case 33: // 32bpp MSB - *pixel_data++ = pixel >> 24; - *pixel_data++ = pixel >> 16; - *pixel_data++ = pixel >> 8; - *pixel_data++ = pixel; - break; - } - } - - pixel_data = (ppixel_data += image->bytes_per_line); - } - - break; - - case StaticGray: - case GrayScale: - for (y = 0, offset = 0; y < height; y++) { - for (x = 0; x < width; x++, offset++) { - r = *(red_table + *(red + offset)); - g = *(green_table + *(green + offset)); - b = *(blue_table + *(blue + offset)); - - g = ((r * 30) + (g * 59) + (b * 11)) / 100; - *pixel_data++ = colors[g].pixel; - } - - pixel_data = (ppixel_data += image->bytes_per_line); - } - - break; - - default: - fprintf(stderr, - i18n-> - getMessage( - FBNLS::ImageSet, FBNLS::ImageUnsupVisual, - "BImage::renderXImage: unsupported visual\n")); - delete [] d; - XDestroyImage(image); - return (XImage *) 0; - } -} - - image->data = (char *) d; - return image; -} - - -Pixmap BImage::renderPixmap() { - Display *disp = BaseDisplay::getXDisplay(); - I18n *i18n = I18n::instance(); - Pixmap pixmap = - XCreatePixmap(disp, - control->drawable(), width, height, control->depth()); - - if (pixmap == None) { - fprintf(stderr, - i18n->getMessage( - FBNLS::ImageSet, FBNLS::ImageErrorCreatingPixmap, - "BImage::renderPixmap: error creating pixmap\n")); - return None; - } - - XImage *image = renderXImage(); - - if (! image) { - XFreePixmap(disp, pixmap); - return None; - } else if (! image->data) { - XDestroyImage(image); - XFreePixmap(disp, pixmap); - return None; - } - - XPutImage(disp, pixmap, - DefaultGC(disp, - control->getScreenInfo()->getScreenNumber()), - image, 0, 0, 0, 0, width, height); - - if (image->data) { - delete [] image->data; - image->data = NULL; - } - - XDestroyImage(image); - - return pixmap; -} - - -void BImage::bevel1() { - if (width > 2 && height > 2) { - unsigned char *pr = red, *pg = green, *pb = blue; - - register unsigned char r, g, b, rr ,gg ,bb; - register unsigned int w = width, h = height - 1, wh = w * h; - - while (--w) { - r = *pr; - rr = r + (r >> 1); - if (rr < r) rr = ~0; - g = *pg; - gg = g + (g >> 1); - if (gg < g) gg = ~0; - b = *pb; - bb = b + (b >> 1); - if (bb < b) bb = ~0; - - *pr = rr; - *pg = gg; - *pb = bb; - - r = *(pr + wh); - rr = (r >> 2) + (r >> 1); - if (rr > r) rr = 0; - g = *(pg + wh); - gg = (g >> 2) + (g >> 1); - if (gg > g) gg = 0; - b = *(pb + wh); - bb = (b >> 2) + (b >> 1); - if (bb > b) bb = 0; - - *((pr++) + wh) = rr; - *((pg++) + wh) = gg; - *((pb++) + wh) = bb; - } - - r = *pr; - rr = r + (r >> 1); - if (rr < r) rr = ~0; - g = *pg; - gg = g + (g >> 1); - if (gg < g) gg = ~0; - b = *pb; - bb = b + (b >> 1); - if (bb < b) bb = ~0; - - *pr = rr; - *pg = gg; - *pb = bb; - - r = *(pr + wh); - rr = (r >> 2) + (r >> 1); - if (rr > r) rr = 0; - g = *(pg + wh); - gg = (g >> 2) + (g >> 1); - if (gg > g) gg = 0; - b = *(pb + wh); - bb = (b >> 2) + (b >> 1); - if (bb > b) bb = 0; - - *(pr + wh) = rr; - *(pg + wh) = gg; - *(pb + wh) = bb; - - pr = red + width; - pg = green + width; - pb = blue + width; - - while (--h) { - r = *pr; - rr = r + (r >> 1); - if (rr < r) rr = ~0; - g = *pg; - gg = g + (g >> 1); - if (gg < g) gg = ~0; - b = *pb; - bb = b + (b >> 1); - if (bb < b) bb = ~0; - - *pr = rr; - *pg = gg; - *pb = bb; - - pr += width - 1; - pg += width - 1; - pb += width - 1; - - r = *pr; - rr = (r >> 2) + (r >> 1); - if (rr > r) rr = 0; - g = *pg; - gg = (g >> 2) + (g >> 1); - if (gg > g) gg = 0; - b = *pb; - bb = (b >> 2) + (b >> 1); - if (bb > b) bb = 0; - - *(pr++) = rr; - *(pg++) = gg; - *(pb++) = bb; - } - - r = *pr; - rr = r + (r >> 1); - if (rr < r) rr = ~0; - g = *pg; - gg = g + (g >> 1); - if (gg < g) gg = ~0; - b = *pb; - bb = b + (b >> 1); - if (bb < b) bb = ~0; - - *pr = rr; - *pg = gg; - *pb = bb; - - pr += width - 1; - pg += width - 1; - pb += width - 1; - - r = *pr; - rr = (r >> 2) + (r >> 1); - if (rr > r) rr = 0; - g = *pg; - gg = (g >> 2) + (g >> 1); - if (gg > g) gg = 0; - b = *pb; - bb = (b >> 2) + (b >> 1); - if (bb > b) bb = 0; - - *pr = rr; - *pg = gg; - *pb = bb; - } -} - - -void BImage::bevel2() { - if (width > 4 && height > 4) { - unsigned char r, g, b, rr ,gg ,bb, *pr = red + width + 1, - *pg = green + width + 1, *pb = blue + width + 1; - unsigned int w = width - 2, h = height - 1, wh = width * (height - 3); - - while (--w) { - r = *pr; - rr = r + (r >> 1); - if (rr < r) rr = ~0; - g = *pg; - gg = g + (g >> 1); - if (gg < g) gg = ~0; - b = *pb; - bb = b + (b >> 1); - if (bb < b) bb = ~0; - - *pr = rr; - *pg = gg; - *pb = bb; - - r = *(pr + wh); - rr = (r >> 2) + (r >> 1); - if (rr > r) rr = 0; - g = *(pg + wh); - gg = (g >> 2) + (g >> 1); - if (gg > g) gg = 0; - b = *(pb + wh); - bb = (b >> 2) + (b >> 1); - if (bb > b) bb = 0; - - *((pr++) + wh) = rr; - *((pg++) + wh) = gg; - *((pb++) + wh) = bb; - } - - pr = red + width; - pg = green + width; - pb = blue + width; - - while (--h) { - r = *pr; - rr = r + (r >> 1); - if (rr < r) rr = ~0; - g = *pg; - gg = g + (g >> 1); - if (gg < g) gg = ~0; - b = *pb; - bb = b + (b >> 1); - if (bb < b) bb = ~0; - - *(++pr) = rr; - *(++pg) = gg; - *(++pb) = bb; - - pr += width - 3; - pg += width - 3; - pb += width - 3; - - r = *pr; - rr = (r >> 2) + (r >> 1); - if (rr > r) rr = 0; - g = *pg; - gg = (g >> 2) + (g >> 1); - if (gg > g) gg = 0; - b = *pb; - bb = (b >> 2) + (b >> 1); - if (bb > b) bb = 0; - - *(pr++) = rr; - *(pg++) = gg; - *(pb++) = bb; - - pr++; pg++; pb++; - } - } -} - - -void BImage::invert() { - register unsigned int i, j, wh = (width * height) - 1; - unsigned char tmp; - - for (i = 0, j = wh; j > i; j--, i++) { - tmp = *(red + j); - *(red + j) = *(red + i); - *(red + i) = tmp; - - tmp = *(green + j); - *(green + j) = *(green + i); - *(green + i) = tmp; - - tmp = *(blue + j); - *(blue + j) = *(blue + i); - *(blue + i) = tmp; - } -} - - -void BImage::dgradient() { - // diagonal gradient code was written by Mike Cole <mike@mydot.com> - // modified for interlacing by Brad Hughes - - float drx, dgx, dbx, dry, dgy, dby, yr = 0.0, yg = 0.0, yb = 0.0, - xr = (float) from->red(), - xg = (float) from->green(), - xb = (float) from->blue(); - unsigned char *pr = red, *pg = green, *pb = blue; - unsigned int w = width * 2, h = height * 2, *xt = xtable, *yt = ytable; - - register unsigned int x, y; - - dry = drx = (float) (to->red() - from->red()); - dgy = dgx = (float) (to->green() - from->green()); - dby = dbx = (float) (to->blue() - from->blue()); - - // Create X table - drx /= w; - dgx /= w; - dbx /= w; - - for (x = 0; x < width; x++) { - *(xt++) = (unsigned char) (xr); - *(xt++) = (unsigned char) (xg); - *(xt++) = (unsigned char) (xb); - - xr += drx; - xg += dgx; - xb += dbx; - } - - // Create Y table - dry /= h; - dgy /= h; - dby /= h; - - for (y = 0; y < height; y++) { - *(yt++) = ((unsigned char) yr); - *(yt++) = ((unsigned char) yg); - *(yt++) = ((unsigned char) yb); - - yr += dry; - yg += dgy; - yb += dby; - } - - // Combine tables to create gradient - - - if (! interlaced) { - - - // normal dgradient - for (yt = ytable, y = 0; y < height; y++, yt += 3) { - for (xt = xtable, x = 0; x < width; x++) { - *(pr++) = *(xt++) + *(yt); - *(pg++) = *(xt++) + *(yt + 1); - *(pb++) = *(xt++) + *(yt + 2); - } - } - - } else { - // faked interlacing effect - unsigned char channel, channel2; - - for (yt = ytable, y = 0; y < height; y++, yt += 3) { - for (xt = xtable, x = 0; x < width; x++) { - if (y & 1) { - channel = *(xt++) + *(yt); - channel2 = (channel >> 1) + (channel >> 2); - if (channel2 > channel) channel2 = 0; - *(pr++) = channel2; - - channel = *(xt++) + *(yt + 1); - channel2 = (channel >> 1) + (channel >> 2); - if (channel2 > channel) channel2 = 0; - *(pg++) = channel2; - - channel = *(xt++) + *(yt + 2); - channel2 = (channel >> 1) + (channel >> 2); - if (channel2 > channel) channel2 = 0; - *(pb++) = channel2; - } else { - channel = *(xt++) + *(yt); - channel2 = channel + (channel >> 3); - if (channel2 < channel) channel2 = ~0; - *(pr++) = channel2; - - channel = *(xt++) + *(yt + 1); - channel2 = channel + (channel >> 3); - if (channel2 < channel) channel2 = ~0; - *(pg++) = channel2; - - channel = *(xt++) + *(yt + 2); - channel2 = channel + (channel >> 3); - if (channel2 < channel) channel2 = ~0; - *(pb++) = channel2; - } - } - } - } - - -} - - -void BImage::hgradient() { - float drx, dgx, dbx, - xr = (float) from->red(), - xg = (float) from->green(), - xb = (float) from->blue(); - unsigned char *pr = red, *pg = green, *pb = blue; - - register unsigned int x, y; - - drx = (float) (to->red() - from->red()); - dgx = (float) (to->green() - from->green()); - dbx = (float) (to->blue() - from->blue()); - - drx /= width; - dgx /= width; - dbx /= width; - - if (interlaced && height > 2) { - // faked interlacing effect - unsigned char channel, channel2; - - for (x = 0; x < width; x++, pr++, pg++, pb++) { - channel = (unsigned char) xr; - channel2 = (channel >> 1) + (channel >> 2); - if (channel2 > channel) channel2 = 0; - *pr = channel2; - - channel = (unsigned char) xg; - channel2 = (channel >> 1) + (channel >> 2); - if (channel2 > channel) channel2 = 0; - *pg = channel2; - - channel = (unsigned char) xb; - channel2 = (channel >> 1) + (channel >> 2); - if (channel2 > channel) channel2 = 0; - *pb = channel2; - - - channel = (unsigned char) xr; - channel2 = channel + (channel >> 3); - if (channel2 < channel) channel2 = ~0; - *(pr + width) = channel2; - - channel = (unsigned char) xg; - channel2 = channel + (channel >> 3); - if (channel2 < channel) channel2 = ~0; - *(pg + width) = channel2; - - channel = (unsigned char) xb; - channel2 = channel + (channel >> 3); - if (channel2 < channel) channel2 = ~0; - *(pb + width) = channel2; - - xr += drx; - xg += dgx; - xb += dbx; - } - - pr += width; - pg += width; - pb += width; - - int offset; - - for (y = 2; y < height; y++, pr += width, pg += width, pb += width) { - if (y & 1) offset = width; else offset = 0; - - memcpy(pr, (red + offset), width); - memcpy(pg, (green + offset), width); - memcpy(pb, (blue + offset), width); - } - } else { - - // normal hgradient - for (x = 0; x < width; x++) { - *(pr++) = (unsigned char) (xr); - *(pg++) = (unsigned char) (xg); - *(pb++) = (unsigned char) (xb); - - xr += drx; - xg += dgx; - xb += dbx; - } - - for (y = 1; y < height; y++, pr += width, pg += width, pb += width) { - memcpy(pr, red, width); - memcpy(pg, green, width); - memcpy(pb, blue, width); - } - - } - -} - - -void BImage::vgradient() { - float dry, dgy, dby, - yr = (float) from->red(), - yg = (float) from->green(), - yb = (float) from->blue(); - unsigned char *pr = red, *pg = green, *pb = blue; - - register unsigned int y; - - dry = (float) (to->red() - from->red()); - dgy = (float) (to->green() - from->green()); - dby = (float) (to->blue() - from->blue()); - - dry /= height; - dgy /= height; - dby /= height; - - if (interlaced) { - // faked interlacing effect - unsigned char channel, channel2; - - for (y = 0; y < height; y++, pr += width, pg += width, pb += width) { - if (y & 1) { - channel = (unsigned char) yr; - channel2 = (channel >> 1) + (channel >> 2); - if (channel2 > channel) channel2 = 0; - memset(pr, channel2, width); - - channel = (unsigned char) yg; - channel2 = (channel >> 1) + (channel >> 2); - if (channel2 > channel) channel2 = 0; - memset(pg, channel2, width); - - channel = (unsigned char) yb; - channel2 = (channel >> 1) + (channel >> 2); - if (channel2 > channel) channel2 = 0; - memset(pb, channel2, width); - } else { - channel = (unsigned char) yr; - channel2 = channel + (channel >> 3); - if (channel2 < channel) channel2 = ~0; - memset(pr, channel2, width); - - channel = (unsigned char) yg; - channel2 = channel + (channel >> 3); - if (channel2 < channel) channel2 = ~0; - memset(pg, channel2, width); - - channel = (unsigned char) yb; - channel2 = channel + (channel >> 3); - if (channel2 < channel) channel2 = ~0; - memset(pb, channel2, width); - } - - yr += dry; - yg += dgy; - yb += dby; - } - } else { - - // normal vgradient - for (y = 0; y < height; y++, pr += width, pg += width, pb += width) { - memset(pr, (unsigned char) yr, width); - memset(pg, (unsigned char) yg, width); - memset(pb, (unsigned char) yb, width); - - yr += dry; - yg += dgy; - yb += dby; - } - } - - -} - - -void BImage::pgradient() { - // pyramid gradient - based on original dgradient, written by - // Mosfet (mosfet@kde.org) - // adapted from kde sources for Blackbox by Brad Hughes - - float yr, yg, yb, drx, dgx, dbx, dry, dgy, dby, - xr, xg, xb; - int rsign, gsign, bsign; - unsigned char *pr = red, *pg = green, *pb = blue; - unsigned int tr = to->red(), tg = to->green(), tb = to->blue(), - *xt = xtable, *yt = ytable; - - register unsigned int x, y; - - dry = drx = (float) (to->red() - from->red()); - dgy = dgx = (float) (to->green() - from->green()); - dby = dbx = (float) (to->blue() - from->blue()); - - rsign = (drx < 0) ? -1 : 1; - gsign = (dgx < 0) ? -1 : 1; - bsign = (dbx < 0) ? -1 : 1; - - xr = yr = (drx / 2); - xg = yg = (dgx / 2); - xb = yb = (dbx / 2); - - // Create X table - drx /= width; - dgx /= width; - dbx /= width; - - for (x = 0; x < width; x++) { - *(xt++) = (unsigned char) ((xr < 0) ? -xr : xr); - *(xt++) = (unsigned char) ((xg < 0) ? -xg : xg); - *(xt++) = (unsigned char) ((xb < 0) ? -xb : xb); - - xr -= drx; - xg -= dgx; - xb -= dbx; - } - - // Create Y table - dry /= height; - dgy /= height; - dby /= height; - - for (y = 0; y < height; y++) { - *(yt++) = ((unsigned char) ((yr < 0) ? -yr : yr)); - *(yt++) = ((unsigned char) ((yg < 0) ? -yg : yg)); - *(yt++) = ((unsigned char) ((yb < 0) ? -yb : yb)); - - yr -= dry; - yg -= dgy; - yb -= dby; - } - - // Combine tables to create gradient - - - if (! interlaced) { - - // normal pgradient - for (yt = ytable, y = 0; y < height; y++, yt += 3) { - for (xt = xtable, x = 0; x < width; x++) { - *(pr++) = (unsigned char) (tr - (rsign * (*(xt++) + *(yt)))); - *(pg++) = (unsigned char) (tg - (gsign * (*(xt++) + *(yt + 1)))); - *(pb++) = (unsigned char) (tb - (bsign * (*(xt++) + *(yt + 2)))); - } - } - - } else { - // faked interlacing effect - unsigned char channel, channel2; - - for (yt = ytable, y = 0; y < height; y++, yt += 3) { - for (xt = xtable, x = 0; x < width; x++) { - if (y & 1) { - channel = (unsigned char) (tr - (rsign * (*(xt++) + *(yt)))); - channel2 = (channel >> 1) + (channel >> 2); - if (channel2 > channel) channel2 = 0; - *(pr++) = channel2; - - channel = (unsigned char) (tg - (gsign * (*(xt++) + *(yt + 1)))); - channel2 = (channel >> 1) + (channel >> 2); - if (channel2 > channel) channel2 = 0; - *(pg++) = channel2; - - channel = (unsigned char) (tb - (bsign * (*(xt++) + *(yt + 2)))); - channel2 = (channel >> 1) + (channel >> 2); - if (channel2 > channel) channel2 = 0; - *(pb++) = channel2; - } else { - channel = (unsigned char) (tr - (rsign * (*(xt++) + *(yt)))); - channel2 = channel + (channel >> 3); - if (channel2 < channel) channel2 = ~0; - *(pr++) = channel2; - - channel = (unsigned char) (tg - (gsign * (*(xt++) + *(yt + 1)))); - channel2 = channel + (channel >> 3); - if (channel2 < channel) channel2 = ~0; - *(pg++) = channel2; - - channel = (unsigned char) (tb - (bsign * (*(xt++) + *(yt + 2)))); - channel2 = channel + (channel >> 3); - if (channel2 < channel) channel2 = ~0; - *(pb++) = channel2; - } - } - } - } - -} - - -void BImage::rgradient() { - // rectangle gradient - based on original dgradient, written by - // Mosfet (mosfet@kde.org) - // adapted from kde sources for Blackbox by Brad Hughes - - float drx, dgx, dbx, dry, dgy, dby, xr, xg, xb, yr, yg, yb; - int rsign, gsign, bsign; - unsigned char *pr = red, *pg = green, *pb = blue; - unsigned int tr = to->red(), tg = to->green(), tb = to->blue(), - *xt = xtable, *yt = ytable; - - register unsigned int x, y; - - dry = drx = (float) (to->red() - from->red()); - dgy = dgx = (float) (to->green() - from->green()); - dby = dbx = (float) (to->blue() - from->blue()); - - rsign = (drx < 0) ? -2 : 2; - gsign = (dgx < 0) ? -2 : 2; - bsign = (dbx < 0) ? -2 : 2; - - xr = yr = (drx / 2); - xg = yg = (dgx / 2); - xb = yb = (dbx / 2); - - // Create X table - drx /= width; - dgx /= width; - dbx /= width; - - for (x = 0; x < width; x++) { - *(xt++) = (unsigned char) ((xr < 0) ? -xr : xr); - *(xt++) = (unsigned char) ((xg < 0) ? -xg : xg); - *(xt++) = (unsigned char) ((xb < 0) ? -xb : xb); - - xr -= drx; - xg -= dgx; - xb -= dbx; - } - - // Create Y table - dry /= height; - dgy /= height; - dby /= height; - - for (y = 0; y < height; y++) { - *(yt++) = ((unsigned char) ((yr < 0) ? -yr : yr)); - *(yt++) = ((unsigned char) ((yg < 0) ? -yg : yg)); - *(yt++) = ((unsigned char) ((yb < 0) ? -yb : yb)); - - yr -= dry; - yg -= dgy; - yb -= dby; - } - - // Combine tables to create gradient - - - if (! interlaced) { - - // normal rgradient - for (yt = ytable, y = 0; y < height; y++, yt += 3) { - for (xt = xtable, x = 0; x < width; x++) { - *(pr++) = (unsigned char) (tr - (rsign * std::max(*(xt++), *(yt)))); - *(pg++) = (unsigned char) (tg - (gsign * std::max(*(xt++), *(yt + 1)))); - *(pb++) = (unsigned char) (tb - (bsign * std::max(*(xt++), *(yt + 2)))); - } - } - - } else { - // faked interlacing effect - unsigned char channel, channel2; - - for (yt = ytable, y = 0; y < height; y++, yt += 3) { - for (xt = xtable, x = 0; x < width; x++) { - if (y & 1) { - channel = (unsigned char) (tr - (rsign * std::max(*(xt++), *(yt)))); - channel2 = (channel >> 1) + (channel >> 2); - if (channel2 > channel) channel2 = 0; - *(pr++) = channel2; - - channel = (unsigned char) (tg - (gsign * std::max(*(xt++), *(yt + 1)))); - channel2 = (channel >> 1) + (channel >> 2); - if (channel2 > channel) channel2 = 0; - *(pg++) = channel2; - - channel = (unsigned char) (tb - (bsign * std::max(*(xt++), *(yt + 2)))); - channel2 = (channel >> 1) + (channel >> 2); - if (channel2 > channel) channel2 = 0; - *(pb++) = channel2; - } else { - channel = (unsigned char) (tr - (rsign * std::max(*(xt++), *(yt)))); - channel2 = channel + (channel >> 3); - if (channel2 < channel) channel2 = ~0; - *(pr++) = channel2; - - channel = (unsigned char) (tg - (gsign * std::max(*(xt++), *(yt + 1)))); - channel2 = channel + (channel >> 3); - if (channel2 < channel) channel2 = ~0; - *(pg++) = channel2; - - channel = (unsigned char) (tb - (bsign * std::max(*(xt++), *(yt + 2)))); - channel2 = channel + (channel >> 3); - if (channel2 < channel) channel2 = ~0; - *(pb++) = channel2; - } - } - } - } - -} - - -void BImage::egradient() { - // elliptic gradient - based on original dgradient, written by - // Mosfet (mosfet@kde.org) - // adapted from kde sources for Blackbox by Brad Hughes - - float drx, dgx, dbx, dry, dgy, dby, yr, yg, yb, xr, xg, xb; - int rsign, gsign, bsign; - unsigned char *pr = red, *pg = green, *pb = blue; - unsigned int *xt = xtable, *yt = ytable, - tr = (unsigned long) to->red(), - tg = (unsigned long) to->green(), - tb = (unsigned long) to->blue(); - - register unsigned int x, y; - - dry = drx = (float) (to->red() - from->red()); - dgy = dgx = (float) (to->green() - from->green()); - dby = dbx = (float) (to->blue() - from->blue()); - - rsign = (drx < 0) ? -1 : 1; - gsign = (dgx < 0) ? -1 : 1; - bsign = (dbx < 0) ? -1 : 1; - - xr = yr = (drx / 2); - xg = yg = (dgx / 2); - xb = yb = (dbx / 2); - - // Create X table - drx /= width; - dgx /= width; - dbx /= width; - - for (x = 0; x < width; x++) { - *(xt++) = (unsigned long) (xr * xr); - *(xt++) = (unsigned long) (xg * xg); - *(xt++) = (unsigned long) (xb * xb); - - xr -= drx; - xg -= dgx; - xb -= dbx; - } - - // Create Y table - dry /= height; - dgy /= height; - dby /= height; - - for (y = 0; y < height; y++) { - *(yt++) = (unsigned long) (yr * yr); - *(yt++) = (unsigned long) (yg * yg); - *(yt++) = (unsigned long) (yb * yb); - - yr -= dry; - yg -= dgy; - yb -= dby; - } - - // Combine tables to create gradient - if (! interlaced) { - // normal egradient - for (yt = ytable, y = 0; y < height; y++, yt += 3) { - for (xt = xtable, x = 0; x < width; x++) { - *(pr++) = (unsigned char) - (tr - (rsign * control->getSqrt(*(xt++) + *(yt)))); - *(pg++) = (unsigned char) - (tg - (gsign * control->getSqrt(*(xt++) + *(yt + 1)))); - *(pb++) = (unsigned char) - (tb - (bsign * control->getSqrt(*(xt++) + *(yt + 2)))); - } - } - - } else { - // faked interlacing effect - unsigned char channel, channel2; - - for (yt = ytable, y = 0; y < height; y++, yt += 3) { - for (xt = xtable, x = 0; x < width; x++) { - if (y & 1) { - channel = (unsigned char) - (tr - (rsign * control->getSqrt(*(xt++) + *(yt)))); - channel2 = (channel >> 1) + (channel >> 2); - if (channel2 > channel) channel2 = 0; - *(pr++) = channel2; - - channel = (unsigned char) - (tg - (gsign * control->getSqrt(*(xt++) + *(yt + 1)))); - channel2 = (channel >> 1) + (channel >> 2); - if (channel2 > channel) channel2 = 0; - *(pg++) = channel2; - - channel = (unsigned char) - (tb - (bsign * control->getSqrt(*(xt++) + *(yt + 2)))); - channel2 = (channel >> 1) + (channel >> 2); - if (channel2 > channel) channel2 = 0; - *(pb++) = channel2; - } else { - channel = (unsigned char) - (tr - (rsign * control->getSqrt(*(xt++) + *(yt)))); - channel2 = channel + (channel >> 3); - if (channel2 < channel) channel2 = ~0; - *(pr++) = channel2; - - channel = (unsigned char) - (tg - (gsign * control->getSqrt(*(xt++) + *(yt + 1)))); - channel2 = channel + (channel >> 3); - if (channel2 < channel) channel2 = ~0; - *(pg++) = channel2; - - channel = (unsigned char) - (tb - (bsign * control->getSqrt(*(xt++) + *(yt + 2)))); - channel2 = channel + (channel >> 3); - if (channel2 < channel) channel2 = ~0; - *(pb++) = channel2; - } - } - } - } - -} - - -void BImage::pcgradient() { - // pipe cross gradient - based on original dgradient, written by - // Mosfet (mosfet@kde.org) - // adapted from kde sources for Blackbox by Brad Hughes - - float drx, dgx, dbx, dry, dgy, dby, xr, xg, xb, yr, yg, yb; - int rsign, gsign, bsign; - unsigned char *pr = red, *pg = green, *pb = blue; - unsigned int *xt = xtable, *yt = ytable, - tr = to->red(), - tg = to->green(), - tb = to->blue(); - - register unsigned int x, y; - - dry = drx = (float) (to->red() - from->red()); - dgy = dgx = (float) (to->green() - from->green()); - dby = dbx = (float) (to->blue() - from->blue()); - - rsign = (drx < 0) ? -2 : 2; - gsign = (dgx < 0) ? -2 : 2; - bsign = (dbx < 0) ? -2 : 2; - - xr = yr = (drx / 2); - xg = yg = (dgx / 2); - xb = yb = (dbx / 2); - - // Create X table - drx /= width; - dgx /= width; - dbx /= width; - - for (x = 0; x < width; x++) { - *(xt++) = (unsigned char) ((xr < 0) ? -xr : xr); - *(xt++) = (unsigned char) ((xg < 0) ? -xg : xg); - *(xt++) = (unsigned char) ((xb < 0) ? -xb : xb); - - xr -= drx; - xg -= dgx; - xb -= dbx; - } - - // Create Y table - dry /= height; - dgy /= height; - dby /= height; - - for (y = 0; y < height; y++) { - *(yt++) = ((unsigned char) ((yr < 0) ? -yr : yr)); - *(yt++) = ((unsigned char) ((yg < 0) ? -yg : yg)); - *(yt++) = ((unsigned char) ((yb < 0) ? -yb : yb)); - - yr -= dry; - yg -= dgy; - yb -= dby; - } - - // Combine tables to create gradient - if (! interlaced) { - - // normal pcgradient - for (yt = ytable, y = 0; y < height; y++, yt += 3) { - for (xt = xtable, x = 0; x < width; x++) { - *(pr++) = (unsigned char) (tr - (rsign * std::min(*(xt++), *(yt)))); - *(pg++) = (unsigned char) (tg - (gsign * std::min(*(xt++), *(yt + 1)))); - *(pb++) = (unsigned char) (tb - (bsign * std::min(*(xt++), *(yt + 2)))); - } - } - - } else { - // faked interlacing effect - unsigned char channel, channel2; - - for (yt = ytable, y = 0; y < height; y++, yt += 3) { - for (xt = xtable, x = 0; x < width; x++) { - if (y & 1) { - channel = (unsigned char) (tr - (rsign * std::min(*(xt++), *(yt)))); - channel2 = (channel >> 1) + (channel >> 2); - if (channel2 > channel) channel2 = 0; - *(pr++) = channel2; - - channel = (unsigned char) (tg - (bsign * std::min(*(xt++), *(yt + 1)))); - channel2 = (channel >> 1) + (channel >> 2); - if (channel2 > channel) channel2 = 0; - *(pg++) = channel2; - - channel = (unsigned char) (tb - (gsign * std::min(*(xt++), *(yt + 2)))); - channel2 = (channel >> 1) + (channel >> 2); - if (channel2 > channel) channel2 = 0; - *(pb++) = channel2; - } else { - channel = (unsigned char) (tr - (rsign * std::min(*(xt++), *(yt)))); - channel2 = channel + (channel >> 3); - if (channel2 < channel) channel2 = ~0; - *(pr++) = channel2; - - channel = (unsigned char) (tg - (gsign * std::min(*(xt++), *(yt + 1)))); - channel2 = channel + (channel >> 3); - if (channel2 < channel) channel2 = ~0; - *(pg++) = channel2; - - channel = (unsigned char) (tb - (bsign * std::min(*(xt++), *(yt + 2)))); - channel2 = channel + (channel >> 3); - if (channel2 < channel) channel2 = ~0; - *(pb++) = channel2; - } - } - } - } - -} - - -void BImage::cdgradient() { - // cross diagonal gradient - based on original dgradient, written by - // Mosfet (mosfet@kde.org) - // adapted from kde sources for Blackbox by Brad Hughes - - float drx, dgx, dbx, dry, dgy, dby, yr = 0.0, yg = 0.0, yb = 0.0, - xr = (float) from->red(), - xg = (float) from->green(), - xb = (float) from->blue(); - unsigned char *pr = red, *pg = green, *pb = blue; - unsigned int w = width * 2, h = height * 2, *xt, *yt; - - register unsigned int x, y; - - dry = drx = (float) (to->red() - from->red()); - dgy = dgx = (float) (to->green() - from->green()); - dby = dbx = (float) (to->blue() - from->blue()); - - // Create X table - drx /= w; - dgx /= w; - dbx /= w; - - for (xt = (xtable + (width * 3) - 1), x = 0; x < width; x++) { - *(xt--) = (unsigned char) xb; - *(xt--) = (unsigned char) xg; - *(xt--) = (unsigned char) xr; - - xr += drx; - xg += dgx; - xb += dbx; - } - - // Create Y table - dry /= h; - dgy /= h; - dby /= h; - - for (yt = ytable, y = 0; y < height; y++) { - *(yt++) = (unsigned char) yr; - *(yt++) = (unsigned char) yg; - *(yt++) = (unsigned char) yb; - - yr += dry; - yg += dgy; - yb += dby; - } - - // Combine tables to create gradient - - if (! interlaced) { - // normal cdgradient - for (yt = ytable, y = 0; y < height; y++, yt += 3) { - for (xt = xtable, x = 0; x < width; x++) { - *(pr++) = *(xt++) + *(yt); - *(pg++) = *(xt++) + *(yt + 1); - *(pb++) = *(xt++) + *(yt + 2); - } - } - - } else { - // faked interlacing effect - unsigned char channel, channel2; - - for (yt = ytable, y = 0; y < height; y++, yt += 3) { - for (xt = xtable, x = 0; x < width; x++) { - if (y & 1) { - channel = *(xt++) + *(yt); - channel2 = (channel >> 1) + (channel >> 2); - if (channel2 > channel) channel2 = 0; - *(pr++) = channel2; - - channel = *(xt++) + *(yt + 1); - channel2 = (channel >> 1) + (channel >> 2); - if (channel2 > channel) channel2 = 0; - *(pg++) = channel2; - - channel = *(xt++) + *(yt + 2); - channel2 = (channel >> 1) + (channel >> 2); - if (channel2 > channel) channel2 = 0; - *(pb++) = channel2; - } else { - channel = *(xt++) + *(yt); - channel2 = channel + (channel >> 3); - if (channel2 < channel) channel2 = ~0; - *(pr++) = channel2; - - channel = *(xt++) + *(yt + 1); - channel2 = channel + (channel >> 3); - if (channel2 < channel) channel2 = ~0; - *(pg++) = channel2; - - channel = *(xt++) + *(yt + 2); - channel2 = channel + (channel >> 3); - if (channel2 < channel) channel2 = ~0; - *(pb++) = channel2; - } - } - } - } - -} - - -BImageControl::BImageControl(const ScreenInfo *scrn, bool dither, - int _cpc, unsigned long cache_timeout, unsigned long cmax): -m_timer(this) { - I18n *i18n = I18n::instance(); - Display *disp = BaseDisplay::instance()->getXDisplay(); - screeninfo = scrn; - setDither(dither); - setColorsPerChannel(_cpc); - - cache_max = cmax; -#ifdef TIMEDCACHE - if (cache_timeout) { - m_timer.setTimeout(cache_timeout); - m_timer.start(); - } -#endif // TIMEDCACHE - - colors = (XColor *) 0; - ncolors = 0; - - grad_xbuffer = grad_ybuffer = (unsigned int *) 0; - grad_buffer_width = grad_buffer_height = 0; - - screen_depth = screeninfo->getDepth(); - window = screeninfo->getRootWindow(); - screen_number = screeninfo->getScreenNumber(); - - int count; - XPixmapFormatValues *pmv = XListPixmapFormats(disp, &count); - m_colormap = screeninfo->colormap(); - - if (pmv) { - bits_per_pixel = 0; - for (int i = 0; i < count; i++) { - if (pmv[i].depth == screen_depth) { - bits_per_pixel = pmv[i].bits_per_pixel; - break; - } - } - - XFree(pmv); - } - - if (bits_per_pixel == 0) - bits_per_pixel = screen_depth; - if (bits_per_pixel >= 24) - setDither(false); - - red_offset = green_offset = blue_offset = 0; - - switch (visual()->c_class) { - case TrueColor: { - int i; - - // compute color tables - unsigned long red_mask = visual()->red_mask, - green_mask = visual()->green_mask, - blue_mask = visual()->blue_mask; - - while (! (red_mask & 1)) { red_offset++; red_mask >>= 1; } - while (! (green_mask & 1)) { green_offset++; green_mask >>= 1; } - while (! (blue_mask & 1)) { blue_offset++; blue_mask >>= 1; } - - red_bits = 255 / red_mask; - green_bits = 255 / green_mask; - blue_bits = 255 / blue_mask; - - for (i = 0; i < 256; i++) { - red_color_table[i] = i / red_bits; - green_color_table[i] = i / green_bits; - blue_color_table[i] = i / blue_bits; - } - } - - break; - - case PseudoColor: - case StaticColor: { - - ncolors = colors_per_channel * colors_per_channel * colors_per_channel; - - if (ncolors > (1 << screen_depth)) { - colors_per_channel = (1 << screen_depth) / 3; - ncolors = colors_per_channel * colors_per_channel * colors_per_channel; - } - - if (colors_per_channel < 2 || ncolors > (1 << screen_depth)) { - fprintf(stderr, - i18n-> - getMessage( - FBNLS::ImageSet, FBNLS::ImageInvalidColormapSize, - "BImageControl::BImageControl: invalid colormap size %d " - "(%d/%d/%d) - reducing"), - ncolors, colors_per_channel, colors_per_channel, - colors_per_channel); - - colors_per_channel = (1 << screen_depth) / 3; - } - - colors = new XColor[ncolors]; - if (! colors) { - fprintf(stderr, - i18n-> - getMessage( - FBNLS::ImageSet, FBNLS::ImageErrorAllocatingColormap, - "BImageControl::BImageControl: error allocating " - "colormap\n")); - throw static_cast<int>(1); //throw exit code 1 - } - - int i = 0, ii, p, r, g, b, - -#ifdef ORDEREDPSEUDO - bits = 256 / colors_per_channel; -#else // !ORDEREDPSEUDO - bits = 255 / (colors_per_channel - 1); -#endif // ORDEREDPSEUDO - - red_bits = green_bits = blue_bits = bits; - - for (i = 0; i < 256; i++) - red_color_table[i] = green_color_table[i] = blue_color_table[i] = - i / bits; - - for (r = 0, i = 0; r < colors_per_channel; r++) { - for (g = 0; g < colors_per_channel; g++) { - for (b = 0; b < colors_per_channel; b++, i++) { - colors[i].red = (r * 0xffff) / (colors_per_channel - 1); - colors[i].green = (g * 0xffff) / (colors_per_channel - 1); - colors[i].blue = (b * 0xffff) / (colors_per_channel - 1);; - colors[i].flags = DoRed|DoGreen|DoBlue; - } - } - } - - for (i = 0; i < ncolors; i++) { - if (! XAllocColor(disp, colormap(), &colors[i])) { - fprintf(stderr, - i18n->getMessage( - FBNLS::ImageSet, FBNLS::ImageColorAllocFail, - "couldn't alloc color %i %i %i\n"), - colors[i].red, colors[i].green, colors[i].blue); - colors[i].flags = 0; - } else - colors[i].flags = DoRed|DoGreen|DoBlue; - } - - XColor icolors[256]; - int incolors = (((1 << screen_depth) > 256) ? 256 : (1 << screen_depth)); - - for (i = 0; i < incolors; i++) - icolors[i].pixel = i; - - XQueryColors(disp, colormap(), icolors, incolors); - for (i = 0; i < ncolors; i++) { - if (! colors[i].flags) { - unsigned long chk = 0xffffffff, pixel, close = 0; - p = 2; - - while (p--) { - for (ii = 0; ii < incolors; ii++) { - r = (colors[i].red - icolors[i].red) >> 8; - g = (colors[i].green - icolors[i].green) >> 8; - b = (colors[i].blue - icolors[i].blue) >> 8; - pixel = (r * r) + (g * g) + (b * b); - - if (pixel < chk) { - chk = pixel; - close = ii; - } - - colors[i].red = icolors[close].red; - colors[i].green = icolors[close].green; - colors[i].blue = icolors[close].blue; - - if (XAllocColor(disp, colormap(), - &colors[i])) { - colors[i].flags = DoRed|DoGreen|DoBlue; - break; - } - } - } - } - } - - break; - } - - case GrayScale: - case StaticGray: - { - - if (visual()->c_class == StaticGray) { - ncolors = 1 << screen_depth; - } else { - ncolors = colors_per_channel * colors_per_channel * colors_per_channel; - - if (ncolors > (1 << screen_depth)) { - colors_per_channel = (1 << screen_depth) / 3; - ncolors = - colors_per_channel * colors_per_channel * colors_per_channel; - } - } - - if (colors_per_channel < 2 || ncolors > (1 << screen_depth)) { - fprintf(stderr, - i18n-> - getMessage( - FBNLS::ImageSet, FBNLS::ImageInvalidColormapSize, - "BImageControl::BImageControl: invalid colormap size %d " - "(%d/%d/%d) - reducing"), - ncolors, colors_per_channel, colors_per_channel, - colors_per_channel); - - colors_per_channel = (1 << screen_depth) / 3; - } - - colors = new XColor[ncolors]; - if (! colors) { - fprintf(stderr, - i18n-> - getMessage( - FBNLS::ImageSet, FBNLS::ImageErrorAllocatingColormap, - "BImageControl::BImageControl: error allocating " - "colormap\n")); - throw static_cast<int>(1); // throw exit code 1 - } - - int i = 0, ii, p, bits = 255 / (colors_per_channel - 1); - red_bits = green_bits = blue_bits = bits; - - for (i = 0; i < 256; i++) - red_color_table[i] = green_color_table[i] = blue_color_table[i] = - i / bits; - - for (i = 0; i < ncolors; i++) { - colors[i].red = (i * 0xffff) / (colors_per_channel - 1); - colors[i].green = (i * 0xffff) / (colors_per_channel - 1); - colors[i].blue = (i * 0xffff) / (colors_per_channel - 1);; - colors[i].flags = DoRed|DoGreen|DoBlue; - - if (! XAllocColor(disp, colormap(), - &colors[i])) { - fprintf(stderr, - i18n-> - getMessage( - FBNLS::ImageSet, FBNLS::ImageColorAllocFail, - "couldn't alloc color %i %i %i\n"), - colors[i].red, colors[i].green, colors[i].blue); - colors[i].flags = 0; - } else - colors[i].flags = DoRed|DoGreen|DoBlue; - } - - - XColor icolors[256]; - int incolors = (((1 << screen_depth) > 256) ? 256 : - (1 << screen_depth)); - - for (i = 0; i < incolors; i++) - icolors[i].pixel = i; - - XQueryColors(disp, colormap(), icolors, incolors); - for (i = 0; i < ncolors; i++) { - if (! colors[i].flags) { - unsigned long chk = 0xffffffff, pixel, close = 0; - - p = 2; - while (p--) { - for (ii = 0; ii < incolors; ii++) { - int r = (colors[i].red - icolors[i].red) >> 8; - int g = (colors[i].green - icolors[i].green) >> 8; - int b = (colors[i].blue - icolors[i].blue) >> 8; - pixel = (r * r) + (g * g) + (b * b); - - if (pixel < chk) { - chk = pixel; - close = ii; - } - - colors[i].red = icolors[close].red; - colors[i].green = icolors[close].green; - colors[i].blue = icolors[close].blue; - - if (XAllocColor(disp, colormap(), - &colors[i])) { - colors[i].flags = DoRed|DoGreen|DoBlue; - break; - } - } - } - } - } - - break; - } - - default: - fprintf(stderr, - i18n-> - getMessage( - FBNLS::ImageSet, FBNLS::ImageUnsupVisual, - "BImageControl::BImageControl: unsupported visual %d\n"), - visual()->c_class); - throw static_cast<int>(1); //throw error code 1 - - } -} - - -BImageControl::~BImageControl() { - if (sqrt_table) { - delete [] sqrt_table; - } - - if (grad_xbuffer) { - delete [] grad_xbuffer; - } - - if (grad_ybuffer) { - delete [] grad_ybuffer; - } - - if (colors) { - unsigned long *pixels = new unsigned long [ncolors]; - - for (int color = 0; color < ncolors; color++) - *(pixels + color) = (*(colors + color)).pixel; - - XFreeColors(BaseDisplay::getXDisplay(), colormap(), pixels, ncolors, 0); - - delete [] colors; - } - - if (cache.size() > 0) { - fprintf(stderr, - I18n::instance()-> - getMessage( - FBNLS::ImageSet, FBNLS::ImagePixmapRelease, - "BImageContol::~BImageControl: pixmap cache - " - "releasing %d pixmaps\n"), cache.size()); - - CacheList::iterator it = cache.begin(); - CacheList::iterator it_end = cache.end(); - for (; it != it_end; ++it) { - XFreePixmap(BaseDisplay::getXDisplay(), (*it)->pixmap); - delete (*it); - } - - } -} - - -Pixmap BImageControl::searchCache(unsigned int width, unsigned int height, - unsigned long texture_type, - const FbTk::Color &color, const FbTk::Color &color_to) { - CacheList::iterator it = cache.begin(); - CacheList::iterator it_end = cache.end(); - for (; it != it_end; ++it) { - if (((*it)->width == width) && - ((*it)->height == height) && - ((*it)->texture == texture_type) && - ((*it)->pixel1 == color.pixel())) { - if (texture_type & FbTk::Texture::GRADIENT) { - if ((*it)->pixel2 == color_to.pixel()) { - (*it)->count++; - return (*it)->pixmap; - } - } else { - (*it)->count++; - return (*it)->pixmap; - } - } - } - - return None; -} - - -Pixmap BImageControl::renderImage(unsigned int width, unsigned int height, - const FbTk::Texture &texture) { - - if (texture.type() & FbTk::Texture::PARENTRELATIVE) - return ParentRelative; - - // search cache first - Pixmap pixmap = searchCache(width, height, texture.type(), - texture.color(), texture.colorTo()); - if (pixmap) - return pixmap; // return cache item - - // render new image - BImage image(this, width, height); - pixmap = image.render(texture); - - if (pixmap) { - // create new cache item and add it to cache list - - Cache *tmp = new Cache; - - tmp->pixmap = pixmap; - tmp->width = width; - tmp->height = height; - tmp->count = 1; - tmp->texture = texture.type(); - tmp->pixel1 = texture.color().pixel(); - - if (texture.type() & FbTk::Texture::GRADIENT) - tmp->pixel2 = texture.colorTo().pixel(); - else - tmp->pixel2 = 0l; - - cache.push_back(tmp); - - if ((unsigned) cache.size() > cache_max) { -#ifdef DEBUG - cerr<<I18n::instance()-> - getMessage( - FBNLS::ImageSet, FBNLS::ImagePixmapCacheLarge, - "BImageControl::renderImage: cache is large, " - "forcing cleanout\n")<<endl; -#endif // DEBUG - timeout(); - } - - return pixmap; - } - - return None; -} - - -void BImageControl::removeImage(Pixmap pixmap) { - if (!pixmap) - return; - - CacheList::iterator it = cache.begin(); - CacheList::iterator it_end = cache.end(); - for (; it != it_end; ++it) { - if ((*it)->pixmap == pixmap) { - if ((*it)->count) { - (*it)->count--; - -#ifdef TIMEDCACHE - timeout(); -#else // !TIMEDCACHE - if (! (*it)->count) timeout(); -#endif // TIMEDCACHE - } - - return; - } - } -} - - -void BImageControl::colorTables(unsigned char **rmt, unsigned char **gmt, - unsigned char **bmt, - int *roff, int *goff, int *boff, - int *rbit, int *gbit, int *bbit) { - - if (rmt) *rmt = red_color_table; - if (gmt) *gmt = green_color_table; - if (bmt) *bmt = blue_color_table; - - if (roff) *roff = red_offset; - if (goff) *goff = green_offset; - if (boff) *boff = blue_offset; - - if (rbit) *rbit = red_bits; - if (gbit) *gbit = green_bits; - if (bbit) *bbit = blue_bits; -} - - -void BImageControl::getXColorTable(XColor **c, int *n) { - if (c) *c = colors; - if (n) *n = ncolors; -} - - -void BImageControl::getGradientBuffers(unsigned int w, - unsigned int h, - unsigned int **xbuf, - unsigned int **ybuf) -{ - if (w > grad_buffer_width) { - if (grad_xbuffer) { - delete [] grad_xbuffer; - } - - grad_buffer_width = w; - - grad_xbuffer = new unsigned int[grad_buffer_width * 3]; - } - - if (h > grad_buffer_height) { - if (grad_ybuffer) { - delete [] grad_ybuffer; - } - - grad_buffer_height = h; - - grad_ybuffer = new unsigned int[grad_buffer_height * 3]; - } - - *xbuf = grad_xbuffer; - *ybuf = grad_ybuffer; -} - - -void BImageControl::installRootColormap() { - BaseDisplay::instance()->grab(); - - Bool install = True; - int i = 0, ncmap = 0; - Colormap *cmaps = - XListInstalledColormaps(BaseDisplay::getXDisplay(), window, &ncmap); - - if (cmaps) { - for (i = 0; i < ncmap; i++) { - if (*(cmaps + i) == colormap()) - install = False; - } - - if (install) - XInstallColormap(BaseDisplay::getXDisplay(), colormap()); - - XFree(cmaps); - } - - BaseDisplay::instance()->ungrab(); -} - - -void BImageControl::setColorsPerChannel(int cpc) { - if (cpc < 2) cpc = 2; - if (cpc > 6) cpc = 6; - - colors_per_channel = cpc; -} - - -unsigned long BImageControl::getSqrt(unsigned int x) { - if (! sqrt_table) { - // build sqrt table for use with elliptic gradient - - sqrt_table = new unsigned long[(256 * 256 * 2) + 1]; - int i = 0; - - for (; i < (256 * 256 * 2); i++) - *(sqrt_table + i) = bsqrt(i); - } - - return (*(sqrt_table + x)); -} - -void BImageControl::timeout() { - CacheList::iterator it = cache.begin(); - CacheList::iterator it_end = cache.end(); - for (; it != it_end; ++it) { - Cache *tmp = (*it); - - if (tmp->count <= 0) { - XFreePixmap(BaseDisplay::getXDisplay(), tmp->pixmap); - it = cache.erase(it); - delete tmp; - if (it == it_end) break; - } - } -}
D src/Image.hh

@@ -1,187 +0,0 @@

-// Image.hh for Fluxbox Window Manager -// Copyright (c) 2001 - 2002 Henrik Kinnunen (fluxbox@linuxmail.org) -// -// Image.hh for Blackbox - an X11 Window manager -// Copyright (c) 1997 - 2000 Brad Hughes (bhughes@tcac.net) -// -// Permission is hereby granted, free of charge, to any person obtaining a -// copy of this software and associated documentation files (the "Software"), -// to deal in the Software without restriction, including without limitation -// the rights to use, copy, modify, merge, publish, distribute, sublicense, -// and/or sell copies of the Software, and to permit persons to whom the -// Software is furnished to do so, subject to the following conditions: -// -// The above copyright notice and this permission notice shall be included in -// all copies or substantial portions of the Software. -// -// THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR -// IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, -// FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL -// THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER -// LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING -// FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER -// DEALINGS IN THE SOFTWARE. - -// $Id: Image.hh,v 1.17 2002/11/27 22:03:00 fluxgen Exp $ - -#ifndef IMAGE_HH -#define IMAGE_HH - - -#include "BaseDisplay.hh" -#include "Color.hh" -#include "Texture.hh" -#include "Timer.hh" - -#include <X11/Xlib.h> -#include <X11/Xutil.h> -#include <list> - -class BImageControl; - -/** - Renders to pixmap -*/ -class BImage { -public: - BImage(BImageControl *ic, unsigned int width, unsigned int height); - ~BImage(); - /// render to pixmap - Pixmap render(const FbTk::Texture &src_texture); - /// render solid texture to pixmap - Pixmap renderSolid(const FbTk::Texture &src_texture); - /// render gradient texture to pixmap - Pixmap renderGradient(const FbTk::Texture &src_texture); - -protected: - /** - Render to pixmap - @return rendered pixmap - */ - Pixmap renderPixmap(); - /** - Render to XImage - @returns allocated and rendered XImage, user is responsible to deallocate - */ - XImage *renderXImage(); - /** - @name render functions - */ - //@{ - void invert(); - void bevel1(); - void bevel2(); - void dgradient(); - void egradient(); - void hgradient(); - void pgradient(); - void rgradient(); - void vgradient(); - void cdgradient(); - void pcgradient(); - //@} - -private: - BImageControl *control; - bool interlaced; - - XColor *colors; // color table - - const FbTk::Color *from, *to; - int red_offset, green_offset, blue_offset, red_bits, green_bits, blue_bits, - ncolors, cpc, cpccpc; - unsigned char *red, *green, *blue, *red_table, *green_table, *blue_table; - unsigned int width, height, *xtable, *ytable; -}; - -/** - Holds screen info and color tables -*/ -class BImageControl : public TimeoutHandler { -public: - BImageControl(const ScreenInfo *screen, bool dither = false, int colors_per_channel = 4, - unsigned long cache_timeout = 300000l, unsigned long cache_max = 200l); - virtual ~BImageControl(); - - inline bool doDither() const { return m_dither; } - inline Colormap colormap() const { return m_colormap; } - inline const ScreenInfo *getScreenInfo() const { return screeninfo; } - inline Window drawable() const { return window; } - - /// @return visual of screen - inline Visual *visual() { return screeninfo->getVisual(); } - /// @return Bits per pixel of screen - inline int bitsPerPixel() const { return bits_per_pixel; } - /// @return depth of screen - inline int depth() const { return screen_depth; } - inline int colorsPerChannel() const { return colors_per_channel; } - - unsigned long getSqrt(unsigned int val); - /** - Render to pixmap - @param width width of pixmap - @param height height of pixmap - @param src_texture texture type to render - @return pixmap of the rendered image, on failure None - */ - Pixmap renderImage(unsigned int width, unsigned int height, - const FbTk::Texture &src_texture); - - void installRootColormap(); - void removeImage(Pixmap thepix); - void colorTables(unsigned char **, unsigned char **, unsigned char **, - int *, int *, int *, int *, int *, int *); - void getXColorTable(XColor **, int *); - void getGradientBuffers(unsigned int, unsigned int, - unsigned int **, unsigned int **); - void setDither(bool d) { m_dither = d; } - void setColorsPerChannel(int cpc); - - virtual void timeout(); - -protected: - /** - Search cache for a specific pixmap - @return None if no cache was found - */ - Pixmap searchCache(unsigned int width, unsigned int height, unsigned long texture_type, - const FbTk::Color &color, const FbTk::Color &color_to); - -private: - bool m_dither; - const ScreenInfo *screeninfo; - - BTimer m_timer; - - Colormap m_colormap; - - Window window; - XColor *colors; ///< color table - - int colors_per_channel, ncolors, screen_number, screen_depth, - bits_per_pixel, red_offset, green_offset, blue_offset, - red_bits, green_bits, blue_bits; - - unsigned char red_color_table[256], green_color_table[256], - blue_color_table[256]; - unsigned int *grad_xbuffer, *grad_ybuffer, grad_buffer_width, - grad_buffer_height; - - static unsigned long *sqrt_table; /// sqrt lookup table - - typedef struct Cache { - Pixmap pixmap; - - unsigned int count, width, height; - unsigned long pixel1, pixel2, texture; - } Cache; - - unsigned long cache_max; - typedef std::list<Cache *> CacheList; - - CacheList cache; -}; - - -#endif // IMAGE_HH -