📄 roiscaler.java
字号:
/* * CVS identifier: * * $Id: ROIScaler.java,v 1.8 2001/02/19 11:19:43 grosbois Exp $ * * Class: ROIScaler * * Description: This class takes care of the scaling of the * samples * * * * COPYRIGHT: * * This software module was originally developed by Rapha雔 Grosbois and * Diego Santa Cruz (Swiss Federal Institute of Technology-EPFL); Joel * Askel鰂 (Ericsson Radio Systems AB); and Bertrand Berthelot, David * Bouchard, F閘ix Henry, Gerard Mozelle and Patrice Onno (Canon Research * Centre France S.A) in the course of development of the JPEG2000 * standard as specified by ISO/IEC 15444 (JPEG 2000 Standard). This * software module is an implementation of a part of the JPEG 2000 * Standard. Swiss Federal Institute of Technology-EPFL, Ericsson Radio * Systems AB and Canon Research Centre France S.A (collectively JJ2000 * Partners) agree not to assert against ISO/IEC and users of the JPEG * 2000 Standard (Users) any of their rights under the copyright, not * including other intellectual property rights, for this software module * with respect to the usage by ISO/IEC and Users of this software module * or modifications thereof for use in hardware or software products * claiming conformance to the JPEG 2000 Standard. Those intending to use * this software module in hardware or software products are advised that * their use may infringe existing patents. The original developers of * this software module, JJ2000 Partners and ISO/IEC assume no liability * for use of this software module or modifications thereof. No license * or right to this software module is granted for non JPEG 2000 Standard * conforming products. JJ2000 Partners have full right to use this * software module for his/her own purpose, assign or donate this * software module to any third party and to inhibit third parties from * using this software module for non JPEG 2000 Standard conforming * products. This copyright notice must be included in all copies or * derivative works of this software module. * * Copyright (c) 1999/2000 JJ2000 Partners. * */package jj2000.j2k.roi.encoder;import jj2000.j2k.quantization.quantizer.*;import jj2000.j2k.codestream.writer.*;import jj2000.j2k.wavelet.analysis.*;import jj2000.j2k.quantization.*;import jj2000.j2k.image.input.*;import jj2000.j2k.wavelet.*;import jj2000.j2k.encoder.*;import jj2000.j2k.image.*;import jj2000.j2k.util.*;import jj2000.j2k.roi.*;import jj2000.j2k.*;import java.util.*;import java.io.*;/** * This class deals with the ROI functionality. * * <p>The ROI method is the Maxshift method. The ROIScaler works by scaling * the quantized wavelet coefficients that do not affect the ROI (i.e * background coefficients) so that these samples get a lower significance * than the ROI ones. By scaling the coefficients sufficiently, the ROI * coefficients can be recognized by their amplitude alone and no ROI mask * needs to be generated at the decoder side. * * <p>The source module must be a quantizer and code-block's data is exchange * with thanks to CBlkWTData instances. * * @see Quantizer * @see CBlkWTData * */public class ROIScaler extends ImgDataAdapter implements CBlkQuantDataSrcEnc { /** The prefix for ROI Scaler options: 'R' */ public final static char OPT_PREFIX = 'R'; /** The list of parameters that are accepted for ROI coding. Options * for ROI Scaler start with 'R'. */ private final static String [][] pinfo = { { "Rroi","[<component idx>] R <left> <top> <width> <height>"+ " or [<component idx>] C <centre column> <centre row> "+ "<radius> or [<component idx>] A <filename>", "Specifies ROIs shape and location. The shape can be either "+ "rectangular 'R', or circular 'C' or arbitrary 'A'. "+ "Each new occurrence of an 'R', a 'C' or an 'A' is a new ROI. "+ "For circular and rectangular ROIs, all values are "+ "given as their pixel values relative to the canvas origin. "+ "Arbitrary shapes must be included in a PGM file where non 0 "+ "values correspond to ROI coefficients. The PGM file must have "+ "the size as the image. "+ "The component idx specifies which components "+ "contain the ROI. The component index is specified as described "+ "by points 3 and 4 in the general comment on tile-component idx. "+ "If this option is used, the codestream is layer progressive by "+ "default unless it is overridden by the 'Aptype' option.", null}, { "Ralign","[on|off]", "By specifying this argument, the ROI mask will be "+ "limited to covering only entire code-blocks. The ROI coding can "+ "then be performed without any actual scaling of the coefficients "+ "but by instead scaling the distortion estimates.","off"}, { "Rstart_level","<level>", "This argument forces the lowest <level> resolution levels to "+ "belong to the ROI. By doing this, it is possible to avoid only "+ "getting information for the ROI at an early stage of "+ "transmission.<level> = 0 means the lowest resolution level "+ "belongs to the ROI, 1 means the two lowest etc. (-1 deactivates"+ " the option)","-1"}, { "Rno_rect","[on|off]", "This argument makes sure that the ROI mask generation is not done "+ "using the fast ROI mask generation for rectangular ROIs "+ "regardless of whether the specified ROIs are rectangular or not", "off"}, }; /** The maximum number of magnitude bit-planes in any subband. One value * for each tile-component */ private int maxMagBits[][]; /** Flag indicating the presence of ROIs */ private boolean roi; /** Flag indicating if block aligned ROIs are used */ private boolean blockAligned; /** Number of resolution levels to include in ROI mask */ private int useStartLevel; /** The class generating the ROI mask */ private ROIMaskGenerator mg; /** The ROI mask */ private DataBlkInt roiMask; /** The source of quantized wavelet transform coefficients */ private Quantizer src; /** * Constructor of the ROI scaler, takes a Quantizer as source of data to * scale. * * @param src The quantizer that is the source of data. * * @param mg The mask generator that will be used for all components * * @param roi Flag indicating whether there are rois specified. * * @param sLev The resolution levels that belong entirely to ROI * * @param uba Flag indicating whether block aligning is used. * * @param encSpec The encoder specifications for addition of roi specs * */ public ROIScaler(Quantizer src, ROIMaskGenerator mg, boolean roi, int sLev, boolean uba, EncoderSpecs encSpec){ super(src); this.src = src; this.roi = roi; this.useStartLevel = sLev; if(roi){ // If there is no ROI, no need to do this this.mg = mg; roiMask = new DataBlkInt(); calcMaxMagBits(encSpec); blockAligned = uba; } } /** * Returns the number of code-blocks in a subband, along the horizontal * and vertical dimensions. * * @param sb The subband for which to return the number of blocks. * * @param co If not null the values are returned in this object. If null a * new object is allocated and returned. * * @return The number of code-blocks along the horizontal dimension in * 'Coord.x' and the number of code-blocks along the vertical dimension in * 'Coord.y'. * */ public Coord getNumCodeBlocks(SubbandAn sb, Coord co) { return src.getNumCodeBlocks(sb,co); } /** * Since ROI scaling is always a reversible operation, it calls * isReversible() method of it source (the quantizer module). * * @param t The tile to test for reversibility * * @param c The component to test for reversibility * * @return True if the quantized data is reversible, false if not. * */ public boolean isReversible(int t,int c){ return src.isReversible(t,c); } /** * Returns a reference to the subband tree structure representing the * subband decomposition for the specified tile-component. * * @param t The index of the tile. * * @param c The index of the component. * * @return The subband tree structure, see SubbandAn. * * @see SubbandAn * * @see Subband * */ public SubbandAn getSubbandTree(int t,int c) { return src.getSubbandTree(t,c); } /** * Returns the horizontal coordinate of the origin of the cell and * code-block partition, with respect to the canvas origin, on the * reference grid. Allowable values are 0 and 1, nothing else. * * @return The horizontal coordinate of the origin of the cell and * code-block partitions, with respect to the canvas origin, on the * reference grid. * */ public int getPartitionULX() { return src.getPartitionULX(); } /** * Returns the vertical coordinate of the origin of the cell and * code-block partition, with respect to the canvas origin, on the * reference grid. Allowable values are 0 and 1, nothing else. * * @return The vertical coordinate of the origin of the cell and * code-block partitions, with respect to the canvas origin, on the * reference grid. * */ public int getPartitionULY() { return src.getPartitionULY(); } /** * Creates a ROIScaler object. The Quantizer is the source of data to * scale. * * <P> The ROI Scaler creates a ROIMaskGenerator depending on what ROI * information is in the ParameterList. If only rectangular ROI are used, * the fast mask generator for rectangular ROI can be used. * * @param src The source of data to scale * * @param pl The parameter list (or options). * * @param encSpec The encoder specifications for addition of roi specs * * @exception IllegalArgumentException If an error occurs while parsing * the options in 'pl' * */ public static ROIScaler createInstance(Quantizer src, ParameterList pl, EncoderSpecs encSpec){ Vector roiVector = new Vector(); ROIMaskGenerator maskGen = null; // Check parameters pl.checkList(OPT_PREFIX,pl.toNameArray(pinfo)); // Get parameters and check if there are and ROIs specified String roiopt = pl.getParameter("Rroi"); if (roiopt == null) { // No ROIs specified! Create ROIScaler with no mask generator return new ROIScaler(src,null,false,-1,false,encSpec); } // Check if the lowest resolution levels should belong to the ROI int sLev = pl.getIntParameter("Rstart_level"); // Check if the ROIs are block-aligned boolean useBlockAligned = pl.getBooleanParameter("Ralign"); // Check if generic mask generation is specified boolean onlyRect = !pl.getBooleanParameter("Rno_rect"); // Parse the ROIs parseROIs(roiopt,src.getNumComps(),roiVector); ROI[] roiArray = new ROI[roiVector.size()]; roiVector.copyInto(roiArray); // If onlyRect has been forced, check if there are any non-rectangular // ROIs specified. Currently, only the presence of circular ROIs will // make this false if(onlyRect) { for(int i=roiArray.length-1 ; i>=0 ; i--) if(!roiArray[i].rect){ onlyRect=false; break; } } if(onlyRect){ // It's possible to use the fast ROI mask generation when only // rectangular ROIs are specified. maskGen = new RectROIMaskGenerator(roiArray,src.getNumComps()); } else{ // It's necessary to use the generic mask generation maskGen = new ArbROIMaskGenerator(roiArray,src.getNumComps(),src); } return new ROIScaler(src,maskGen,true,sLev,useBlockAligned,encSpec); } /** * This function parses the values given for the ROIs with the argument * -Rroi. Currently only circular and rectangular ROIs are supported. * * <P> A rectangular ROI is indicated by a 'R' followed the coordinates * for the upper left corner of the ROI and then its width and height. * * <P> A circular ROI is indicated by a 'C' followed by the coordinates of * the circle center and then the radius. * * <P> Before the R and C values, the component that are affected by the * ROI are indicated. * * @param roiopt The info on the ROIs * * @param nc number of components * * @param roiVector The vcector containing the ROI parsed from the cmd line * * @return The ROIs specified in roiopt * */ protected static Vector parseROIs(String roiopt, int nc,Vector roiVector){ ROI[] ROIs; ROI roi; StringTokenizer stok; char tok; int nrOfROIs = 0; char c; int comp,ulx,uly,w,h,x,y,rad; boolean[] roiInComp = null; stok = new StringTokenizer(roiopt); String word; while(stok.hasMoreTokens()){ word = stok.nextToken(); switch(word.charAt(0)){ case 'c': // Components specification roiInComp = ModuleSpec.parseIdx(word,nc); break; case 'R': // Rectangular ROI to be read nrOfROIs++; try{ word = stok.nextToken(); ulx = (new Integer(word)).intValue(); word = stok.nextToken(); uly = (new Integer(word)).intValue(); word = stok.nextToken();
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -