001/* 002 * $RCSfile: J2KImageWriteParam.java,v $ 003 * 004 * 005 * Copyright (c) 2005 Sun Microsystems, Inc. All Rights Reserved. 006 * 007 * Redistribution and use in source and binary forms, with or without 008 * modification, are permitted provided that the following conditions 009 * are met: 010 * 011 * - Redistribution of source code must retain the above copyright 012 * notice, this list of conditions and the following disclaimer. 013 * 014 * - Redistribution in binary form must reproduce the above copyright 015 * notice, this list of conditions and the following disclaimer in 016 * the documentation and/or other materials provided with the 017 * distribution. 018 * 019 * Neither the name of Sun Microsystems, Inc. or the names of 020 * contributors may be used to endorse or promote products derived 021 * from this software without specific prior written permission. 022 * 023 * This software is provided "AS IS," without a warranty of any 024 * kind. ALL EXPRESS OR IMPLIED CONDITIONS, REPRESENTATIONS AND 025 * WARRANTIES, INCLUDING ANY IMPLIED WARRANTY OF MERCHANTABILITY, 026 * FITNESS FOR A PARTICULAR PURPOSE OR NON-INFRINGEMENT, ARE HEREBY 027 * EXCLUDED. SUN MIDROSYSTEMS, INC. ("SUN") AND ITS LICENSORS SHALL 028 * NOT BE LIABLE FOR ANY DAMAGES SUFFERED BY LICENSEE AS A RESULT OF 029 * USING, MODIFYING OR DISTRIBUTING THIS SOFTWARE OR ITS 030 * DERIVATIVES. IN NO EVENT WILL SUN OR ITS LICENSORS BE LIABLE FOR 031 * ANY LOST REVENUE, PROFIT OR DATA, OR FOR DIRECT, INDIRECT, SPECIAL, 032 * CONSEQUENTIAL, INCIDENTAL OR PUNITIVE DAMAGES, HOWEVER CAUSED AND 033 * REGARDLESS OF THE THEORY OF LIABILITY, ARISING OUT OF THE USE OF OR 034 * INABILITY TO USE THIS SOFTWARE, EVEN IF SUN HAS BEEN ADVISED OF THE 035 * POSSIBILITY OF SUCH DAMAGES. 036 * 037 * You acknowledge that this software is not designed or intended for 038 * use in the design, construction, operation or maintenance of any 039 * nuclear facility. 040 * 041 * $Revision: 1.2 $ 042 * $Date: 2006/09/20 23:23:30 $ 043 * $State: Exp $ 044 */ 045package com.github.jaiimageio.jpeg2000; 046 047import java.util.Locale; 048 049import javax.imageio.ImageWriteParam; 050 051/** 052 * A subclass of <code>ImageWriteParam</code> for writing images in 053 * the JPEG 2000 format. 054 * 055 * <p>JPEG 2000 plugin supports to losslessly or lossy compress gray-scale, 056 * RGB, and RGBA images with byte, unsigned short or short data type. It also 057 * supports losslessly compress bilevel, and 8-bit color indexed images. The 058 * result data is in the of JP2 format -- JPEG 2000 Part 1 or baseline format. 059 * 060 * <p>The parameters for encoding JPEG 2000 are listed in the following table: 061 * 062 * <p><table border=1> 063 * <caption><b>JPEG 2000 Plugin Decoding Parameters</b></caption> 064 * <tr><th>Parameter Name</th> <th>Description</th></tr> 065 * <tr> 066 * <td>numDecompositionLevels</td> 067 * <td> The number of decomposition levels to generate. This value must 068 * be in the range 069 * <code>0 ≤ numDecompositionLevels ≤ 32 070 * </code>. The default value is <code>5</code>. Note that the number 071 * of resolution levels is 072 * <code>numDecompositionLevels + 1</code>. 073 * The number of decomposition levels is constant across 074 * all components and all tiles. 075 * </td> 076 * </tr> 077 * <tr> 078 * <td>encodingRate</td> 079 * <td> The bitrate in bits-per-pixel for encoding. Should be set when 080 * lossy compression scheme is used. With the default value 081 * <code>Double.MAX_VALUE</code>, a lossless compression will be done. 082 * </td> 083 * </tr> 084 * <tr> 085 * <td>lossless</td> 086 * <td> Indicates using the lossless scheme or not. It is equivalent to 087 * use reversible quantization and 5x3 integer wavelet filters. The 088 * default is <code>true</code>. 089 * </td> 090 * </tr> 091 * <tr> 092 * <td>componentTransformation</td> 093 * <td> Specifies to utilize the component transformation on some tiles. 094 * If the wavelet transform is reversible (w5x3 filter), the Reversible 095 * Component Transformation (RCT) is applied. If not reversible 096 * (w9x7 filter), the Irreversible Component Transformation (ICT) is used. 097 * </td> 098 * </tr> 099 * <tr> 100 * <td>filters</td> 101 * <td> Specifies which wavelet filters to use for the specified 102 * tile-components. JPEG 2000 part I only supports w5x3 and w9x7 filters. 103 * </td> 104 * </tr> 105 * <tr> 106 * <td>codeBlockSize</td> 107 * <td> Specifies the maximum code-block size to use for tile-component. 108 * The maximum width and height is 1024, however the block size 109 * (i.e. width x height) must not exceed 4096. The minimum width and 110 * height is 4. The default values are (64, 64). 111 * </td> 112 * </tr> 113 * <tr> 114 * <td>progressionType</td> 115 * <td> Specifies which type of progression should be used when generating 116 * the codestream. 117 * <p> The format is ont of the progression types defined below: 118 * 119 * <p> res : Resolution-Layer-Component-Position 120 * <p> layer: Layer-Resolution-Component-Position 121 * <p> res-pos: Resolution-Position-Component-Layer 122 * <p> pos-comp: Position-Component-Resolution-Layer 123 * <p> comp-pos: Component-Position-Resolution-Layer 124 * </td> 125 * </tr> 126 * <tr> 127 * <td>SOP</td> 128 * <td>Specifies whether start of packet (SOP) markers should be used. 129 * true enables, false disables it. The default value is false. 130 * </td> 131 * </tr> 132 * <tr> 133 * <td>EPH</td> 134 * <td>Specifies whether end of packet header (EPH) markers should be used. 135 * true enables, false disables it. The default value is false. 136 * </td> 137 * </tr> 138 * <tr> 139 * <td>writeCodeStreamOnly</td> 140 * <td>Specifies whether write only the jpeg2000 code stream, i.e, no any 141 * box is written. The default value is false. 142 * </td> 143 * </tr> 144 * </table> 145 */ 146public class J2KImageWriteParam extends ImageWriteParam { 147 /** The filter for lossy compression. */ 148 public static final String FILTER_97 = "w9x7"; 149 150 /** The filter for lossless compression. */ 151 public static final String FILTER_53 = "w5x3"; 152 153 /** 154 * The number of decomposition levels. 155 */ 156 private int numDecompositionLevels = 5; 157 158 /** 159 * The bitrate in bits-per-pixel for encoding. Should be set when lossy 160 * compression scheme is used. The default is 161 * <code>Double.MAX_VALUE</code>. 162 */ 163 private double encodingRate = Double.MAX_VALUE; 164 165 /** 166 * Indicates using the lossless scheme or not. It is equivalent to 167 * use reversible quantization and 5x3 integer wavelet filters. 168 */ 169 private boolean lossless = true; 170 171 /** Specifies to utilize the component transformation with some tiles. 172 * If the wavelet transform is reversible (w5x3 filter), the 173 * Reversible Component Transformation (RCT) is applied. If not reversible 174 * (w9x7 filter), the Irreversible Component Transformation (ICT) 175 * is used. 176 */ 177 private boolean componentTransformation = true; 178 179 /** Specifies which filters to use for the specified tile-components. 180 * JPEG 2000 part I only supports w5x3 and w9x7 filters. 181 */ 182 private String filter = FILTER_53; 183 184 /** Specifies the maximum code-block size to use for tile-component. 185 * The maximum width and height is 1024, however the image area 186 * (i.e. width x height) must not exceed 4096. The minimum 187 * width and height is 4. Default: 64 64. 188 */ 189 private int[] codeBlockSize = new int[]{64, 64}; 190 191 /** See above. 192 */ 193 private String progressionType = "layer"; 194 195 /** Specifies whether end of packet header (EPH) markers should be used. 196 * true enables, false disables it. Default: false. 197 */ 198 private boolean EPH = false; 199 200 /** Specifies whether start of packet (SOP) markers should be used. 201 * true enables, false disables it. Default: false. 202 */ 203 private boolean SOP = false; 204 205 /** Specifies whether write only the jpeg2000 code stream, i.e, no any 206 * box is written. The default value is false. 207 */ 208 private boolean writeCodeStreamOnly = false; 209 210 /** 211 * Constructor which sets the <code>Locale</code>. 212 * 213 * @param locale a <code>Locale</code> to be used to localize 214 * compression type names and quality descriptions, or 215 * <code>null</code>. 216 */ 217 public J2KImageWriteParam(Locale locale) { 218 super(locale); 219 setDefaults(); 220 } 221 222 /** 223 * Constructs a <code>J2KImageWriteParam</code> object with default 224 * values for all parameters. 225 */ 226 public J2KImageWriteParam() { 227 super(); 228 setDefaults(); 229 } 230 231 /** Set source */ 232 private void setDefaults() { 233 // override the params in the super class 234 canOffsetTiles = true; 235 canWriteTiles = true; 236 canOffsetTiles = true; 237 compressionTypes = new String[] {"JPEG2000"}; 238 canWriteCompressed = true; 239 tilingMode = MODE_EXPLICIT; 240 } 241 242 /** 243 * Sets <code>numDecompositionLevels</code>. 244 * 245 * @param numDecompositionLevels the number of decomposition levels. 246 * @throws IllegalArgumentException if <code>numDecompositionLevels</code> 247 * is negative or greater than 32. 248 * @see #getNumDecompositionLevels 249 */ 250 public void setNumDecompositionLevels(int numDecompositionLevels) { 251 if(numDecompositionLevels < 0 || numDecompositionLevels > 32) { 252 throw new IllegalArgumentException 253 ("numDecompositionLevels < 0 || numDecompositionLevels > 32"); 254 } 255 this.numDecompositionLevels = numDecompositionLevels; 256 } 257 258 /** 259 * Gets <code>numDecompositionLevels</code>. 260 * 261 * @return the number of decomposition levels. 262 * @see #setNumDecompositionLevels 263 */ 264 public int getNumDecompositionLevels() { 265 return numDecompositionLevels; 266 } 267 268 /** 269 * Sets <code>encodingRate</code>. 270 * 271 * @param rate the encoding rate in bits-per-pixel. 272 * @see #getEncodingRate() 273 */ 274 public void setEncodingRate(double rate) { 275 this.encodingRate = rate; 276 if (encodingRate != Double.MAX_VALUE) { 277 lossless = false; 278 filter = FILTER_97; 279 } else { 280 lossless = true; 281 filter = FILTER_53; 282 } 283 } 284 285 /** 286 * Gets <code>encodingRate</code>. 287 * 288 * @return the encoding rate in bits-per-pixel. 289 * @see #setEncodingRate(double) 290 */ 291 public double getEncodingRate() { 292 return encodingRate; 293 } 294 295 /** 296 * Sets <code>lossless</code>. 297 * 298 * @param lossless whether the compression scheme is lossless. 299 * @see #getLossless() 300 */ 301 public void setLossless(boolean lossless) { 302 this.lossless = lossless; 303 } 304 305 /** 306 * Gets <code>lossless</code>. 307 * 308 * @return whether the compression scheme is lossless. 309 * @see #setLossless(boolean) 310 */ 311 public boolean getLossless() { 312 return lossless; 313 } 314 315 /** 316 * Sets <code>filter</code>. 317 * 318 * @param value which wavelet filters to use for the specified 319 * tile-components. 320 * @see #getFilter() 321 */ 322 public void setFilter(String value) { 323 filter = value; 324 } 325 326 /** 327 * Gets <code>filters</code>. 328 * 329 * @return which wavelet filters to use for the specified 330 * tile-components. 331 * @see #setFilter(String) 332 */ 333 public String getFilter() { 334 return filter; 335 } 336 337 /** 338 * Sets <code>componentTransformation</code>. 339 * 340 * @param value whether to utilize the component transformation. 341 * @see #getComponentTransformation() 342 */ 343 public void setComponentTransformation(boolean value) { 344 componentTransformation = value; 345 } 346 347 /** 348 * Gets <code>componentTransformation</code>. 349 * 350 * @return whether to utilize the component transformation. 351 * @see #setComponentTransformation(boolean) 352 */ 353 public boolean getComponentTransformation() { 354 return componentTransformation; 355 } 356 357 /** 358 * Sets <code>codeBlockSize</code>. 359 * 360 * @param value the maximum code-block size to use per tile-component. 361 * @see #getCodeBlockSize() 362 */ 363 public void setCodeBlockSize(int[] value) { 364 codeBlockSize = value; 365 } 366 367 /** 368 * Gets <code>codeBlockSize</code>. 369 * 370 * @return the maximum code-block size to use per tile-component. 371 * @see #setCodeBlockSize(int[]) 372 */ 373 public int[] getCodeBlockSize() { 374 return codeBlockSize; 375 } 376 377 /** 378 * Sets <code>SOP</code>. 379 * 380 * @param value whether start of packet (SOP) markers should be used. 381 * @see #getSOP() 382 */ 383 public void setSOP(boolean value) { 384 SOP = value; 385 } 386 387 /** 388 * Gets <code>SOP</code>. 389 * 390 * @return whether start of packet (SOP) markers should be used. 391 * @see #setSOP(boolean) 392 */ 393 public boolean getSOP() { 394 return SOP; 395 } 396 397 /** 398 * Sets <code>EPH</code>. 399 * 400 * @param value whether end of packet header (EPH) markers should be used. 401 * @see #getEPH() 402 */ 403 public void setEPH(boolean value) { 404 EPH = value; 405 } 406 407 /** 408 * Gets <code>EPH</code>. 409 * 410 * @return whether end of packet header (EPH) markers should be used. 411 * @see #setEPH(boolean) 412 */ 413 public boolean getEPH() { 414 return EPH; 415 } 416 417 /** 418 * Sets <code>progressionType</code>. 419 * 420 * @param value which type of progression should be used when generating 421 * the codestream. 422 * @see #getProgressionType() 423 */ 424 public void setProgressionType(String value) { 425 progressionType = value; 426 } 427 428 /** 429 * Gets <code>progressionType</code>. 430 * 431 * @return which type of progression should be used when generating 432 * the codestream. 433 * @see #setProgressionType(String) 434 */ 435 public String getProgressionType() { 436 return progressionType; 437 } 438 439 /** Sets <code>writeCodeStreamOnly</code>. 440 * 441 * @param value Whether the jpeg2000 code stream only or the jp2 format 442 * will be written into the output. 443 * @see #getWriteCodeStreamOnly() 444 */ 445 public void setWriteCodeStreamOnly(boolean value) { 446 writeCodeStreamOnly = value; 447 } 448 449 /** Gets <code>writeCodeStreamOnly</code>. 450 * 451 * @return whether the jpeg2000 code stream only or the jp2 format 452 * will be written into the output. 453 * @see #setWriteCodeStreamOnly(boolean) 454 */ 455 public boolean getWriteCodeStreamOnly() { 456 return writeCodeStreamOnly; 457 } 458}