blob: 7859886988c4e0a8c3b1d95cb0451fe653ffa2f7 [file] [log] [blame]
DRCf8e00552011-02-04 11:06:36 +00001/*
Leon Scroggins III3993b372018-07-16 10:43:45 -04002 * Copyright (C)2011-2012, 2014-2015, 2017-2018 D. R. Commander.
3 * All Rights Reserved.
DRCf8e00552011-02-04 11:06:36 +00004 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions are met:
7 *
8 * - Redistributions of source code must retain the above copyright notice,
9 * this list of conditions and the following disclaimer.
10 * - Redistributions in binary form must reproduce the above copyright notice,
11 * this list of conditions and the following disclaimer in the documentation
12 * and/or other materials provided with the distribution.
13 * - Neither the name of the libjpeg-turbo Project nor the names of its
14 * contributors may be used to endorse or promote products derived from this
15 * software without specific prior written permission.
16 *
17 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS",
18 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
19 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
20 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDERS OR CONTRIBUTORS BE
21 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
22 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
23 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
24 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
25 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
26 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
27 * POSSIBILITY OF SUCH DAMAGE.
28 */
29
30/*
Leon Scroggins III3993b372018-07-16 10:43:45 -040031 * This program demonstrates how to compress, decompress, and transform JPEG
32 * images using the TurboJPEG Java API
DRCf8e00552011-02-04 11:06:36 +000033 */
34
35import java.io.*;
DRCf5467112011-09-20 05:02:19 +000036import java.awt.*;
DRC026f7ce2011-02-23 20:51:54 +000037import java.awt.image.*;
DRCf5467112011-09-20 05:02:19 +000038import java.nio.*;
DRC026f7ce2011-02-23 20:51:54 +000039import javax.imageio.*;
DRC16c70772011-03-07 09:59:08 +000040import javax.swing.*;
DRCc5a41992011-02-08 06:54:36 +000041import org.libjpegturbo.turbojpeg.*;
DRCf8e00552011-02-04 11:06:36 +000042
DRCf8e00552011-02-04 11:06:36 +000043
Leon Scroggins III3993b372018-07-16 10:43:45 -040044@SuppressWarnings("checkstyle:JavadocType")
45class TJExample implements TJCustomFilter {
DRCf8e00552011-02-04 11:06:36 +000046
Leon Scroggins III3993b372018-07-16 10:43:45 -040047 static final String CLASS_NAME =
48 new TJExample().getClass().getName();
49
50 static final int DEFAULT_SUBSAMP = TJ.SAMP_444;
51 static final int DEFAULT_QUALITY = 95;
52
53
54 static final String[] SUBSAMP_NAME = {
55 "4:4:4", "4:2:2", "4:2:0", "Grayscale", "4:4:0", "4:1:1"
56 };
57
58 static final String[] COLORSPACE_NAME = {
59 "RGB", "YCbCr", "GRAY", "CMYK", "YCCK"
60 };
61
62
63 /* DCT filter example. This produces a negative of the image. */
64
65 @SuppressWarnings("checkstyle:JavadocMethod")
66 public void customFilter(ShortBuffer coeffBuffer, Rectangle bufferRegion,
67 Rectangle planeRegion, int componentIndex,
68 int transformIndex, TJTransform transform)
69 throws TJException {
70 for (int i = 0; i < bufferRegion.width * bufferRegion.height; i++) {
71 coeffBuffer.put(i, (short)(-coeffBuffer.get(i)));
72 }
73 }
74
75
76 static void usage() throws Exception {
77 System.out.println("\nUSAGE: java [Java options] " + CLASS_NAME +
78 " <Input image> <Output image> [options]\n");
79
80 System.out.println("Input and output images can be in any image format that the Java Image I/O");
DRC026f7ce2011-02-23 20:51:54 +000081 System.out.println("extensions understand. If either filename ends in a .jpg extension, then");
Leon Scroggins III3993b372018-07-16 10:43:45 -040082 System.out.println("the TurboJPEG API will be used to compress or decompress the image.\n");
83
84 System.out.println("Compression Options (used if the output image is a JPEG image)");
85 System.out.println("--------------------------------------------------------------\n");
86
87 System.out.println("-subsamp <444|422|420|gray> = Apply this level of chrominance subsampling when");
88 System.out.println(" compressing the output image. The default is to use the same level of");
89 System.out.println(" subsampling as in the input image, if the input image is also a JPEG");
90 System.out.println(" image, or to use grayscale if the input image is a grayscale non-JPEG");
91 System.out.println(" image, or to use " +
92 SUBSAMP_NAME[DEFAULT_SUBSAMP] +
93 " subsampling otherwise.\n");
94
95 System.out.println("-q <1-100> = Compress the output image with this JPEG quality level");
96 System.out.println(" (default = " + DEFAULT_QUALITY + ").\n");
97
98 System.out.println("Decompression Options (used if the input image is a JPEG image)");
99 System.out.println("---------------------------------------------------------------\n");
100
101 System.out.println("-scale M/N = Scale the input image by a factor of M/N when decompressing it.");
102 System.out.print("(M/N = ");
103 for (int i = 0; i < SCALING_FACTORS.length; i++) {
104 System.out.print(SCALING_FACTORS[i].getNum() + "/" +
105 SCALING_FACTORS[i].getDenom());
106 if (SCALING_FACTORS.length == 2 && i != SCALING_FACTORS.length - 1)
DRC67bee862013-04-27 12:36:07 +0000107 System.out.print(" or ");
Leon Scroggins III3993b372018-07-16 10:43:45 -0400108 else if (SCALING_FACTORS.length > 2) {
109 if (i != SCALING_FACTORS.length - 1)
DRC67bee862013-04-27 12:36:07 +0000110 System.out.print(", ");
Leon Scroggins III3993b372018-07-16 10:43:45 -0400111 if (i == SCALING_FACTORS.length - 2)
DRC67bee862013-04-27 12:36:07 +0000112 System.out.print("or ");
DRC5528b552011-03-01 20:43:47 +0000113 }
114 }
115 System.out.println(")\n");
Leon Scroggins III3993b372018-07-16 10:43:45 -0400116
DRCe8573012011-03-04 10:13:59 +0000117 System.out.println("-hflip, -vflip, -transpose, -transverse, -rot90, -rot180, -rot270 =");
Leon Scroggins III3993b372018-07-16 10:43:45 -0400118 System.out.println(" Perform one of these lossless transform operations on the input image");
119 System.out.println(" prior to decompressing it (these options are mutually exclusive.)\n");
120
121 System.out.println("-grayscale = Perform lossless grayscale conversion on the input image prior");
122 System.out.println(" to decompressing it (can be combined with the other transform operations");
123 System.out.println(" above.)\n");
124
125 System.out.println("-crop WxH+X+Y = Perform lossless cropping on the input image prior to");
126 System.out.println(" decompressing it. X and Y specify the upper left corner of the cropping");
127 System.out.println(" region, and W and H specify the width and height of the cropping region.");
128 System.out.println(" X and Y must be evenly divible by the MCU block size (8x8 if the input");
129 System.out.println(" image was compressed using no subsampling or grayscale, 16x8 if it was");
130 System.out.println(" compressed using 4:2:2 subsampling, or 16x16 if it was compressed using");
131 System.out.println(" 4:2:0 subsampling.)\n");
132
133 System.out.println("General Options");
134 System.out.println("---------------\n");
135
136 System.out.println("-display = Display output image (Output filename need not be specified in this");
DRC16c70772011-03-07 09:59:08 +0000137 System.out.println(" case.)\n");
Leon Scroggins III3993b372018-07-16 10:43:45 -0400138
DRC73d74c12012-06-29 23:46:38 +0000139 System.out.println("-fastupsample = Use the fastest chrominance upsampling algorithm available in");
Leon Scroggins III3993b372018-07-16 10:43:45 -0400140 System.out.println(" the underlying codec.\n");
141
DRC73d74c12012-06-29 23:46:38 +0000142 System.out.println("-fastdct = Use the fastest DCT/IDCT algorithms available in the underlying");
Leon Scroggins III3993b372018-07-16 10:43:45 -0400143 System.out.println(" codec.\n");
144
DRC73d74c12012-06-29 23:46:38 +0000145 System.out.println("-accuratedct = Use the most accurate DCT/IDCT algorithms available in the");
Leon Scroggins III3993b372018-07-16 10:43:45 -0400146 System.out.println(" underlying codec.\n");
147
DRCe1303ef2011-02-16 03:26:48 +0000148 System.exit(1);
149 }
150
DRC026f7ce2011-02-23 20:51:54 +0000151
DRC67bee862013-04-27 12:36:07 +0000152 public static void main(String[] argv) {
DRCf8e00552011-02-04 11:06:36 +0000153
154 try {
155
Leon Scroggins III3993b372018-07-16 10:43:45 -0400156 TJScalingFactor scalingFactor = new TJScalingFactor(1, 1);
157 int outSubsamp = -1, outQual = -1;
158 TJTransform xform = new TJTransform();
DRC16c70772011-03-07 09:59:08 +0000159 boolean display = false;
Leon Scroggins III3993b372018-07-16 10:43:45 -0400160 int flags = 0;
161 int width, height;
162 String inFormat = "jpg", outFormat = "jpg";
163 BufferedImage img = null;
164 byte[] imgBuf = null;
165
166 if (argv.length < 2)
167 usage();
DRC026f7ce2011-02-23 20:51:54 +0000168
Leon Scroggins IIIbd7903e2018-02-28 14:05:04 -0500169 if (argv[1].substring(0, 2).equalsIgnoreCase("-d"))
170 display = true;
171
Leon Scroggins III3993b372018-07-16 10:43:45 -0400172 /* Parse arguments. */
Leon Scroggins IIIbd7903e2018-02-28 14:05:04 -0500173 for (int i = 2; i < argv.length; i++) {
174 if (argv[i].length() < 2)
175 continue;
176 else if (argv[i].length() > 2 &&
Leon Scroggins III3993b372018-07-16 10:43:45 -0400177 argv[i].substring(0, 3).equalsIgnoreCase("-sc") &&
178 i < argv.length - 1) {
Leon Scroggins IIIbd7903e2018-02-28 14:05:04 -0500179 int match = 0;
Leon Scroggins III3993b372018-07-16 10:43:45 -0400180 String[] scaleArg = argv[++i].split("/");
181 if (scaleArg.length == 2) {
182 TJScalingFactor tempsf =
183 new TJScalingFactor(Integer.parseInt(scaleArg[0]),
184 Integer.parseInt(scaleArg[1]));
185 for (int j = 0; j < SCALING_FACTORS.length; j++) {
186 if (tempsf.equals(SCALING_FACTORS[j])) {
187 scalingFactor = SCALING_FACTORS[j];
188 match = 1;
189 break;
DRC5528b552011-03-01 20:43:47 +0000190 }
DRC026f7ce2011-02-23 20:51:54 +0000191 }
DRC026f7ce2011-02-23 20:51:54 +0000192 }
Leon Scroggins III3993b372018-07-16 10:43:45 -0400193 if (match != 1)
Leon Scroggins IIIbd7903e2018-02-28 14:05:04 -0500194 usage();
Leon Scroggins III3993b372018-07-16 10:43:45 -0400195 } else if (argv[i].length() > 2 &&
196 argv[i].substring(0, 3).equalsIgnoreCase("-su") &&
197 i < argv.length - 1) {
198 i++;
199 if (argv[i].substring(0, 1).equalsIgnoreCase("g"))
200 outSubsamp = TJ.SAMP_GRAY;
201 else if (argv[i].equals("444"))
202 outSubsamp = TJ.SAMP_444;
203 else if (argv[i].equals("422"))
204 outSubsamp = TJ.SAMP_422;
205 else if (argv[i].equals("420"))
206 outSubsamp = TJ.SAMP_420;
207 else
Leon Scroggins IIIbd7903e2018-02-28 14:05:04 -0500208 usage();
Leon Scroggins III3993b372018-07-16 10:43:45 -0400209 } else if (argv[i].substring(0, 2).equalsIgnoreCase("-q") &&
210 i < argv.length - 1) {
211 outQual = Integer.parseInt(argv[++i]);
212 if (outQual < 1 || outQual > 100)
213 usage();
214 } else if (argv[i].substring(0, 2).equalsIgnoreCase("-g"))
Leon Scroggins IIIbd7903e2018-02-28 14:05:04 -0500215 xform.options |= TJTransform.OPT_GRAY;
216 else if (argv[i].equalsIgnoreCase("-hflip"))
217 xform.op = TJTransform.OP_HFLIP;
218 else if (argv[i].equalsIgnoreCase("-vflip"))
219 xform.op = TJTransform.OP_VFLIP;
220 else if (argv[i].equalsIgnoreCase("-transpose"))
221 xform.op = TJTransform.OP_TRANSPOSE;
222 else if (argv[i].equalsIgnoreCase("-transverse"))
223 xform.op = TJTransform.OP_TRANSVERSE;
224 else if (argv[i].equalsIgnoreCase("-rot90"))
225 xform.op = TJTransform.OP_ROT90;
226 else if (argv[i].equalsIgnoreCase("-rot180"))
227 xform.op = TJTransform.OP_ROT180;
228 else if (argv[i].equalsIgnoreCase("-rot270"))
229 xform.op = TJTransform.OP_ROT270;
230 else if (argv[i].equalsIgnoreCase("-custom"))
231 xform.cf = new TJExample();
232 else if (argv[i].length() > 2 &&
Leon Scroggins III3993b372018-07-16 10:43:45 -0400233 argv[i].substring(0, 2).equalsIgnoreCase("-c") &&
234 i < argv.length - 1) {
235 String[] cropArg = argv[++i].split("[x\\+]");
236 if (cropArg.length != 4)
Leon Scroggins IIIbd7903e2018-02-28 14:05:04 -0500237 usage();
Leon Scroggins III3993b372018-07-16 10:43:45 -0400238 xform.width = Integer.parseInt(cropArg[0]);
239 xform.height = Integer.parseInt(cropArg[1]);
240 xform.x = Integer.parseInt(cropArg[2]);
241 xform.y = Integer.parseInt(cropArg[3]);
242 if (xform.x < 0 || xform.y < 0 || xform.width < 1 ||
243 xform.height < 1)
Leon Scroggins IIIbd7903e2018-02-28 14:05:04 -0500244 usage();
Leon Scroggins IIIbd7903e2018-02-28 14:05:04 -0500245 xform.options |= TJTransform.OPT_CROP;
Leon Scroggins III3993b372018-07-16 10:43:45 -0400246 } else if (argv[i].substring(0, 2).equalsIgnoreCase("-d"))
Leon Scroggins IIIbd7903e2018-02-28 14:05:04 -0500247 display = true;
248 else if (argv[i].equalsIgnoreCase("-fastupsample")) {
249 System.out.println("Using fast upsampling code");
250 flags |= TJ.FLAG_FASTUPSAMPLE;
Leon Scroggins III3993b372018-07-16 10:43:45 -0400251 } else if (argv[i].equalsIgnoreCase("-fastdct")) {
Leon Scroggins IIIbd7903e2018-02-28 14:05:04 -0500252 System.out.println("Using fastest DCT/IDCT algorithm");
253 flags |= TJ.FLAG_FASTDCT;
Leon Scroggins III3993b372018-07-16 10:43:45 -0400254 } else if (argv[i].equalsIgnoreCase("-accuratedct")) {
Leon Scroggins IIIbd7903e2018-02-28 14:05:04 -0500255 System.out.println("Using most accurate DCT/IDCT algorithm");
256 flags |= TJ.FLAG_ACCURATEDCT;
Leon Scroggins III3993b372018-07-16 10:43:45 -0400257 } else usage();
DRCf8e00552011-02-04 11:06:36 +0000258 }
Leon Scroggins III3993b372018-07-16 10:43:45 -0400259
260 /* Determine input and output image formats based on file extensions. */
DRCf7f3ea42011-03-01 20:03:32 +0000261 String[] inFileTokens = argv[0].split("\\.");
DRC67bee862013-04-27 12:36:07 +0000262 if (inFileTokens.length > 1)
DRC026f7ce2011-02-23 20:51:54 +0000263 inFormat = inFileTokens[inFileTokens.length - 1];
DRC16c70772011-03-07 09:59:08 +0000264 String[] outFileTokens;
DRC67bee862013-04-27 12:36:07 +0000265 if (display)
266 outFormat = "bmp";
DRC16c70772011-03-07 09:59:08 +0000267 else {
268 outFileTokens = argv[1].split("\\.");
DRC67bee862013-04-27 12:36:07 +0000269 if (outFileTokens.length > 1)
DRC16c70772011-03-07 09:59:08 +0000270 outFormat = outFileTokens[outFileTokens.length - 1];
271 }
DRCf8e00552011-02-04 11:06:36 +0000272
DRC67bee862013-04-27 12:36:07 +0000273 if (inFormat.equalsIgnoreCase("jpg")) {
Leon Scroggins III3993b372018-07-16 10:43:45 -0400274 /* Input image is a JPEG image. Decompress and/or transform it. */
275 boolean doTransform = (xform.op != TJTransform.OP_NONE ||
276 xform.options != 0 || xform.cf != null);
277
278 /* Read the JPEG file into memory. */
279 File jpegFile = new File(argv[0]);
280 FileInputStream fis = new FileInputStream(jpegFile);
281 int jpegSize = fis.available();
282 if (jpegSize < 1) {
DRC026f7ce2011-02-23 20:51:54 +0000283 System.out.println("Input file contains no data");
284 System.exit(1);
285 }
Leon Scroggins III3993b372018-07-16 10:43:45 -0400286 byte[] jpegBuf = new byte[jpegSize];
287 fis.read(jpegBuf);
DRC026f7ce2011-02-23 20:51:54 +0000288 fis.close();
289
DRCe8573012011-03-04 10:13:59 +0000290 TJDecompressor tjd;
Leon Scroggins III3993b372018-07-16 10:43:45 -0400291 if (doTransform) {
292 /* Transform it. */
293 TJTransformer tjt = new TJTransformer(jpegBuf);
294 TJTransform[] xforms = new TJTransform[1];
295 xforms[0] = xform;
296 xforms[0].options |= TJTransform.OPT_TRIM;
297 TJDecompressor[] tjds = tjt.transform(xforms, 0);
298 tjd = tjds[0];
299 tjt.close();
DRC67bee862013-04-27 12:36:07 +0000300 } else
Leon Scroggins III3993b372018-07-16 10:43:45 -0400301 tjd = new TJDecompressor(jpegBuf);
DRCe8573012011-03-04 10:13:59 +0000302
DRC026f7ce2011-02-23 20:51:54 +0000303 width = tjd.getWidth();
304 height = tjd.getHeight();
305 int inSubsamp = tjd.getSubsamp();
Leon Scroggins III3993b372018-07-16 10:43:45 -0400306 int inColorspace = tjd.getColorspace();
DRC026f7ce2011-02-23 20:51:54 +0000307
Leon Scroggins III3993b372018-07-16 10:43:45 -0400308 System.out.println((doTransform ? "Transformed" : "Input") +
309 " Image (jpg): " + width + " x " + height +
310 " pixels, " + SUBSAMP_NAME[inSubsamp] +
311 " subsampling, " + COLORSPACE_NAME[inColorspace]);
312
313 if (outFormat.equalsIgnoreCase("jpg") && doTransform &&
314 scalingFactor.isOne() && outSubsamp < 0 && outQual < 0) {
315 /* Input image has been transformed, and no re-compression options
316 have been selected. Write the transformed image to disk and
317 exit. */
318 File outFile = new File(argv[1]);
319 FileOutputStream fos = new FileOutputStream(outFile);
DRC40dd3142014-08-17 12:23:49 +0000320 fos.write(tjd.getJPEGBuf(), 0, tjd.getJPEGSize());
DRC7d4b0012011-03-04 13:40:42 +0000321 fos.close();
322 System.exit(0);
323 }
324
Leon Scroggins III3993b372018-07-16 10:43:45 -0400325 /* Scaling and/or a non-JPEG output image format and/or compression
326 options have been selected, so we need to decompress the
327 input/transformed image. */
328 width = scalingFactor.getScaled(width);
329 height = scalingFactor.getScaled(height);
330 if (outSubsamp < 0)
331 outSubsamp = inSubsamp;
DRC026f7ce2011-02-23 20:51:54 +0000332
DRC67bee862013-04-27 12:36:07 +0000333 if (!outFormat.equalsIgnoreCase("jpg"))
DRC73d74c12012-06-29 23:46:38 +0000334 img = tjd.decompress(width, height, BufferedImage.TYPE_INT_RGB,
335 flags);
DRC67bee862013-04-27 12:36:07 +0000336 else
Leon Scroggins III3993b372018-07-16 10:43:45 -0400337 imgBuf = tjd.decompress(width, 0, height, TJ.PF_BGRX, flags);
DRC026f7ce2011-02-23 20:51:54 +0000338 tjd.close();
DRC67bee862013-04-27 12:36:07 +0000339 } else {
Leon Scroggins III3993b372018-07-16 10:43:45 -0400340 /* Input image is not a JPEG image. Load it into memory. */
341 img = ImageIO.read(new File(argv[0]));
DRC98ca1c32013-01-19 06:43:27 +0000342 if (img == null)
343 throw new Exception("Input image type not supported.");
DRC026f7ce2011-02-23 20:51:54 +0000344 width = img.getWidth();
345 height = img.getHeight();
DRC67bee862013-04-27 12:36:07 +0000346 if (outSubsamp < 0) {
347 if (img.getType() == BufferedImage.TYPE_BYTE_GRAY)
DRC026f7ce2011-02-23 20:51:54 +0000348 outSubsamp = TJ.SAMP_GRAY;
DRC67bee862013-04-27 12:36:07 +0000349 else
Leon Scroggins III3993b372018-07-16 10:43:45 -0400350 outSubsamp = DEFAULT_SUBSAMP;
DRC026f7ce2011-02-23 20:51:54 +0000351 }
Leon Scroggins III3993b372018-07-16 10:43:45 -0400352 System.out.println("Input Image: " + width + " x " + height +
353 " pixels");
DRCf8e00552011-02-04 11:06:36 +0000354 }
DRCe8573012011-03-04 10:13:59 +0000355 System.gc();
DRC67bee862013-04-27 12:36:07 +0000356 if (!display)
Leon Scroggins III3993b372018-07-16 10:43:45 -0400357 System.out.print("Output Image (" + outFormat + "): " + width +
358 " x " + height + " pixels");
DRCe1303ef2011-02-16 03:26:48 +0000359
DRC67bee862013-04-27 12:36:07 +0000360 if (display) {
Leon Scroggins III3993b372018-07-16 10:43:45 -0400361 /* Display the uncompressed image */
DRC16c70772011-03-07 09:59:08 +0000362 ImageIcon icon = new ImageIcon(img);
363 JLabel label = new JLabel(icon, JLabel.CENTER);
364 JOptionPane.showMessageDialog(null, label, "Output Image",
DRC67bee862013-04-27 12:36:07 +0000365 JOptionPane.PLAIN_MESSAGE);
366 } else if (outFormat.equalsIgnoreCase("jpg")) {
Leon Scroggins III3993b372018-07-16 10:43:45 -0400367 /* Output image format is JPEG. Compress the uncompressed image. */
368 if (outQual < 0)
369 outQual = DEFAULT_QUALITY;
370 System.out.println(", " + SUBSAMP_NAME[outSubsamp] +
DRC67bee862013-04-27 12:36:07 +0000371 " subsampling, quality = " + outQual);
DRC026f7ce2011-02-23 20:51:54 +0000372
Leon Scroggins III3993b372018-07-16 10:43:45 -0400373 TJCompressor tjc = new TJCompressor();
DRC4f1580c2011-02-25 06:11:03 +0000374 tjc.setSubsamp(outSubsamp);
375 tjc.setJPEGQuality(outQual);
DRC67bee862013-04-27 12:36:07 +0000376 if (img != null)
DRCb1481392014-03-14 08:53:33 +0000377 tjc.setSourceImage(img, 0, 0, 0, 0);
Leon Scroggins III3993b372018-07-16 10:43:45 -0400378 else
379 tjc.setSourceImage(imgBuf, 0, 0, width, 0, height, TJ.PF_BGRX);
380 byte[] jpegBuf = tjc.compress(flags);
381 int jpegSize = tjc.getCompressedSize();
DRC026f7ce2011-02-23 20:51:54 +0000382 tjc.close();
383
Leon Scroggins III3993b372018-07-16 10:43:45 -0400384 /* Write the JPEG image to disk. */
385 File outFile = new File(argv[1]);
386 FileOutputStream fos = new FileOutputStream(outFile);
DRC026f7ce2011-02-23 20:51:54 +0000387 fos.write(jpegBuf, 0, jpegSize);
388 fos.close();
DRC67bee862013-04-27 12:36:07 +0000389 } else {
Leon Scroggins III3993b372018-07-16 10:43:45 -0400390 /* Output image format is not JPEG. Save the uncompressed image
391 directly to disk. */
DRC0ad78a62011-02-23 20:57:17 +0000392 System.out.print("\n");
Leon Scroggins III3993b372018-07-16 10:43:45 -0400393 File outFile = new File(argv[1]);
394 ImageIO.write(img, outFormat, outFile);
DRC026f7ce2011-02-23 20:51:54 +0000395 }
DRCf8e00552011-02-04 11:06:36 +0000396
Leon Scroggins III3993b372018-07-16 10:43:45 -0400397 } catch (Exception e) {
DRCe8573012011-03-04 10:13:59 +0000398 e.printStackTrace();
399 System.exit(-1);
DRCf8e00552011-02-04 11:06:36 +0000400 }
401 }
402
Leon Scroggins III3993b372018-07-16 10:43:45 -0400403 static final TJScalingFactor[] SCALING_FACTORS =
404 TJ.getScalingFactors();
DRCf8e00552011-02-04 11:06:36 +0000405};