Toshihiro Shimizu 890ddd
Toshihiro Shimizu 890ddd
Toshihiro Shimizu 890ddd
#include "trop.h"
Toshihiro Shimizu 890ddd
Shinya Kitaoka 120a6e
namespace {
Toshihiro Shimizu 890ddd
Toshihiro Shimizu 890ddd
//-------------------------------------------------------------------
Toshihiro Shimizu 890ddd
Toshihiro Shimizu 890ddd
template <typename channel_type="" pixel,="" typename=""></typename>
Shinya Kitaoka 120a6e
void computeBBox(TRasterPT<pixel> ras, TRect &bbox) {</pixel>
Shinya Kitaoka 120a6e
  bbox   = ras->getBounds();
Shinya Kitaoka 120a6e
  int lx = ras->getLx();
Shinya Kitaoka 120a6e
  int ly = ras->getLy();
Shinya Kitaoka 120a6e
Shinya Kitaoka 120a6e
  // se c'e' un pixel opaco in alto a sin e in basso a destra allora bbox =
Shinya Kitaoka 120a6e
  // bounds
Shinya Kitaoka 120a6e
  if (ras->pixels(0)[0].m != 0 && ras->pixels(ly - 1)[lx - 1].m != 0) return;
Toshihiro Shimizu 890ddd
Toshihiro Shimizu 890ddd
  int y;
Shinya Kitaoka 120a6e
  ras->lock();
Shinya Kitaoka 120a6e
  for (y = 0; y < ly; y++) {
Shinya Kitaoka 120a6e
    CHANNEL_TYPE *pix    = &(ras->pixels(y)->m);
Shinya Kitaoka 120a6e
    CHANNEL_TYPE *endPix = pix + 4 * lx;
Shinya Kitaoka 120a6e
    while (pix < endPix && *pix == 0) pix += 4;
Shinya Kitaoka 120a6e
    if (pix < endPix) break;
Shinya Kitaoka 120a6e
  }
Shinya Kitaoka 120a6e
  if (y == ly) {
Shinya Kitaoka 120a6e
    // tutta trasparente
Shinya Kitaoka 120a6e
    bbox = TRect();
Shinya Kitaoka 120a6e
    ras->unlock();
Shinya Kitaoka 120a6e
    return;
Shinya Kitaoka 120a6e
  }
Shinya Kitaoka 120a6e
  bbox.y0 = y;
Shinya Kitaoka 120a6e
  for (y = ly - 1; y > bbox.y0; y--) {
Shinya Kitaoka 120a6e
    CHANNEL_TYPE *pix    = &(ras->pixels(y)->m);
Shinya Kitaoka 120a6e
    CHANNEL_TYPE *endPix = pix + 4 * lx;
Shinya Kitaoka 120a6e
    while (pix < endPix && *pix == 0) pix += 4;
Shinya Kitaoka 120a6e
    if (pix < endPix) break;
Shinya Kitaoka 120a6e
  }
Shinya Kitaoka 120a6e
  bbox.y1 = y;
Shinya Kitaoka 120a6e
  assert(bbox.y0 <= bbox.y1);
Shinya Kitaoka 120a6e
  bbox.x0 = lx;
Shinya Kitaoka 120a6e
  bbox.x1 = -1;
Shinya Kitaoka 120a6e
  for (y = bbox.y0; y <= bbox.y1; y++) {
Shinya Kitaoka 120a6e
    CHANNEL_TYPE *row = &(ras->pixels(y)->m);
Shinya Kitaoka 120a6e
    int x             = 0;
Shinya Kitaoka 120a6e
    for (x = 0; x < bbox.x0 && row[x * 4] == 0; x++) {
Shinya Kitaoka 120a6e
    }
Shinya Kitaoka 120a6e
    bbox.x0 = x;
Shinya Kitaoka 120a6e
    for (x = lx - 1; x > bbox.x1 && row[x * 4] == 0; x--) {
Shinya Kitaoka 120a6e
    }
Shinya Kitaoka 120a6e
    bbox.x1 = x;
Shinya Kitaoka 120a6e
  }
Shinya Kitaoka 120a6e
  assert(bbox.x0 <= bbox.x1);
Shinya Kitaoka 120a6e
Shinya Kitaoka 120a6e
  ras->unlock();
Shinya Kitaoka 120a6e
  /*
Shinya Kitaoka 120a6e
Shinya Kitaoka 120a6e
  UCHAR *row_m = &(ras->pixels()->m);
Shinya Kitaoka 120a6e
// se c'e' un pixel opaco in alto a sin e in basso a destra allora bbox = bounds
Shinya Kitaoka 120a6e
if(row_m[0] && row_m[(ly-1)*wrap4 + (lx-1)*4])
Shinya Kitaoka 120a6e
    return;
Shinya Kitaoka 120a6e
Shinya Kitaoka 120a6e
int y;
Shinya Kitaoka 120a6e
UCHAR *m, *max_m, *min_m;
Shinya Kitaoka 120a6e
Shinya Kitaoka 120a6e
for(y=0;y
Shinya Kitaoka 120a6e
    {
Shinya Kitaoka 120a6e
max_m = row_m + lx * 4;
Shinya Kitaoka 120a6e
           for(m = row_m; m
Shinya Kitaoka 120a6e
           if(m
Shinya Kitaoka 120a6e
           row_m += wrap4;
Shinya Kitaoka 120a6e
          }
Shinya Kitaoka 120a6e
if(y>=ly)
Shinya Kitaoka 120a6e
    {
Shinya Kitaoka 120a6e
           // tutta trasparente
Shinya Kitaoka 120a6e
           return;
Shinya Kitaoka 120a6e
          }
Shinya Kitaoka 120a6e
Shinya Kitaoka 120a6e
  bbox.y0 = bbox.y1 = y;
Shinya Kitaoka 120a6e
bbox.x0 = (m - row_m)/4;
Shinya Kitaoka 120a6e
assert(0<=bbox.x0 && bbox.x0
Shinya Kitaoka 120a6e
assert(ras->pixels(bbox.y0)[bbox.x0].m>0);
Shinya Kitaoka 120a6e
assert(bbox.x0 == 0 || ras->pixels(bbox.y0)[bbox.x0-1].m==0);
Shinya Kitaoka 120a6e
Shinya Kitaoka 120a6e
min_m = m;
Shinya Kitaoka 120a6e
for(m = max_m - 4;m>min_m && *m==0;m-=4) {}
Shinya Kitaoka 120a6e
bbox.x1 = (m - row_m)/4;
Shinya Kitaoka 120a6e
assert(0<=bbox.x1 && bbox.x1
Shinya Kitaoka 120a6e
assert(ras->pixels(bbox.y0)[bbox.x1].m>0);
Shinya Kitaoka 120a6e
assert(bbox.x1 == lx-1 || ras->pixels(bbox.y0)[bbox.x1+1].m==0);
Shinya Kitaoka 120a6e
Shinya Kitaoka 120a6e
  row_m += wrap4;
Shinya Kitaoka 120a6e
Shinya Kitaoka 120a6e
for(y++;y
Shinya Kitaoka 120a6e
    {
Shinya Kitaoka 120a6e
max_m = row_m + lx * 4;
Shinya Kitaoka 120a6e
           for(m = row_m; m
Shinya Kitaoka 120a6e
           if(m
Shinya Kitaoka 120a6e
             {
Shinya Kitaoka 120a6e
                    int x = (m - row_m)/4;
Shinya Kitaoka 120a6e
                          if(x
Shinya Kitaoka 120a6e
                            {
Shinya Kitaoka 120a6e
                                   bbox.x0 = x;
Shinya Kitaoka 120a6e
     assert(0<=bbox.x0 && bbox.x0
Shinya Kitaoka 120a6e
     assert(ras->pixels(y)[bbox.x0].m>0);
Shinya Kitaoka 120a6e
     assert(bbox.x0 == 0 || ras->pixels(y)[bbox.x0-1].m==0);
Shinya Kitaoka 120a6e
    }
Shinya Kitaoka 120a6e
  min_m = row_m + bbox.x1*4;
Shinya Kitaoka 120a6e
                    for(m = max_m - 4;m>min_m && *m==0;m-=4) {}
Shinya Kitaoka 120a6e
                          if(m>min_m)
Shinya Kitaoka 120a6e
                            {
Shinya Kitaoka 120a6e
                                   x = (m - row_m)/4;
Shinya Kitaoka 120a6e
                                   assert(x>bbox.x1);
Shinya Kitaoka 120a6e
                                   bbox.x1 = x;
Shinya Kitaoka 120a6e
                                  }
Shinya Kitaoka 120a6e
                          bbox.y1 = y;
Shinya Kitaoka 120a6e
                   }
Shinya Kitaoka 120a6e
           row_m += wrap4;
Toshihiro Shimizu 890ddd
          }
Toshihiro Shimizu 890ddd
*/
Toshihiro Shimizu 890ddd
}
Toshihiro Shimizu 890ddd
Toshihiro Shimizu 890ddd
//-------------------------------------------------------------------
Toshihiro Shimizu 890ddd
Shinya Kitaoka 120a6e
inline bool isTransparent(TPixelCM32 *pix) {
Shinya Kitaoka 120a6e
  return (!pix->isPureInk() &&
Shinya Kitaoka 120a6e
          //  (pix->getPaint()==BackgroundStyle
Shinya Kitaoka 120a6e
          (pix->getPaint() == 0 && pix->isPurePaint()));
Toshihiro Shimizu 890ddd
}
Toshihiro Shimizu 890ddd
Toshihiro Shimizu 890ddd
//-------------------------------------------------------------------
Toshihiro Shimizu 890ddd
Shinya Kitaoka 120a6e
void computeBBoxCM32(TRasterCM32P ras, TRect &bbox) {
Shinya Kitaoka 120a6e
  bbox   = ras->getBounds();
Shinya Kitaoka 120a6e
  int lx = ras->getLx();
Shinya Kitaoka 120a6e
  int ly = ras->getLy();
Shinya Kitaoka 120a6e
Shinya Kitaoka 120a6e
  // se c'e' un pixel opaco in alto a sin e in basso a destra allora bbox =
Shinya Kitaoka 120a6e
  // bounds
Shinya Kitaoka 120a6e
  if (!isTransparent(&(ras->pixels(0)[0])) &&
Shinya Kitaoka 120a6e
      !isTransparent(&(ras->pixels(ly - 1)[lx - 1])))
Shinya Kitaoka 120a6e
    return;
Shinya Kitaoka 120a6e
Shinya Kitaoka 120a6e
  int y;
Shinya Kitaoka 120a6e
  ras->lock();
Shinya Kitaoka 120a6e
  for (y = 0; y < ly; y++) {
Shinya Kitaoka 120a6e
    TPixelCM32 *pix    = ras->pixels(y);
Shinya Kitaoka 120a6e
    TPixelCM32 *endPix = pix + lx;
Shinya Kitaoka 120a6e
    while (pix < endPix && isTransparent(pix)) ++pix;
Shinya Kitaoka 120a6e
    if (pix < endPix) break;
Shinya Kitaoka 120a6e
  }
Shinya Kitaoka 120a6e
  if (y == ly) {
Shinya Kitaoka 120a6e
    // tutta trasparente
Shinya Kitaoka 120a6e
    bbox = TRect();
Shinya Kitaoka 120a6e
    ras->unlock();
Shinya Kitaoka 120a6e
    return;
Shinya Kitaoka 120a6e
  }
Shinya Kitaoka 120a6e
  bbox.y0 = y;
Shinya Kitaoka 120a6e
  for (y = ly - 1; y > bbox.y0; y--) {
Shinya Kitaoka 120a6e
    TPixelCM32 *pix    = ras->pixels(y);
Shinya Kitaoka 120a6e
    TPixelCM32 *endPix = pix + lx;
Shinya Kitaoka 120a6e
    while (pix < endPix && isTransparent(pix)) ++pix;
Shinya Kitaoka 120a6e
    if (pix < endPix) break;
Shinya Kitaoka 120a6e
  }
Shinya Kitaoka 120a6e
  bbox.y1 = y;
Shinya Kitaoka 120a6e
  assert(bbox.y0 <= bbox.y1);
Shinya Kitaoka 120a6e
  bbox.x0 = lx;
Shinya Kitaoka 120a6e
  bbox.x1 = -1;
Shinya Kitaoka 120a6e
  for (y = bbox.y0; y <= bbox.y1; y++) {
Shinya Kitaoka 120a6e
    TPixelCM32 *row = ras->pixels(y);
Shinya Kitaoka 120a6e
    int x           = 0;
Shinya Kitaoka 120a6e
    for (x = 0; x < bbox.x0 && isTransparent(&row[x]); x++) {
Shinya Kitaoka 120a6e
    }
Shinya Kitaoka 120a6e
    bbox.x0 = x;
Shinya Kitaoka 120a6e
    for (x = lx - 1; x > bbox.x1 && isTransparent(&row[x]); x--) {
Shinya Kitaoka 120a6e
    }
Shinya Kitaoka 120a6e
    bbox.x1 = x;
Shinya Kitaoka 120a6e
  }
Shinya Kitaoka 120a6e
  assert(bbox.x0 <= bbox.x1);
Shinya Kitaoka 120a6e
  ras->unlock();
Toshihiro Shimizu 890ddd
}
Toshihiro Shimizu 890ddd
Toshihiro Shimizu 890ddd
//-------------------------------------------------------------------
Toshihiro Shimizu 890ddd
Shinya Kitaoka 120a6e
}  // namespace
Toshihiro Shimizu 890ddd
Toshihiro Shimizu 890ddd
//-------------------------------------------------------------------
Toshihiro Shimizu 890ddd
Shinya Kitaoka 120a6e
void TRop::computeBBox(TRasterP ras, TRect &bbox) {
Shinya Kitaoka 120a6e
  TRaster32P ras32 = ras;
Shinya Kitaoka 120a6e
  if (ras32) {
Shinya Kitaoka 120a6e
    ::computeBBox<tpixel32, uchar="">(ras32, bbox);</tpixel32,>
Shinya Kitaoka 120a6e
    return;
Shinya Kitaoka 120a6e
  }
Shinya Kitaoka 120a6e
Shinya Kitaoka 120a6e
  TRaster64P ras64 = ras;
Shinya Kitaoka 120a6e
  if (ras64) {
Shinya Kitaoka 120a6e
    ::computeBBox<tpixel64, ushort="">(ras64, bbox);</tpixel64,>
Shinya Kitaoka 120a6e
    return;
Shinya Kitaoka 120a6e
  }
Shinya Kitaoka 120a6e
Shinya Kitaoka 120a6e
  TRasterCM32P rasCM32 = ras;
Shinya Kitaoka 120a6e
  if (rasCM32) {
Shinya Kitaoka 120a6e
    computeBBoxCM32(rasCM32, bbox);
Shinya Kitaoka 120a6e
    return;
Shinya Kitaoka 120a6e
  }
Shinya Kitaoka 120a6e
Shinya Kitaoka 120a6e
  TRasterGR8P ras8 = ras;
Shinya Kitaoka 120a6e
  if (ras8) {
Shinya Kitaoka 120a6e
    bbox = ras->getBounds();
Shinya Kitaoka 120a6e
    return;
Shinya Kitaoka 120a6e
  }
Shinya Kitaoka 120a6e
  assert(0);
Toshihiro Shimizu 890ddd
}