2023.02.23

画像処理

画像の一部を切り出す

このサイトで紹介している画像操作クラスMyBufferedImage0」を利用して、JPEG/BMP/TIFFなどの画像の一部を切り出してをJPEG形式ファイル保存する方法を説明します。

切り出す範囲は、画像の左上のピクセル座標と、切り出し後の画像の幅と高さをピクセルで指定します。

MyBufferedImage0」には画像の読込、画像の保存、色の取得、色の設定など画像処理に必要なメソッドが用意されているので、比較的簡単に画像処理プログラムを作成することができます。

画像の切り出し

ここでの切り出し処理は、切り出す画像の外側の座標を指定することができます。画像の外側の色は、ソースコードの中で白色にしています。

画像の切り出し(外側)

切り出し方法

以下の方法で変換します。

①元の画像をMyBufferedImage0.readメソッドで読み込む

②切り出し後のサイズの画像をMyBufferedImage0.createメソッドで作成

③元の画像の色を取得し、切り出し後の画像に設定する

④切り出し後の画像をMyBufferedImage0.writeJPGメソッドで保存

以上です。

Javaソースコード

画像の一部を切り出すJavaソースコードです。MyBufferedImage0クラスを利用しています。

MySubImage.java

001
002
003
004
005
006
007
008
009
010
011
012
013
014
015
016
017
018
019
020
021
022
023
024
025
026
027
028
029
030
031
032
033
034
035
036
037
038
039
040
041
042
043
044
045
046
047
048
049
050
051
052
053
054
055
056
057
058
059
060
061
062
063
064
065
066
067
068
069
070
071
072
073
074
075
076
public class MySubImage {
	public static void main(String[] args) {
		// ファイル名
		String inname, outname;
		int x, y;	// 切り出す左上のピクセル座標
		int w, h;	// 切り出す画像サイズ

		// 入力した引数が6つ以上かを調べる
		if ( 6 > args.length ) {
			// 入力した引数が6つ未満の場合、使用方法を表示する
			System.out.println( "MySubImage [入力画像名]  [出力JPG名]  [左上のX座標]  [左上のY座標]  [切り出す画像の幅]  [切り出す画像の高さ]" );
			return;
		}

		// 入力画像名をinnameに代入(拡張子省略なし)
		inname  = args[ 0 ];
		// 出力JPG名をoutnameに代入(拡張子".jpg"省略なし)
		outname = args[ 1 ];

		// 引数を変数に代入
		try {
			// 引数を変換し、縁の幅に代入
			x = Integer.valueOf( args[ 2 ] );
			y = Integer.valueOf( args[ 3 ] );
			w = Integer.valueOf( args[ 4 ] );
			h = Integer.valueOf( args[ 5 ] );
		}
		catch( NumberFormatException ne ) {
			System.out.println( "引数が不正です" );
			return;
		}

		if ( ( 1 > w ) || ( 1 > h ) ) {
			System.out.println( "画像サイズが不正です" );
			return;
		}

		// 画像操作クラス
		MyBufferedImage0 inimg = new MyBufferedImage0();	// 入力用
		MyBufferedImage0 outimg = new MyBufferedImage0();	// 出力用

		// 入力画像の読み込み
		if ( !inimg.read( inname ) ) {
			System.out.println( "読み込みに失敗しました!(" + inname +")" );
			return;
		}

		// 出力用の画像の作成
		if ( !outimg.create( w, h, java.awt.image.BufferedImage.TYPE_3BYTE_BGR ) ) {
			System.out.println( "出力用の画像の作成に読み込みに失敗しました!" );
			return;
		}

		// 切り出し処理
		int defcolor =0xffffffff;	// 白色

		for ( int dy = 0; dy < h; dy++ ) {
			for ( int dx = 0; dx < w; dx++ ) {
				// 入力画像から色を取得
				int color = inimg.getRGB( dx + x, dy + y, defcolor );

				// 出力画像に色を設定
				outimg.setRGB( dx, dy, color );
			}
		}

		// JPG画像の保存
		if ( !outimg.writeJPG( outname ) ) {
			System.out.println( "保存に失敗しました!(" + outname +")" );
			return;
		}

		// 正常に終了
		System.out.println( "正常に終了しました" );
	}
}

