はじめに
GUIに独自の表示を行うには、直接描画を行う機能が必要となります。このために用意されているのが、Graphics
クラスです。このクラスの基本的な使い方をマスターして、コンポーネントに自由に描画できるようになりましょう。
対象読者
- Javaに興味がある、けれどプログラミング経験がない、という人。
- Javaに興味がある、けれど何から手をつければいいか分からない、という人。
- Javaに興味はない、でも何でもいいからプログラミングをしたい、という人。
グラフィック描画の仕組み
AWTやSwingといったGUI構築のライブラリには、各種のコンポーネントが用意されています。これらを組み合わせれば、基本的な画面表示を行うことはでしょう。が、それ以上のことを行うには、独自に描画を行うための機能を理解する必要があります。
AWT/Swingのコンポーネントには、それぞれにGraphics
というクラスが組み込まれています。これはjava.awtパッケージにあるクラスで、そのコンポーネントの表示を行う働きを持つものです。一般に「グラフィック・コンテキスト」と呼ばれるのですが、要するに「描画に関する情報を管理しているもの」と考えてください。
このGraphics
には多数の描画用メソッドが用意されており、それらを呼び出すことでコンポーネントへの図形の描画を行うことができます。またjava.awtパッケージにあることからも分かるように、これはAWT/Swing両方で共通して利用されます。
このGraphics
は、コンポーネントに用意されているgetGraphics
というメソッドで得ることができます。では、実際にGraphics
を利用して描画する簡単なサンプルを作成してみましょう。
package codezine.java; import java.awt.*; import javax.swing.*; public class Sample extends JFrame { Graphics g; public Sample(){ this.setSize(300, 200); this.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); this.setVisible(true); this.g = this.getGraphics(); // 描画のサンプル g.setColor(Color.RED); g.fillOval(50, 50, 100, 100); g.dispose(); } public static void main(String[] args) { new Sample(); } }
これは、getGraphics
でthis
(つまり、表示されているウインドウJFrame
)のGraphics
を取得し、そのメソッドを呼び出してウインドウに図形を描画する簡単なサンプルです。実行すると、ウインドウに赤い円が表示されます(ただし! このソースコードには問題があります。詳細は後述)。
さっそく描画を行っている部分を見てみましょう。まず、this.getGraphics
でGraphics
インスタンスを取得していますね。それから、次のようにして描画に使う色を設定しています。
g.setColor(Color.RED);
Graphics
での図形の描画は「色を設定する」「描画をする」といったことの繰り返しになります。Graphics
では、描画図形の色に関する情報が保持されており、描画のためのメソッドを実行すると、この保持されている色を使って描画を行うようになります。そこで、最初にsetColor
というメソッドを呼び出して描画に使う色を設定しておくのです。
描画の色は、java.awtパッケージのColor
クラスを使って指定します。これは色に関する情報を管理するクラスです。RGBの輝度を指定して新たなColor
を作成することもできますが、主な色については最初からクラスフィールドとして用意されているのでそれを利用するとよいでしょう。ここではColor
クラスのRED
というクラスフィールドを使っています。名前から分かるように、赤のColor
インスタンスです。
続いて、円の描画を行います。これは、Graphics
クラスのfillOval
というメソッドを使います。このfillOval
は、描画図形の位置と大きさを引数で渡すと指定の図形を描画するというものです。Graphics
の描画メソッドは、大体このように位置と大きさを渡して描画させます。
そして、最後にGraphics
のdispose
というメソッドを呼び出しています。これは、このGraphics
インスタンスを破棄するものです。なんでこんなことをするの? と思うでしょうが、これには深いわけがあります。実は、このGraphics
は、その内部でJava仮想マシン外の機能(要するに、OSにあるAPIなど)の力を借りているのです。このため、インスタンスを作ると、OSのメモリを余計に消費してしまいます。そこで、「getGraphics
でGraphics
を取り出したときには、使い終わったらdispose
しておく」というのが、いわばマナーになっています。