Package net.sourceforge.jiu.geometry

Source Code of net.sourceforge.jiu.geometry.Crop

/*
* Crop
*
* Copyright (c) 2001, 2002, 2003 Marco Schmidt.
* All rights reserved.
*/

package net.sourceforge.jiu.geometry;

import net.sourceforge.jiu.data.PixelImage;
import net.sourceforge.jiu.data.IntegerImage;
import net.sourceforge.jiu.ops.ImageToImageOperation;
import net.sourceforge.jiu.ops.MissingParameterException;
import net.sourceforge.jiu.ops.WrongParameterException;

/**
* Copies a rectangular area of one image to another image that is exactly as large
* as that rectangular area.
* Works with all image data classes implementing {@link net.sourceforge.jiu.data.IntegerImage}.
* <em>Make sure to use zero-based parameters when defining the bounds with
* {@link #setBounds}!</em>
* <h3>Usage example</h3>
* In this example we assume that the input image is larger than 20 pixels in both directions.
* Ten pixels will be removed from any of its four borders.
* <pre>
* PixelImage image = ...; // something implementing IntegerImage
* Crop crop = new Crop();
* crop.setInputImage(image);
* crop.setBounds(10, 10, image.getWidth() - 9, image.getHeight() - 9);
* crop.process();
* PixelImage croppedImage = crop.getOutputImage();
* </pre>
* @author Marco Schmidt
*/
public class Crop extends ImageToImageOperation
{
  private int x1;
  private int y1;
  private int x2;
  private int y2;

  private void checkBounds() throws WrongParameterException
  {
    PixelImage in = getInputImage();
    if (x1 >= in.getWidth())
    {
      throw new WrongParameterException("x1 must be smaller than input image width.");
    }
    if (x2 >= in.getWidth())
    {
      throw new WrongParameterException("x2 must be smaller than input image width.");
    }
    if (y1 >= in.getHeight())
    {
      throw new WrongParameterException("y1 must be smaller than input image height.");
    }
    if (y2 >= in.getHeight())
    {
      throw new WrongParameterException("y2 must be smaller than input image height.");
    }
  }

  private void process(IntegerImage in, IntegerImage out)
  {
    final int OUT_WIDTH = x2 - x1 + 1;
    final int OUT_HEIGHT = y2 - y1 + 1;
    if (out == null)
    {
      out = (IntegerImage)in.createCompatibleImage(OUT_WIDTH, OUT_HEIGHT);
      setOutputImage(out);
    }
    int totalItems = in.getNumChannels() * OUT_HEIGHT;
    int processedItems = 0;
    for (int c = 0; c < in.getNumChannels(); c++)
    {
      for (int yfrom = y1, yto = 0; yto < OUT_HEIGHT; yfrom++, yto++)
      {
        for (int xfrom = x1, xto = 0; xto < OUT_WIDTH; xfrom++, xto++)
        {
          out.putSample(c, xto, yto, in.getSample(c, xfrom, yfrom));
        }
        setProgress(processedItems++, totalItems);
      }
    }
  }

  public void process() throws
    MissingParameterException,
    WrongParameterException
  {
    ensureInputImageIsAvailable();
    checkBounds();
    ensureOutputImageResolution(x2 - x1 + 1, y2 - y1 + 1);
    if (getInputImage() instanceof IntegerImage)
    {
      process((IntegerImage)getInputImage(), (IntegerImage)getOutputImage());
    }
    else
    {
      throw new WrongParameterException("Input image must implement IntegerImage.");
    }
  }

  /**
   * Specify the rectangular section of the original image that is to be
   * copied to the output image by this operation.
   * Note that the arguments are not checked directly against any input image that may have
   * been provided to this Crop object, that checking is done later in {@link #process()}.
   * If any of the arguments provided here are outside of the input image's resolution
   * (e.g. x1 == 100 although the input image's width is only 60), a
   * {@link net.sourceforge.jiu.ops.WrongParameterException} will be thrown from
   * within {@link #process()}.
   * <p>
   * Note that the arguments to this method are zero-based, so the first column and row
   * are 0, the second 1, the third 2, and so on.
   * If you have a image that is 200 pixels wide and 100 pixels high,
   * values from 0 to 199 are valid for the x arguments, and values from 0 to 99 are valid
   * for the vertical direction.
   * @param x1 horizontal position of upper left corner of the rectangle
   * @param y1 vertical position of upper left corner of the rectangle
   * @param x2 horizontal position of lower right corner of the rectangle
   * @param y2 vertical position of lower right corner of the rectangle
   * @throws IllegalArgumentException if any of the arguments is negative or x1 larger than x2 or y1 larger than y2
   */
  public void setBounds(int x1, int y1, int x2, int y2) throws IllegalArgumentException
  {
    if (x1 < 0)
    {
      throw new IllegalArgumentException("x1 must not be negative.");
    }
    if (y1 < 0)
    {
      throw new IllegalArgumentException("y1 must not be negative.");
    }
    if (x2 < 0)
    {
      throw new IllegalArgumentException("x2 must not be negative.");
    }
    if (y2 < 0)
    {
      throw new IllegalArgumentException("y2 must not be negative.");
    }
    if (x1 > x2)
    {
      throw new IllegalArgumentException("x1 must not be larger than x2.");
    }
    if (y1 > y2)
    {
      throw new IllegalArgumentException("y1 must not be larger than y2.");
    }
    this.x1 = x1;
    this.y1 = y1;
    this.x2 = x2;
    this.y2 = y2;
  }
}
TOP

Related Classes of net.sourceforge.jiu.geometry.Crop

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.