void ofPixels_<PixelType>::set(int channel,PixelType val){
	switch(pixelFormat){
		case OF_PIXELS_RGB:
		case OF_PIXELS_BGR:
		case OF_PIXELS_RGBA:
		case OF_PIXELS_BGRA:
		case OF_PIXELS_GRAY:
		case OF_PIXELS_GRAY_ALPHA:{
			Pixels pixels = getPixelsIter();
			Pixel _end = pixels.end();
			for(Pixel pixel=pixels.begin();pixel!=_end;pixel++){
				pixel[channel] = val;
			}
		}
		break;
		case OF_PIXELS_RGB565:
		case OF_PIXELS_NV12:
		case OF_PIXELS_NV21:
		case OF_PIXELS_YV12:
		case OF_PIXELS_I420:
		case OF_PIXELS_YUY2:
		case OF_PIXELS_UYVY:
		case OF_PIXELS_Y:
		case OF_PIXELS_U:
		case OF_PIXELS_V:
		case OF_PIXELS_UV:
		case OF_PIXELS_VU:
		case OF_PIXELS_UNKNOWN:
		default:
			ofLogWarning() << "setting channels not supported for " << ofToString(pixelFormat) << " format";
			break;
	}
}
void Image_VGA_Planar::convert(const Pixels& newContent,
	const Pixels& newMask)
{
	auto dims = this->dimensions();
	unsigned long dataSize = dims.x * dims.y;

	stream::pos len = this->content->size();

	// Cut off any leftover data or resize so there's enough space
	if (dataSize + this->off != len) {
		this->content->truncate(dataSize + this->off);
	} // else size didn't need to change, e.g. fixed-size VGA image

	Pixels pix;
	pix.resize(dataSize, 0);

	// Convert the linear data to planar
	unsigned int planeWidth = dims.x / 4;
	unsigned int planeSize = planeWidth * dims.y;
	for (unsigned int i = 0; i < dataSize; i++) {
		pix[i] = newContent[i % planeSize * 4 + i / planeSize];
	}

	this->content->seekp(this->off, stream::start);
	this->content->write(pix.data(), dataSize);

	return;
}
void ofPixels_<PixelType>::swapRgb(){
	switch(pixelFormat){
	case OF_PIXELS_RGB:
	case OF_PIXELS_BGR:
	case OF_PIXELS_RGBA:
	case OF_PIXELS_BGRA:{
		Pixels pixels = getPixelsIter();
		Pixel _end = pixels.end();
		for(Pixel pixel=pixels.begin();pixel!=_end;pixel++){
			std::swap(pixel[0],pixel[2]);
		}
	}
	break;
	default:
		ofLogWarning("ofPixels") << "rgb swap not supported for this pixel format";
		break;
	}
	switch(pixelFormat){
	case OF_PIXELS_RGB:
		pixelFormat = OF_PIXELS_BGR;
		break;
	case OF_PIXELS_BGR:
		pixelFormat = OF_PIXELS_RGB;
		break;
	case OF_PIXELS_RGBA:
		pixelFormat = OF_PIXELS_BGRA;
		break;
	case OF_PIXELS_BGRA:
		pixelFormat = OF_PIXELS_RGBA;
		break;
	default:
		break;
	}
}
Pixels Image_SW93Beta_BG_Planar::convert_mask() const
{
	int dataSize = SWBGP_WIDTH * SWBGP_HEIGHT * 4;

	// Return an entirely opaque mask
	Pixels pix;
	pix.resize(dataSize, 0);
	return pix;
}
Pixels Image_VGA_Planar::convert_mask() const
{
	auto dims = this->dimensions();
	int dataSize = dims.x * dims.y;

	// Return an entirely opaque mask
	Pixels pix;
	pix.resize(dataSize, 0);
	return pix;
}
bool GridHealerAbstractBase::pointsAreGood (const QImage &image,
                                            int x0,
                                            int y0,
                                            int x1,
                                            int y1) const
{
  Pixels pixels;

  int stopCountAt = pixelCountInRegionThreshold (m_modelGridRemoval);

  // Skip if either endpoint is an unwanted artifact. Look at start point below (since it is connected
  // to the end point below), and the start point above (which is connected to the end point above)
  return ((pixels.countBlackPixelsAroundPoint (image, x0, y0, stopCountAt) >= stopCountAt) &&
          (pixels.countBlackPixelsAroundPoint (image, x1, y1, stopCountAt) >= stopCountAt));
}
Beispiel #7
0
SplineFunction::SplineFunction(Pixels& pixels, int direction, int i) :
    pixels(pixels)
{
    // si es vertical, las columnas serian las filas de la imagen
    cols = direction == HORIZONTAL ? pixels[0].size() : pixels.size(); // saco los bordes
    if(cols % 2 == 0) {
        points_count = cols/2;
    } else {
        points_count = cols/2 - (i+1)%2; // si la fila es par hay un pixel verde menos
    }

    splines_count = points_count-1;

    h = 2;

    c_matrix = new vector<vector<double>>(points_count, vector<double>(points_count));
    v = new vector<double>(points_count);
    a.resize(points_count);
    b.resize(points_count);
    c.resize(points_count);
    d.resize(points_count);
    if(direction == HORIZONTAL) DoHorizontal(i);
    else DoVertical(i);
    delete(c_matrix);
    delete(v);
}
Beispiel #8
0
void nearestNeighbour(Pixels &pixels, int channel) {
    for(int i=1; i<pixels.size(); i++) {
        for(int j=1; j<pixels[i].size(); j++) {
            if(i%2 == 0) {
                if(j%2 == 0) {
                    if(channel == RED) {
                        pixels[i][j].setChannelWithPixel(channel, pixels[i-1][j-1]);
                    } else if(channel == GREEN) {
                        pixels[i][j].setChannelWithPixel(channel, pixels[i-1][j]);
                    }
                } else {
                    if(channel == RED) {
                        pixels[i][j].setChannelWithPixel(channel, pixels[i-1][j]);
                    } else if(channel == BLUE) {
                        pixels[i][j].setChannelWithPixel(channel, pixels[i][j-1]);
                    }
                }
            } else {
                if(j%2 == 0) {
                    if(channel == RED) {
                        pixels[i][j].setChannelWithPixel(channel, pixels[i][j-1]);
                    } else if(channel == BLUE) {
                        pixels[i][j].setChannelWithPixel(channel, pixels[i-1][j]);
                    }
                } else {
                    if(channel == BLUE) {
                        pixels[i][j].setChannelWithPixel(channel, pixels[i-1][j-1]);
                    } else if(channel == GREEN) {
                        pixels[i][j].setChannelWithPixel(channel, pixels[i-1][j]);
                    }
                }
            }
        }
    }
}
void InnerGlowStyle::operator() (Pixels destPixels, Pixels maskPixels)
{
  if (!active)
    return;

  SharedTable <Colour> table;
  
  if (reverse)
    table = colours.withReversedStops().createLookupTable ();
  else
    table = colours.createLookupTable ();

#if 1
  // Anti-Aliased
  //
  DistanceTransform::Meijster::calculateAntiAliased (
    RenderPixelAntiAliased (
      destPixels,
      opacity,
      choke,
      size,
      table),
    GetMask (maskPixels),
    maskPixels.getWidth (),
    maskPixels.getHeight (),
    DistanceTransform::Meijster::EuclideanMetric ());
#else
  // Regular
  //
  DistanceTransform::Meijster::calculate (
    RenderPixel (
      destPixels,
      opacity,
      choke,
      size,
      table),
    TestMask (maskPixels),
    maskPixels.getWidth (),
    maskPixels.getHeight (),
    DistanceTransform::Meijster::EuclideanMetric ());
#endif
}
Beispiel #10
0
void directional_interpolation(Pixels& pixels)
{
    int rows = pixels.size();
    int cols = pixels[0].size();
    vector<SplineFunction*> horizontal_splines(rows);
    vector<SplineFunction*> vertical_splines(cols);

    horizontal_splines[0] = NULL;
    for(int i = 1; i < rows-1; i++)
    {
        horizontal_splines[i] = new SplineFunction(pixels, HORIZONTAL, i);
    }
    horizontal_splines[rows-1] = NULL;

    vertical_splines[0] = NULL;
    for(int i = 1; i < cols-1; i++)
    {
        vertical_splines[i] = new SplineFunction(pixels, VERTICAL, i);
    }
    vertical_splines[cols-1] = NULL;

    for(int i = 1; i < rows-1; i++)
    {
        for(int j = 1; j < cols-1; j++)
        {
            if((i % 2 == 0 && j % 2 == 1) || (i % 2 == 1 && j % 2 == 0)) continue;  // avoid green locations

            double gradient_v = (i >=2 && i <= rows-3) ? abs(pixels[i+2][j].green - pixels[i-2][j].green) : 0;
            double gradient_h = (j >=2 && j <= cols-3) ? abs(pixels[i][j+2].green - pixels[i][j-2].green) : 0;
            double value_v = vertical_splines[j]->eval(i);
            double value_h = horizontal_splines[i]->eval(j);

            double avg;
            if(gradient_h == gradient_v)
                avg = (value_h + value_v)/2;
            else {
                avg = value_h * (gradient_v / (gradient_h + gradient_v))
                       + value_v * (gradient_h / (gradient_h + gradient_v));
            }
            pixels[i][j].green = MAX(0, MIN(255, round(avg)));
        }
        delete horizontal_splines[i];
    }

    for(int i = 1; i < cols-1; i++)
    {
        delete vertical_splines[i];
    }
}
Beispiel #11
0
void bilinear(Pixels &pixels, int channel) {
    int color;
    for(int i=1; i<pixels.size()-1; i++) {
        for(int j=1; j<pixels[i].size()-1; j++) {
            if(i%2 == 0) {
                if(j%2 == 0) {
                    if(channel == RED) {
                        color = (pixels[i-1][j-1].getChannel(channel) + pixels[i-1][j+1].getChannel(channel) +
                            pixels[i+1][j-1].getChannel(channel) + pixels[i+1][j+1].getChannel(channel)) / 4;
                        pixels[i][j].setChannelWithColor(channel, color);
                    } else if(channel == GREEN) {
                        color = (pixels[i-1][j].getChannel(channel) + pixels[i][j-1].getChannel(channel) +
                            pixels[i][j+1].getChannel(channel) + pixels[i+1][j].getChannel(channel)) / 4;
                        pixels[i][j].setChannelWithColor(channel, color);
                    }
                } else {
                    if(channel == RED) {
                        color = (pixels[i-1][j].getChannel(channel) + pixels[i+1][j].getChannel(channel)) / 2;
                        pixels[i][j].setChannelWithColor(channel, color);
                    } else if(channel == BLUE) {
                        color = (pixels[i][j-1].getChannel(channel) + pixels[i][j+1].getChannel(channel)) / 2;
                        pixels[i][j].setChannelWithColor(channel, color);
                    }
                }
            } else {
                if(j%2 == 0) {
                    if(channel == RED) {
                        color = (pixels[i][j-1].getChannel(channel) + pixels[i][j+1].getChannel(channel)) / 2;
                        pixels[i][j].setChannelWithColor(channel, color);
                    } else if(channel == BLUE) {
                        color = (pixels[i-1][j].getChannel(channel) + pixels[i+1][j].getChannel(channel)) / 2;
                        pixels[i][j].setChannelWithColor(channel, color);
                    }
                } else {
                    if(channel == BLUE) {
                        color = (pixels[i-1][j-1].getChannel(channel) + pixels[i-1][j+1].getChannel(channel) +
                            pixels[i+1][j-1].getChannel(channel) + pixels[i+1][j+1].getChannel(channel)) / 4;
                        pixels[i][j].setChannelWithColor(channel, color);
                    } else if(channel == GREEN) {
                        color = (pixels[i-1][j].getChannel(channel) + pixels[i][j-1].getChannel(channel) +
                            pixels[i][j+1].getChannel(channel) + pixels[i+1][j].getChannel(channel)) / 4;
                        pixels[i][j].setChannelWithColor(channel, color);
                    }
                }
            }
        }
    }
}
Beispiel #12
0
void MHC(Pixels& pixels)   // only supports green channel
{
    int color, rhombus_sum;
    double gradient;
    bilinear(pixels, GREEN);  // se arranca con la bilinear
    for(int i=2; i<pixels.size()-2; i++) {
        for(int j=2; j<pixels[i].size()-2; j++) {
            if((i % 2 == 0 && j % 2 == 1) || (i % 2 == 1 && j % 2 == 0)) continue;  //  green locations

            color = i % 2 == 0 ? BLUE : RED;

            rhombus_sum = 0;
            rhombus_sum += pixels[i][j-2].getChannel(color);
            rhombus_sum += pixels[i][j+2].getChannel(color);
            rhombus_sum += pixels[i-2][j].getChannel(color);
            rhombus_sum += pixels[i+2][j].getChannel(color);
            gradient = pixels[i][j].getChannel(color) - rhombus_sum / 4.0;
            pixels[i][j].green += int(ALPHA * gradient);
            pixels[i][j].green = MAX(0, MIN(255, pixels[i][j].green));
        }
    }
}
Beispiel #13
0
void ofPixels_<PixelType>::setColor(const ofColor_<PixelType>& color) {
	switch(pixelFormat){
		case OF_PIXELS_RGB:{
			Pixels pixels = getPixelsIter();
			Pixel _end = pixels.end();
			for(Pixel pixel=pixels.begin();pixel!=_end;pixel++){
				pixel[0] = color.r;
				pixel[1] = color.g;
				pixel[2] = color.b;
			}
		}
		break;
		case OF_PIXELS_BGR:{
			Pixels pixels = getPixelsIter();
			Pixel _end = pixels.end();
			for(Pixel pixel=pixels.begin();pixel!=_end;pixel++){
				pixel[0] = color.b;
				pixel[1] = color.g;
				pixel[2] = color.r;
			}
		}
		break;
		case OF_PIXELS_RGBA:{
			Pixels pixels = getPixelsIter();
			Pixel _end = pixels.end();
			for(Pixel pixel=pixels.begin();pixel!=_end;pixel++){
				pixel[0] = color.r;
				pixel[1] = color.g;
				pixel[2] = color.b;
				pixel[3] = color.a;
			}
		}
		break;
		case OF_PIXELS_BGRA:{
			Pixels pixels = getPixelsIter();
			Pixel _end = pixels.end();
			for(Pixel pixel=pixels.begin();pixel!=_end;pixel++){
				pixel[0] = color.b;
				pixel[1] = color.g;
				pixel[2] = color.r;
				pixel[3] = color.a;
			}
		}
		break;
		case OF_PIXELS_GRAY:{
			PixelType b = color.getBrightness();
			for(iterator i=begin();i!=end();++i){
				*i = b;
			}
		}
		break;
		case OF_PIXELS_GRAY_ALPHA:{
			PixelType b = color.getBrightness();
			Pixels pixels = getPixelsIter();
			Pixel _end = pixels.end();
			for(Pixel pixel=pixels.begin();pixel!=_end;pixel++){
				pixel[0] = b;
				pixel[1] = color.a;
			}
		}
		break;
		case OF_PIXELS_RGB565:
		case OF_PIXELS_NV12:
		case OF_PIXELS_NV21:
		case OF_PIXELS_YV12:
		case OF_PIXELS_I420:
		case OF_PIXELS_YUY2:
		case OF_PIXELS_UYVY:
		case OF_PIXELS_Y:
		case OF_PIXELS_U:
		case OF_PIXELS_V:
		case OF_PIXELS_UV:
		case OF_PIXELS_VU:
		case OF_PIXELS_UNKNOWN:
		default:
			ofLogWarning("ofPixels") << "setting color not supported yet for " << ofToString(pixelFormat) << " format";
		break;
	}
}
Beispiel #14
0
int main(int argc, char* argv[]) {
    if(argc < 3) {
        cout << "Uso: ./main <archivo de entrada> <archivo de salida>" << endl;
        return 0;
    }
    int metodo = 1;
    if(argc > 3) {
        metodo = int(atoi(argv[3]));
    }
    std::ifstream inputFile(argv[1]);

    int rows, cols;
    inputFile >> cols >> rows;

    Pixels pixels;
    uint color;
    pixels.resize(rows);
    for(int i=0; i<rows; i++) {
        pixels[i].resize(cols);
        for(int j=0; j<cols; j++) {
            pixels[i][j].red = pixels[i][j].green = pixels[i][j].blue = 0;

            inputFile >> color;
            if(i%2 == 0) {
                if(j%2 == 0) {
                    pixels[i][j].blue = color;
                } else {
                    pixels[i][j].green = color;
                }
            } else {
                if(j%2 == 0) {
                    pixels[i][j].green = color;
                } else {
                    pixels[i][j].red = color;
                }
            }
        }
    }

    inputFile.close();

    if(metodo == 1) {
        nearestNeighbour(pixels, RED);
        nearestNeighbour(pixels, GREEN);
        nearestNeighbour(pixels, BLUE);
    } else if(metodo == 2) {
        bilinear(pixels, RED);
        bilinear(pixels, GREEN);
        bilinear(pixels, BLUE);
    } else if(metodo == 3) {
        bilinear(pixels, RED);
        bilinear(pixels, BLUE);
        directional_interpolation(pixels);
    } else if(metodo == 4) {
        bilinear(pixels, RED);
        bilinear(pixels, BLUE);
        MHC(pixels);
    } else {
        nearestNeighbour(pixels, RED);
        nearestNeighbour(pixels, GREEN);
        nearestNeighbour(pixels, BLUE);
    }


    std::ofstream outputFile(argv[2]);
    outputFile << cols << " " << rows << endl;
    for(int i=0; i<rows; i++) {
        for(int j=0; j<cols; j++) {
            outputFile << pixels[i][j].red << " " << pixels[i][j].green << " " << pixels[i][j].blue << endl;
        }
    }

    outputFile.close();

    return 0;
}
Beispiel #15
0
void StrokeStyle::operator () (Pixels destPixels, Pixels maskPixels)
{
  if (!active)
    return;

  if (type != typeGradient)// || gradient.style != GradientFill::styleShapeBurst)
  {
    //
    // Calculate mask using distance transform
    //

    Image matteImage (
      Image::SingleChannel,
      maskPixels.getBounds ().getWidth (),
      maskPixels.getBounds ().getHeight (),
      false);

    Pixels mattePixels (matteImage);

    switch (pos)
    {
    case posInner:
      DistanceTransform::Meijster::calculateAntiAliased (
        RenderMask (Pixels::Map2D (mattePixels), size),
        Inside (maskPixels),
        maskPixels.getWidth (),
        maskPixels.getHeight (),
        DistanceTransform::Meijster::EuclideanMetric ());
      break;

    case posOuter:
      DistanceTransform::Meijster::calculateAntiAliased (
        RenderMask (Pixels::Map2D (mattePixels), size),
        Outside (maskPixels),
        maskPixels.getWidth (),
        maskPixels.getHeight (),
        DistanceTransform::Meijster::EuclideanMetric ());
      break;

    case posCentre:
      break;

    default:
      jassertfalse;
      break;
    };

    //
    // Apply fill using mask
    //

    switch (type)
    {
    case typeColour:
      BlendMode::apply (
        mode,
        Pixels::Iterate2 (destPixels, mattePixels),
        BlendProc::RGB::MaskFill (colour, opacity));
      break;

    case typeGradient:
      break;

    case typePattern:
      break;

    default:
      jassertfalse;
      break;
    };
  }
  else
  {
    //
    // Special case for shape burst gradients
    //
    SharedTable <Colour> colourTable = gradient.colours.createLookupTable ();

    switch (pos)
    {
    case posInner:
      {
        DistanceTransform::Meijster::calculateAntiAliased (
          RenderShapeBurst (Pixels::Map2D (destPixels), size, colourTable),
          Inside (maskPixels),
          maskPixels.getWidth (),
          maskPixels.getHeight (),
          DistanceTransform::Meijster::EuclideanMetric ());
      }
      break;

    case posOuter:
      {
        DistanceTransform::Meijster::calculateAntiAliased (
          RenderShapeBurst (Pixels::Map2D (destPixels), size, colourTable),
          Outside (maskPixels),
          maskPixels.getWidth (),
          maskPixels.getHeight (),
          DistanceTransform::Meijster::EuclideanMetric ());
      }
      break;

    case posCentre:
      {
      }
      break;

    default:
      jassertfalse;
      break;
    };
  }
}
Beispiel #16
0
void BevelEmbossStyle::operator() (Pixels destPixels, Pixels maskPixels)
{
    jassert (destPixels.isRGB ());
    jassert (maskPixels.getBounds () == destPixels.getBounds ());

    if (!active)
        return;

    // Calculate the distance transform on the mask.
    //
    typedef double T;
    Map2D <T> distMap (maskPixels.getWidth (), maskPixels.getHeight ());
    switch (kind)
    {
    case kindOuterBevel:
#if 1
        DistanceTransform::Meijster::calculateAntiAliased (
            AntiAliased::Output <Map2D <T> > (distMap, size),
            AntiAliased::GetMaskOuter (maskPixels),
            maskPixels.getWidth (),
            maskPixels.getHeight (),
            DistanceTransform::Meijster::EuclideanMetric ());
#else
        DistanceTransform::Meijster::calculate (
            Normal::OutputOuter <Map2D <T> > (distMap, size),
            Normal::GetOuter (maskPixels),
            maskPixels.getWidth (),
            maskPixels.getHeight (),
            DistanceTransform::Meijster::EuclideanMetric ());
#endif
        break;

    case kindInnerBevel:
#if 1
        DistanceTransform::Meijster::calculateAntiAliased (
            AntiAliased::Output <Map2D <T> > (distMap, size),
            AntiAliased::GetMaskInner (maskPixels),
            maskPixels.getWidth (),
            maskPixels.getHeight (),
            DistanceTransform::Meijster::EuclideanMetric ());
#else
        DistanceTransform::Meijster::calculate (
            Normal::OutputInner <Map2D <T> > (distMap, size),
            Normal::GetInner (maskPixels),
            maskPixels.getWidth (),
            maskPixels.getHeight (),
            DistanceTransform::Meijster::EuclideanMetric ());
#endif
        break;

    case kindEmboss:
    case kindPillowEmboss:
    case kindStrokeEmboss:
    default:
        jassertfalse;
        break;
    }

#if 0
    {
        for (int y = 0; y < destPixels.getWidth (); ++y)
        {
            for (int x = 0; x < destPixels.getHeight (); ++x)
            {
                PixelRGB& dest (*((PixelRGB*)destPixels.getPixelPointer (x, y)));

                T t = distMap (x, y) * 255 / size;
                uint8 v = uint8 (t + 0.5);

                dest.getRed () = v;
                dest.getGreen () = v;
                dest.getBlue () = v;
            }
        }
    }
#else
    // Apply a softening to the transform.
    //
#if 0
    if (technique == techniqueChiselSoft)
    {
        if (soften > 0)
        {
            RadialImageConvolutionKernel k (soften + 1);
            k.createGaussianBlur ();
            distImage = k.createConvolvedImage (distImage);
            distPixels = Pixels (distImage);
        }
    }
#endif

    Image hiImage (
        Image::SingleChannel,
        destPixels.getCols (),
        destPixels.getRows (),
        true);

    Image loImage (
        Image::SingleChannel,
        destPixels.getCols (),
        destPixels.getRows (),
        true);

    Pixels hiPixels (hiImage);
    Pixels loPixels (loImage);

    LightingTransform::calculate <T> (
        LightingTransform::PixelShader (hiPixels, loPixels),
        distMap,
        10 - depth,
        lightAngle,
        lightElevation);

    // Apply a softening to the masks.
    //
#if 0
    if (technique == techniqueSmooth)
    {
        if (soften > 0)
        {
            RadialImageConvolutionKernel k (soften + 1);
            k.createGaussianBlur ();

            hiImage = k.createConvolvedImage (hiImage);
            hiPixels = Pixels (hiImage);

            loImage = k.createConvolvedImage (loImage);
            loPixels = Pixels (loImage);

            Pixels::Iterate2 (hiPixels, maskPixels) (BlendProc::Gray::CopyMode <BlendMode::multiply> ());
            Pixels::Iterate2 (loPixels, maskPixels) (BlendProc::Gray::CopyMode <BlendMode::multiply> ());
        }
    }
#endif

    // Render highlights.
    //
    BlendMode::apply (
        hilightMode,
        Pixels::Iterate2 (destPixels, hiPixels),
        BlendProc::RGB::MaskFill (hilightColour, hilightOpacity));

    // Render shadows.
    //
    BlendMode::apply (
        shadowMode,
        Pixels::Iterate2 (destPixels, loPixels),
        BlendProc::RGB::MaskFill (shadowColour, shadowOpacity));
#endif
}
Beispiel #17
0
void OuterGlowStyle::operator() (Pixels destPixels, Pixels stencilPixels)
{
  if (!active)
    return;

  //int const width = stencilPixels.getWidth ();
  //int const height = stencilPixels.getHeight ();

  SharedTable <Colour> table = colours.createLookupTable ();

  Map2D <int> dist (stencilPixels.getWidth (), stencilPixels.getHeight ());
  Map2D <int> temp (stencilPixels.getWidth (), stencilPixels.getHeight ());

  if (precise)
  {
    LayerStyles::DistanceMap () (
      Pixels::Map2D (stencilPixels),
      temp,
      stencilPixels.getWidth (),
      stencilPixels.getHeight (),
      size);

  #if 0
    DistanceTransform::Meijster::calculateAntiAliased (
      RenderPixelAntiAliased (
        destPixels,
        opacity,
        spread,
        size,
        table),
      GetMask (stencilPixels),
      stencilPixels.getWidth (),
      stencilPixels.getHeight (),
      DistanceTransform::Meijster::EuclideanMetric ());
  #endif
    for (int y = 0; y < temp.getRows (); ++y)
    {
      for (int x = 0; x < temp.getCols (); ++x)
      {
        int const v = temp (x, y);
        if (v > 0)
          temp (x, y) = (255 - v) * 256;
      }
    }
  }
  else
  {
    // "Softer"

    LayerStyles::BoxBlurAndDilateSettings bd (size, spread);

    LayerStyles::GrayscaleDilation () (
      Pixels::Map2D (stencilPixels),
      stencilPixels.getWidth (),
      stencilPixels.getHeight (),
      dist,
      stencilPixels.getWidth (),
      stencilPixels.getHeight (),
      0,
      0,
      bd.getDilatePixels ());

    BoxBlur () (dist, temp, temp.getCols (), temp.getRows (), bd.getBoxBlurRadius ());
  }

  // Fill
  //
  PixelARGB c (0);
  for (int y = 0; y < temp.getRows (); ++y)
  {
    for (int x = 0; x < temp.getCols (); ++x)
    {
      int const v = (temp (x, y) + 128) / 256;

      PixelRGB& dest (*((PixelRGB*)destPixels.getPixelPointer (x, y)));

      c.setAlpha (uint8(v));
      dest.blend (c);
    }
  }
}
Beispiel #18
0
std::list<FormImage> extract(const std::string& filename, Form& form)
{
    std::list<FormImage> images;
    ColorSpace colorspace;
    PoDoFo::pdf_int64 componentbits;
    PoDoFo::PdfObject* obj = nullptr;
    PoDoFo::PdfObject* color = nullptr;
    PoDoFo::PdfObject* component = nullptr;
    PoDoFo::PdfMemDocument document(filename.c_str());
    PoDoFo::TCIVecObjects it = document.GetObjects().begin();

    while (it != document.GetObjects().end())
    {
        if ((*it)->IsDictionary())
        {
            PoDoFo::PdfObject* objType = (*it)->GetDictionary().GetKey(PoDoFo::PdfName::KeyType);
            PoDoFo::PdfObject* objSubType = (*it)->GetDictionary().GetKey(PoDoFo::PdfName::KeySubtype);

            if ((objType    && objType->IsName()    && objType->GetName().GetName() == "XObject") ||
                (objSubType && objSubType->IsName() && objSubType->GetName().GetName() == "Image" ))
            {
                // Colorspace
                color = (*it)->GetDictionary().GetKey(PoDoFo::PdfName("ColorSpace"));
                colorspace = ColorSpace::Unknown;

                if (color && color->IsReference())
                    color = document.GetObjects().GetObject(color->GetReference());

                // Follow ICCBased reference to the Alternate colorspace
                if (color && color->IsArray() && color->GetArray().GetSize() == 2 &&
                        // First item is ICCBased
                        color->GetArray()[0].IsName() &&
                        color->GetArray()[0].GetName().GetName() == "ICCBased" &&
                        // Second item is reference to color space
                        color->GetArray()[1].IsReference())
                {
                    color = document.GetObjects().GetObject(color->GetArray()[1].GetReference());

                    if (color)
                        color = color->GetDictionary().GetKey(PoDoFo::PdfName("Alternate"));
                }

                // Check if either RGB or Grayscale (either the specified
                // colorspace or the alternate if using an ICCBased colorspace)
                if (color && color->IsName())
                {
                    std::string col = color->GetName().GetName();

                    if (col == "DeviceRGB")
                        colorspace = ColorSpace::RGB;
                    else if (col == "DeviceGray")
                        colorspace = ColorSpace::Gray;
                }

                // Bits per component
                component = (*it)->GetDictionary().GetKey(PoDoFo::PdfName("BitsPerComponent"));
                componentbits = 8;

                if (component && component->IsNumber())
                    componentbits = component->GetNumber();

                // Stream
                obj = (*it)->GetDictionary().GetKey(PoDoFo::PdfName::KeyFilter);

                // JPEG and Flate are in another array
                if (obj && obj->IsArray() && obj->GetArray().GetSize() == 1 &&
                    ((obj->GetArray()[0].IsName() && obj->GetArray()[0].GetName().GetName() == "DCTDecode") ||
                     (obj->GetArray()[0].IsName() && obj->GetArray()[0].GetName().GetName() == "FlateDecode")))
                    obj = &obj->GetArray()[0];

                Pixels pixels;

                if (obj && obj->IsName())
                {
                    std::string name = obj->GetName().GetName();

                    if (name == "DCTDecode")
                        pixels = readPDFImage(*it, PixelType::JPG, colorspace, componentbits, filename, form);
                    else if (name == "CCITTFaxDecode")
                        pixels = readPDFImage(*it, PixelType::TIF, colorspace, componentbits, filename, form);
                    // PNM is the default
                    //else if (name == "FlateDecode")
                    //  pixels = readPDFImage(*it, PixelType::PNM, colorspace, componentbits, filename, form);
                    else
                        pixels = readPDFImage(*it, PixelType::PNM, colorspace, componentbits, filename, form);
                }
                else
                {
                    pixels = readPDFImage(*it, PixelType::PNM, colorspace, componentbits, filename, form);
                }

                document.FreeObjectMemory(*it);

                if (pixels.isLoaded())
                    images.push_back(FormImage(form, std::move(pixels)));
            }
        }

        ++it;
    }

    return images;
}