OpenCvと直接関わらない投稿が続いたが、今回はもとに戻って OpenCvで 『画像サイズの変更』
画像サイズの変更は imgprocクラスの resizeメソッドで行います。
コンストラクタは 生成したjavadocによると
static void resize(Mat src, Mat dst, Size dsize)
static void resize(Mat src, Mat dst, Size dsize, double fx)
static void resize(Mat src, Mat dst, Size dsize, double fx, double fy)
static void resize(Mat src, Mat dst, Size dsize, double fx, double fy, int interpolation)
Mat src:変換元Mat
Mat dsc:変換先Mat
Size dsize:変換先サイズ
double fx,fy:変換倍率
なお dsizeがゼロの場合は fx,fyをもとに変換先サイズを決定し、逆にdsizeがゼロでなければfx,fyは無視されます。
int interpolation:画像のサイズを変更する際の補完手法 imgprocに以下の定数が準備されています。
- INTER_NEAREST 最近傍補間
- INTER_LINEAR バイリニア補間(デフォルト)
- INTER_AREA ピクセル領域の関係を利用したリサンプリング.画像を大幅に縮小する場合は,モアレを避けることができる良い手法です.しかし,画像を拡大する場合は, INTER_NEAREST メソッドと同様になります
- INTER_CUBIC 4×4 の近傍領域を利用するバイキュービック補間
- INTER_LANCZOS4 8×8 の近傍領域を利用する Lanczos法の補間
(OpenCv-CookBooksより)
画像を大幅に縮小するには、INTER_AREA補間が最良で、画像を拡大する場合は、INTER_CUBICか INTER_LINEARを使うと良いそうです。
最初に 画像(240*320ピクセル)をもとの画像で表示します。
String path=Environment.getExternalStorageDirectory()+"/DCIM/100ANDRO/suzuran.jpg"; Bitmap src = BitmapFactory.decodeFile(path); Bitmap src2 = src.copy(Bitmap.Config.ARGB_8888, true); src.recycle(); Mat mat = android.BitmapToMat(src2); src2.recycle(); Imgproc.resize(mat, mat, new Size(mat.width(),mat.height()), 0,0, Imgproc.INTER_LINEAR); Bitmap dsc= Bitmap.createBitmap(mat.width(), mat.height(), Bitmap.Config.ARGB_8888); android.MatToBitmap(mat, dsc); imgv = (ImageView)findViewById(R.id.imageView1); imgv.setImageBitmap(dsc);
うまくいきました。もっともこれじゃresizeメソッドを使う意味はありませんが(笑)
ハイライトされている部分を次のように変えて 横幅をぴったりにしてみます。
//画面サイズ取得 Matrix matrix = new Matrix(); DisplayMetrics metrics = new DisplayMetrics(); this.getWindowManager().getDefaultDisplay().getMetrics(metrics); int screenWidth = metrics.widthPixels; int screenHeight = metrics.heightPixels; //resize 比率取得 double fx = (double)screenWidth/(double)src2.getWidth(); double fy = (double)screenHeight/(double)src2.getHeight(); double f = Math.min(fx, fy); //resize Imgproc.resize(mat, mat, new Size(0,0), f,f, Imgproc.INTER_LINEAR);
うまくいきました。 このとき fx,fy の値をみると 2, 2.5 となっていて 結果 2倍(480*640)で表示されています。
以前書いたように 画面からはみ出すサイズの画像を表示してもそれなりに表示されたので 3倍(720*960)のサイズに拡大して表示してみます。 (1)の部分を
Imgproc.resize(mat, mat, new Size(mat.width() * 3,mat.height() * 3), 0, 0, Imgproc.INTER_LINEAR);
として実行すると
上下の表示位置こそ違い 別に横方向が欠けもせずぴったり表示されています。
見た目は同じでも 無駄なメモリを使うことは 間違いなく、百害あって一利なし 画面をオーバーするサイズの画像を表示することがないよう気をつけなきゃ!!
by Android2.2 with OpenCv 2.3.1 for Android |