このソースのコンパイルには、JavaソースファイルMyBufferedImage0.Java」が必要です。以下から取得してください。

BufferedImageクラスを利用して、利便性の高い画像操作クラスを作成しました。興味のある方は、是非ご覧ください。

2022.11.16

実行方法

コンパイル ソースコードが「ANSI」の場合

C:\talavax\javasample>javac -encoding sjis MySubImage.java

コンパイル ソースコードが「UTF-8」の場合

C:\talavax\javasample>javac MySubImage.java

MyBufferedImage0.Javaは、指定しなくてもコンパイルされます。

sampleimage001_400x320.jpgの一部を切り出してmysubimage_output.jpgに保存

java MySubImage sampleimage001_400x320.jpg mysubimage_output.jpg 140 50 200 150

sampleimage001_400x320.jpgの左上の座標( 140, 50 )から幅200ピクセル、高さ150ピクセルで切り出して、mysubimage_output.jpgに保存します。

切り出し結果

切り出し元の画像 切り出し後の画像

Javaソースコードの解説

ここから、ソースコードを詳しく解説していきます。

001
public class MySubImage {

クラス名を、MySubImageとしています。

002
	public static void main(String[] args) {

このmainメソッドからプログラムを実行します。

004
005
006
		String inname, outname;
		int x, y;	// 切り出す左上のピクセル座標
		int w, h;	// 切り出す画像サイズ

このプログラムで使うファイル名を格納する変数を宣言しています。

008
009
010
011
012
013
		// 入力した引数が6つ以上かを調べる
		if ( 6 > args.length ) {
			// 入力した引数が6つ未満の場合、使用方法を表示する
			System.out.println( "MySubImage [入力画像名]  [出力JPG名]  [左上のX座標]  [左上のY座標]  [切り出す画像の幅]  [切り出す画像の高さ]" );
			return;
		}

6つ以上の引数が与えられたかをチェックし、6つ未満の場合に、使い方のメッセージを表示し、returnによってmainメソッドを抜けています。

015
016
017
018
		// 入力画像名をinnameに代入(拡張子省略なし)
		inname  = args[ 0 ];
		// 出力JPG名をoutnameに代入(拡張子".jpg"省略なし)
		outname = args[ 1 ];

与えられた先頭の2つの引数をそれぞれ、入力画像名の変数(inname)と出力PNG名の変数(outname)に代入しています。

020
021
022
023
024
025
026
027
028
029
030
031
		// 引数を変数に代入
		try {
			// 引数を変換し、縁の幅に代入
			x = Integer.valueOf( args[ 2 ] );
			y = Integer.valueOf( args[ 3 ] );
			w = Integer.valueOf( args[ 4 ] );
			h = Integer.valueOf( args[ 5 ] );
		}
		catch( NumberFormatException ne ) {
			System.out.println( "引数が不正です" );
			return;
		}

与えられた引数お3~6番目のをそれぞれ、画像の左上のx座標画像の左上のy座標、切り出し後の幅w、切り出し後の高さhに代入しています。

033
034
035
036
		if ( ( 1 > w ) || ( 1 > h ) ) {
			System.out.println( "画像サイズが不正です" );
			return;
		}

切り出し後の幅w、切り出し後の高さhのどちらかが1未満の場合にメッセージをコンソール出力して、return文mainメソッドを抜けています。

038
039
040
		// 画像操作クラス
		MyBufferedImage0 inimg = new MyBufferedImage0();	// 入力用
		MyBufferedImage0 outimg = new MyBufferedImage0();	// 出力用

画像を操作するMyBufferedImage0クラスの実体inimgとoutimgを作成しています。

inimgは切り出す元の画像を格納するオブジェクトで、outimgは切り出し後の画像を格納するオブジェクトです。

042
043
044
045
046
		// 入力画像の読み込み
		if ( !inimg.read( inname ) ) {
			System.out.println( "読み込みに失敗しました!(" + inname +")" );
			return;
		}

MyBufferedImage0.readメソッドで、画像ファイルinnameをinimgに読み込んでいます。

MyBufferedImage0.readメソッド

boolean create( String imgname )
・指定した画像ファイルを読み込みます。

  パラメータ imgname  : フルパスの画像ファイル名(拡張子は省略不可)

  戻り値    true   : 画像の読み込みに成功
         false  : 画像の読み込みに失敗
048
049
050
051
052
		// 出力用の画像の作成
		if ( !outimg.create( w, h, java.awt.image.BufferedImage.TYPE_3BYTE_BGR ) ) {
			System.out.println( "出力用の画像の作成に読み込みに失敗しました!" );
			return;
		}

MyBufferedImage0.createメソッドで、切り出し後のサイズの画像を作成しています。

画像のイメージ形式には、java.awt.image.BufferedImage.TYPE_3BYTE_BGRにしています。24ビットカラーです。

MyBufferedImage0.createメソッド

boolean create( int width, int height, int type )
・指定したサイズ、種類の画像を作成します。

  パラメータ width  : 作成する画像の横のピクセル数
        height : 作成する画像の縦のピクセル数
        type   : 作成するイメージの形式
           指定例) BufferedImage.TYPE_INT_RGB

