1bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen/* 2bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen * Copyright (C) 2010 The Android Open Source Project 3bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen * 4bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen * Licensed under the Apache License, Version 2.0 (the "License"); 5bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen * you may not use this file except in compliance with the License. 6bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen * You may obtain a copy of the License at 7bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen * 8bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen * http://www.apache.org/licenses/LICENSE-2.0 9bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen * 10bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen * Unless required by applicable law or agreed to in writing, software 11bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen * distributed under the License is distributed on an "AS IS" BASIS, 12bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 13bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen * See the License for the specific language governing permissions and 14bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen * limitations under the License. 15bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen */ 16bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen 17bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chenpackage android.graphics; 18bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen 19bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chenimport java.io.OutputStream; 20bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen 21bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen/** 22bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen * YuvImage contains YUV data and provides a method that compresses a region of 23bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen * the YUV data to a Jpeg. The YUV data should be provided as a single byte 24d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen * array irrespective of the number of image planes in it. 25a696f5d667227365da732481770767dcb330dd23Mathias Agopian * Currently only ImageFormat.NV21 and ImageFormat.YUY2 are supported. 26bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen * 27d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen * To compress a rectangle region in the YUV data, users have to specify the 28d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen * region by left, top, width and height. 29bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen */ 30bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chenpublic class YuvImage { 31bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen 32bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen /** 33bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen * Number of bytes of temp storage we use for communicating between the 34bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen * native compressor and the java OutputStream. 35bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen */ 36bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen private final static int WORKING_COMPRESS_STORAGE = 4096; 37bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen 38bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen /** 397fb597df52c7c6569a1c9ebacfb7629cf3dc6dc1Keiji Ariyama * The YUV format as defined in {@link ImageFormat}. 40bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen */ 41bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen private int mFormat; 42bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen 43bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen /** 44bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen * The raw YUV data. 45bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen * In the case of more than one image plane, the image planes must be 46bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen * concatenated into a single byte array. 47bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen */ 48bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen private byte[] mData; 49bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen 50bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen /** 51bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen * The number of row bytes in each image plane. 52bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen */ 53bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen private int[] mStrides; 54bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen 55bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen /** 56d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen * The width of the image. 57d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen */ 58d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen private int mWidth; 59d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen 60d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen /** 61d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen * The height of the the image. 62d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen */ 63d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen private int mHeight; 64d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen 65d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen /** 66bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen * Construct an YuvImage. 67bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen * 68d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen * @param yuv The YUV data. In the case of more than one image plane, all the planes must be 69d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen * concatenated into a single byte array. 707fb597df52c7c6569a1c9ebacfb7629cf3dc6dc1Keiji Ariyama * @param format The YUV data format as defined in {@link ImageFormat}. 71d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen * @param width The width of the YuvImage. 72d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen * @param height The height of the YuvImage. 73d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen * @param strides (Optional) Row bytes of each image plane. If yuv contains padding, the stride 74d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen * of each image must be provided. If strides is null, the method assumes no 75d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen * padding and derives the row bytes by format and width itself. 76d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen * @throws IllegalArgumentException if format is not support; width or height <= 0; or yuv is 77d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen * null. 78bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen */ 79d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen public YuvImage(byte[] yuv, int format, int width, int height, int[] strides) { 80a696f5d667227365da732481770767dcb330dd23Mathias Agopian if (format != ImageFormat.NV21 && 81a696f5d667227365da732481770767dcb330dd23Mathias Agopian format != ImageFormat.YUY2) { 82bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen throw new IllegalArgumentException( 83a696f5d667227365da732481770767dcb330dd23Mathias Agopian "only support ImageFormat.NV21 " + 84a696f5d667227365da732481770767dcb330dd23Mathias Agopian "and ImageFormat.YUY2 for now"); 85bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen } 86d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen 87d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen if (width <= 0 || height <= 0) { 88d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen throw new IllegalArgumentException( 89d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen "width and height must large than 0"); 90d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen } 91d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen 92d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen if (yuv == null) { 93d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen throw new IllegalArgumentException("yuv cannot be null"); 94d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen } 95d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen 96d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen if (strides == null) { 97d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen mStrides = calculateStrides(width, format); 98d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen } else { 99d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen mStrides = strides; 100d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen } 101d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen 102bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen mData = yuv; 103bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen mFormat = format; 104d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen mWidth = width; 105d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen mHeight = height; 106bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen } 107bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen 108bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen /** 109bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen * Compress a rectangle region in the YuvImage to a jpeg. 110a696f5d667227365da732481770767dcb330dd23Mathias Agopian * Only ImageFormat.NV21 and ImageFormat.YUY2 111bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen * are supported for now. 112bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen * 113d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen * @param rectangle The rectangle region to be compressed. The medthod checks if rectangle is 114d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen * inside the image. Also, the method modifies rectangle if the chroma pixels 115d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen * in it are not matched with the luma pixels in it. 116d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen * @param quality Hint to the compressor, 0-100. 0 meaning compress for 117d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen * small size, 100 meaning compress for max quality. 118d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen * @param stream OutputStream to write the compressed data. 119d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen * @return True if the compression is successful. 120d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen * @throws IllegalArgumentException if rectangle is invalid; quality is not within [0, 121d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen * 100]; or stream is null. 122bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen */ 123d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen public boolean compressToJpeg(Rect rectangle, int quality, OutputStream stream) { 124d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen Rect wholeImage = new Rect(0, 0, mWidth, mHeight); 125d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen if (!wholeImage.contains(rectangle)) { 126d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen throw new IllegalArgumentException( 127d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen "rectangle is not inside the image"); 128bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen } 129bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen 130bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen if (quality < 0 || quality > 100) { 131bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen throw new IllegalArgumentException("quality must be 0..100"); 132bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen } 133bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen 134bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen if (stream == null) { 135d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen throw new IllegalArgumentException("stream cannot be null"); 136bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen } 137bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen 138d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen adjustRectangle(rectangle); 139d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen int[] offsets = calculateOffsets(rectangle.left, rectangle.top); 140d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen 141d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen return nativeCompressToJpeg(mData, mFormat, rectangle.width(), 142d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen rectangle.height(), offsets, mStrides, quality, stream, 143d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen new byte[WORKING_COMPRESS_STORAGE]); 144bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen } 145bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen 146d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen 147d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen /** 148bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen * @return the YUV data. 149bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen */ 150bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen public byte[] getYuvData() { 151bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen return mData; 152bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen } 153bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen 154bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen /** 1557fb597df52c7c6569a1c9ebacfb7629cf3dc6dc1Keiji Ariyama * @return the YUV format as defined in {@link ImageFormat}. 156bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen */ 157bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen public int getYuvFormat() { 158bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen return mFormat; 159bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen } 160bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen 161bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen /** 162bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen * @return the number of row bytes in each image plane. 163bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen */ 164bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen public int[] getStrides() { 165bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen return mStrides; 166bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen } 167bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen 168d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen /** 169d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen * @return the width of the image. 170d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen */ 171d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen public int getWidth() { 172d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen return mWidth; 173d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen } 174bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen 175d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen /** 176d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen * @return the height of the image. 177d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen */ 178d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen public int getHeight() { 179d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen return mHeight; 180d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen } 181d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen 182d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen int[] calculateOffsets(int left, int top) { 183d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen int[] offsets = null; 184a696f5d667227365da732481770767dcb330dd23Mathias Agopian if (mFormat == ImageFormat.NV21) { 185d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen offsets = new int[] {top * mStrides[0] + left, 186d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen mHeight * mStrides[0] + top / 2 * mStrides[1] 187d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen + left / 2 * 2 }; 188d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen return offsets; 189bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen } 190bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen 191a696f5d667227365da732481770767dcb330dd23Mathias Agopian if (mFormat == ImageFormat.YUY2) { 192d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen offsets = new int[] {top * mStrides[0] + left / 2 * 4}; 193d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen return offsets; 194bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen } 195bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen 196d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen return offsets; 197d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen } 198d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen 199d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen private int[] calculateStrides(int width, int format) { 200d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen int[] strides = null; 201a696f5d667227365da732481770767dcb330dd23Mathias Agopian if (format == ImageFormat.NV21) { 202d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen strides = new int[] {width, width}; 203d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen return strides; 204bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen } 205bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen 206a696f5d667227365da732481770767dcb330dd23Mathias Agopian if (format == ImageFormat.YUY2) { 207d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen strides = new int[] {width * 2}; 208d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen return strides; 209d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen } 210d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen 211d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen return strides; 212d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen } 213d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen 214d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen private void adjustRectangle(Rect rect) { 215d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen int width = rect.width(); 216d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen int height = rect.height(); 217a696f5d667227365da732481770767dcb330dd23Mathias Agopian if (mFormat == ImageFormat.NV21) { 218d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen // Make sure left, top, width and height are all even. 219d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen width &= ~1; 220d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen height &= ~1; 221d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen rect.left &= ~1; 222d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen rect.top &= ~1; 223d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen rect.right = rect.left + width; 224d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen rect.bottom = rect.top + height; 225bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen } 226bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen 227a696f5d667227365da732481770767dcb330dd23Mathias Agopian if (mFormat == ImageFormat.YUY2) { 228d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen // Make sure left and width are both even. 229d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen width &= ~1; 230d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen rect.left &= ~1; 231d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen rect.right = rect.left + width; 232d2391faa5d21a7513f321c03da0945277e291ad7Wei-Ta Chen } 233bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen } 234bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen 235bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen //////////// native methods 236bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen 237bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen private static native boolean nativeCompressToJpeg(byte[] oriYuv, 238bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen int format, int width, int height, int[] offsets, int[] strides, 239bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen int quality, OutputStream stream, byte[] tempStorage); 240bca2d613e0d6d2630fedd302c0d779b7610adbcfWei-Ta Chen} 241