  戻り値    true   : 画像の作成に成功
         false  : 画像の作成に失敗
054
055
		// 切り出し処理
		int defcolor =0xffffffff;	// 白色

ここから、切り出し処理です。

int型変数defcolorは、元の画像の外側を切り出した際に使う色で、色を指定しています。任意の色に変更可能です。

057
058
		for ( int dy = 0; dy < h; dy++ ) {
			for ( int dx = 0; dx < w; dx++ ) {

for文2重ループでを作成しています。

切り出し後の画像ピクセル座標(dxは0~w-1、dyは0~h-1)を処理するループにしています。

059
060
				// 入力画像から色を取得
				int color = inimg.getRGB( dx + x, dy + y, defcolor );

出力画像(切り出し後の画像)のピクセル座標( dx, dy )に、変数colorに格納されている色を設定します。

ピクセル座標( dx + x, dy + y )が、入力画像の外側の座標の場合、変数colorに変数defcolorの値が代入されます。この処理により、入力画像の外側を切り出したときの、外側の色は、defcolorで指定した色になります。

MyBufferedImage0.getRGBメソッド

int getRGB( int x, int y, int defcolor )
・指定した座標の色を取得します。

  パラメータ x  : ピクセルのx座標
        y  : ピクセルのy座標
        defcolor   : (x,y)が画像の範囲外の場合に戻す値

  戻り値    RGBを合成した色
062
063
				// 出力画像に色を設定
				outimg.setRGB( dx, dy, color );

ピクセル座標( dx, dy )に、取得した色colorを設定しています。

MyBufferedImage0.setRGBメソッド

boolean setRGB( int x, int y, int color )
・指定した座標の色を設定します。

  パラメータ x  : ピクセルのx座標
        y  : ピクセルのy座標
        color   : 設定するRGBを合成した色

  戻り値    (x,y)が画像の範囲内の場合、true
         (x,y)が画像の範囲外の場合、false
boolean setRGB( int x, int y, int r, int g, int b )
・指定した座標の色を設定します。

  パラメータ x  : ピクセルのx座標
        y  : ピクセルのy座標
        r  : 赤の輝度
        g  : 緑の輝度
        b  : 青の輝度

  戻り値    (x,y)が画像の範囲内の場合、true
         (x,y)が画像の範囲外の場合、false

  詳細         r、g、bは自動で0~255の範囲に変換されます。
067
068
069
070
071
		// JPG画像の保存
		if ( !outimg.writeJPG( outname ) ) {
			System.out.println( "保存に失敗しました!(" + outname +")" );
			return;
		}

MyBufferedImage0.writeJPGメソッドで、ファイル名outnameでJPEG画像を保存しています。

MyBufferedImage0.writeJPGメソッド

boolean writeJPG( String imgname )
・画像をJPEG形式のファイルで保存します。

  パラメータ imgname  : フルパスのJPEG画像ファイル名

  戻り値    true   : 画像の読み込みに成功
         false  : 画像の読み込みに失敗
073
074
		// 正常に終了
		System.out.println( "正常に終了しました" );

保存に成功したメッセージをprintlnコンソール出力しています。全ての処理が正常終了すると、ここまで処理が実行されます。

関連コンテンツ

画像フォーマット形式・色・大きさ・傾きなどの変更、特定の図形(文字・記号など)を見つけたり、取り出したりする画像処理について詳しく解説。

2015.11.29

一般に使われている画像フォーマットには、いろいろな種類があります。画像フォーマットBMP、JPEG、PNG、GIF、TIFFの特徴を知ってますか?

2015.11.29

このサイトのオリジナルクラスのMyBufferedImage0クラスを利用して、JPEG、BMP、TIFFなどの各種画像ファイルをPNG形式のファイルに保存するプログラムを紹介しています。

2022.11.18

このサイトのオリジナルクラスのMyBufferedImage0クラスを利用して、JPEG、PNG、BMP、TIFFなどの各種画像の横と縦のピクセル数を求めるプログラムを紹介しています。

2022.11.19

条件式を判断して処理を分岐する方法を詳しく説明しています。

2023.03.20

変数やクラスに格納されている値をコンソール出力する方法は?

2020.03.23

メソッドを抜けるときに使用するreturn文について説明しています。

2020.03.20

プログラムの最初に実行されるメソッドは?

2022.12.13

プログラミングで使う変数って何?

2020.03.23

Javaのプログラムを書いてみませんか?プログラムの書き方をくわしく説明しています。

2020.03.23

「Javaソースコード」から実行可能な「オブジェクトコード」に変換する方法をくわしく説明しています。

2020.03.23

BufferedImageクラスを利用して、利便性の高い画像操作クラスを作成しました。興味のある方は、是非ご覧ください。

2022.11.16

ファイルは、データを取り扱うとき管理単位の一つで、ハードディスク、SSD,USBメモリ、CD/DVD/ブルーレイなどの記憶媒体に保存するときに使われます。詳しくは、記事をご覧ください。

2022.08.12

画像って何?

2022.07.25

画像の座標系はどのように定義されていますか?

2020.03.23

デジタル画像データを構成している要素について解説しています。

2015.12.22

メソッドの定義方法を詳しく解説しています。Javaのサンプルソースコードを使った説明もあります。

2020.03.23

平面上の位置を表す座標系の1つXY座標系について詳しく解説。

2020.03.23

プログラミング言語とは?種類や特徴について説明しています。

2022.08.03

Javaプログラムの構成について解説しています。詳しくは、こちらをご覧ください。

2020.03.23

コンピュータに保存されたファイルを特定するための名前がファイル名です。その付け方は?

2016.11.23

オブジェクト指向の考え方を、Javaのソースコードを使って詳しく解説しています。興味のある方は、是非ご覧ください。

2022.09.02

PCやスマートフォンのディスプレイに表示されている色、プリンターで印刷される色の仕組みについて解説しています。

2020.03.23

処理を繰り返すために使用するfor文について解説しています。

2020.03.23

for文などのループ中に、さらにループがある多重ループについて解説しています。

2021.02.09

繰り返し処理の作り方を解説しています。

2016.03.02

広告