|
|
PaintTest 色属性の設定 |
H.Kamifuji . |
Java2D において図形の線や塗りつぶしを行う色の設定方法について、事例にて説明します。 現在(2021/08)では、JDK-16.0.2 にアップされています。一部、上位互換について、見直しを行っていきます。 現在(2021/11)では、JDK-17.0.1 にアップされています。一部、上位互換について、見直しを行っていきます。 現在(2023/04)では、JDK-20.0.1 にアップされています。一部、上位互換について、見直しを行っていきます。 現在(2024/10)では、JDK-23 にアップされています。一部、上位互換について、見直しを行っていきます。 |
|
図形の線を描画したり塗りつぶしたりする為の色の指定方法について確認します。色を設定するには図形が描画される前に Graphics2D クラスで用意されている「setPaint」メソッドを使って色に関する属性を設定します。setPaint public abstract void setPaint(Paint paint)Graphics2D コンテキストに Paint 属性を設定します。このメソッドを null Paint オブジェクトで呼び出しても、この Graphics2D の現在の Paint 属性には影響しません。 パラメータ: paint - 描画プロセスで色を生成するために使われる Paint、または null 引数にはPaintインターフェースを実装したクラスのオブジェクトを指定します。 Paintインターフェース色の指定と言っても単純な色の指定の他にグラデーションパターンを指定したり画像を使って塗りつぶしを行ったりすることが可能です。それぞれPaintインターフェースを実装したクラスを使うことで実現できます。 Paintインターフェースを実装している主なクラスは以下の通りです。
※「LinearGradientPaint」クラス及び「RadialGradientPaint」クラスはJ2SE1.6から導入されたクラスです。 public void paintComponent(Graphics g){ Graphics2D g2 = (Graphics2D)g; g2.setPaint(Color.RED); }各クラスを使った指定方法は次項のページ以降で確認していきます。 |
まず単純な色を指定する方法を確認します。「setPaint」メソッドの引数にColorクラスのオブジェクトを指定します。 ※Colorクラスについては『Colorクラス』を参照して下さい。 具体的には次のように記述します。 public void paintComponent(Graphics g) { Graphics2D g2 = (Graphics2D)g; g2.setPaint(Color.RED); g2.draw(new Ellipse2D.Double(30, 40, 50, 50)); g2.setPaint(new Color(210, 30, 50)); g2.fill(new RoundRectangle2D.Double(30, 130, 110, 50, 10, 20)); }「setPaint」メソッドを実行した後で実行された「draw」メソッド及び「fill」メソッドで設定が反映されます。 サンプルプログラム下記のサンプルを実行してみよう。/** * Colorクラスによる色の指定 */ import javax.swing.*; import java.awt.Graphics; import java.awt.Graphics2D; import java.awt.RenderingHints; import java.awt.geom.*; import java.awt.Color; import java.awt.BasicStroke; public class PaintTest1 extends JPanel { public static void main(String[] args) { JFrame frame = new JFrame(); PaintTest1 app = new PaintTest1(); frame.getContentPane().add(app); frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); frame.setBounds(10, 10, 300, 200); frame.setTitle("タイトル"); frame.setVisible(true); } public void paintComponent(Graphics g) { Graphics2D g2 = (Graphics2D)g; g2.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON); BasicStroke wideStroke = new BasicStroke(4.0f); g2.setStroke(wideStroke); g2.setPaint(Color.BLUE); g2.draw(new Ellipse2D.Double(70, 20, 50, 50)); g2.setPaint(Color.RED); g2.draw(new Ellipse2D.Double(110, 20, 50, 50)); g2.setPaint(Color.GREEN); g2.draw(new Ellipse2D.Double(150, 20, 50, 50)); g2.setPaint(Color.PINK); g2.draw(new Ellipse2D.Double(190, 20, 50, 50)); g2.setPaint(Color.YELLOW); g2.fill(new RoundRectangle2D.Double(30, 100, 110, 50, 10, 20)); } }上記をコンパイルした後で実行すると次のように表示されます。 ![]() |
主に塗りつぶし用としてグラデーションパターンを指定する方法を確認します。「setPaint」メソッドの引数にGradientPaint クラスのオブジェクトを指定します。 クラス図は次のようになっています。 java.lang.Object ⇒ java.awt.GradientPaint public class GradientPaint extends Object implements Paintコンストラクタは次の4つが用意されています。
GradientPaintクラスでは色が指定された2つの点を使ってグラデーションパターンを設定します。またグラデーションのパターンとして循環式と非循環式を指定することが出来ます。 循環式と非循環式の違いそれではまず循環式と非循環式によるグラデーションパターンの違いを確認してみます。 次のような長方形の領域を塗りつぶす場合を例として考えてみます。 ![]() GradientPaintクラスでは2つの点に対してそれぞれ色を指定します。この2点間の間の領域で2つの色を使ったグラデーションが作成されます。 ![]() まず非循環式の場合です。非循環式の場合は2点間の間の領域はグラデーションとなりますが、それぞれの点の外側の領域はグラデーションが行われず点に設定された色が適用されます。 ![]() 次に循環式の場合です。循環式の場合は2点間の間の領域はグラデーションとなる点は同じですがそれぞれの点の外側の領域についても同じようにグラデーションが適用されます。 ![]() 具体的な使用方法は次項のページ以降で確認します。 |
非循環式によるグラデーションを設定してみます。GradientPaintクラスのコンストラクタの中で非循環式を使う場合は次のコンストラクタを使用します。GradientPaint public GradientPaint(float x1, float y1, Color color1, float x2, float y2, Color color2)シンプルな非循環式の GradientPaint オブジェクトを構築します。 パラメータ: x1 - ユーザー空間で最初に指定された Point の x 座標 y1 - ユーザー空間で最初に指定された Point の y 座標 color1 - 最初に指定された Point の Color x2 - ユーザー空間で 2 番目に指定された Point の x 座標 y2 - ユーザー空間で 2 番目に指定された Point の y 座標 color2 - 2 番目に指定された Point の Color 例外: NullPointerException - いずれか 1 つのカラーが null の場合 グラデーションを決定する為の2つの点の座標(x1, y1)と(x2, y2)を指定し、それぞれの点に設定する色を表すColorクラスのオブジェクトを引数に指定します。(Colorクラスについては『Colorクラス』を参照して下さい)。 具体的には次のように記述します。 public void paintComponent(Graphics g) { Graphics2D g2 = (Graphics2D)g; GradientPaint gradient = new GradientPaint( 50.0f, 50.0f, Color.ORANGE, 190.0f, 110.0f, Color.YELLOW ); g2.setPaint(gradient); g2.fill(new Rectangle2D.Double(20, 20, 200, 130)); }「setPaint」メソッドを実行した後で実行された「draw」メソッド及び「fill」メソッドで設定が反映されます。 Point2Dクラスによる座標指定2つの点の座標を指定する方法としてPoint2Dクラスのオブジェクトを使用するコンストラクタも用意されています。 GradientPaint public GradientPaint(Point2D pt1, Color color1, Point2D pt2, Color color2)シンプルな非循環式の GradientPaint オブジェクトを構築します。 パラメータ: pt1 - ユーザー空間で最初に指定された Point color1 - 最初に指定された Point の Color pt2 - ユーザー空間で 2 番目に指定された Point color2 - 2 番目に指定された Point の Color 例外: NullPointerException - カラーとポイントのいずれか 1 つが null の場合 Point2Dクラスは二次元空間における座標を表す2つの値を保持するためのクラスです。Point2Dクラスはabstractクラスであるため実際にはサブクラスであるPoint2D.DoubleクラスやPoint2D.Floatクラスを使います。詳しくは『Point2Dクラス』を参照して下さい。 具体的には次のように記述します。 public void paintComponent(Graphics g) { Graphics2D g2 = (Graphics2D)g; GradientPaint gradient = new GradientPaint( new Point2D.Double(50.0d, 50.0d), Color.ORANGE, new Point2D.Double(190.0f, 110.0f), Color.YELLOW ); g2.setPaint(gradient); g2.fill(new Rectangle2D.Double(20, 20, 200, 130)); } サンプルプログラム下記のサンプルを実行してみよう。/** * 非循環式によるグラデーション表示 */ import javax.swing.*; import java.awt.Graphics; import java.awt.Graphics2D; import java.awt.RenderingHints; import java.awt.geom.*; import java.awt.Color; import java.awt.GradientPaint; public class PaintTest2 extends JPanel{ public static void main(String[] args){ JFrame frame = new JFrame(); PaintTest2 app = new PaintTest2(); frame.getContentPane().add(app); frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); frame.setBounds(10, 10, 300, 200); frame.setTitle("タイトル"); frame.setVisible(true); } public void paintComponent(Graphics g){ Graphics2D g2 = (Graphics2D)g; g2.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON); GradientPaint gradient = new GradientPaint( 50.0f, 50.0f, Color.ORANGE, 190.0f, 110.0f, Color.YELLOW ); g2.setPaint(gradient); g2.fill(new Rectangle2D.Double(20, 20, 200, 130)); /* g2.setPaint(Color.black); g2.draw(new Ellipse2D.Double(45, 45, 10, 10)); g2.draw(new Ellipse2D.Double(185, 105, 10, 10)); */ } }上記をコンパイルした後で実行すると次のように表示されます。 ![]() 上記のサンプルでコメントとなっている部分があります。コメントを外すとグラデーションの基準となっている2つの点が円で表示されます。 ![]() |
循環式によるグラデーションを設定してみます。GradientPaintクラスのコンストラクタの中で非循環式を使う場合は次のコンストラクタを使用します。GradientPaint public GradientPaint(float x1, float y1, Color color1, float x2, float y2, Color color2, boolean cyclic)boolean パラメータに応じて、循環式または非循環式の GradientPaint オブジェクトを構築します。 パラメータ: x1 - ユーザー空間で最初に指定された Point の x 座標 y1 - ユーザー空間で最初に指定された Point の y 座標 color1 - 最初に指定された Point の Color x2 - ユーザー空間で 2 番目に指定された Point の x 座標 y2 - ユーザー空間で 2 番目に指定された Point の y 座標 color2 - 2 番目に指定された Point の Color cyclic - グラデーションパターンが 2 色を繰り返し循環する場合は true、そうでない場合は false 例外: NullPointerException - カラーとポイントのいずれか 1 つが null の場合 グラデーションを決定する為の2つの点の座標(x1, y1)と(x2, y2)を指定し、それぞれの点に設定する色を表すColorクラスのオブジェクトを引数に指定します。(Colorクラスについては『Colorクラス』を参照して下さい)。 そして最後の引数にグラデーションパターンとして循環式かどうかを表すboolean型の値を設定します。循環式にする場合は「true」を設定して下さい。(「false」を設定すれば非循環式として利用できます)。 具体的には次のように記述します。 public void paintComponent(Graphics g) { Graphics2D g2 = (Graphics2D)g; GradientPaint gradient = new GradientPaint( 50.0f, 50.0f, Color.ORANGE, 190.0f, 110.0f, Color.YELLOW, true ); g2.setPaint(gradient); g2.fill(new Rectangle2D.Double(20, 20, 200, 130)); }「setPaint」メソッドを実行した後で実行された「draw」メソッド及び「fill」メソッドで設定が反映されます。 Point2Dクラスによる座標指定2つの点の座標を指定する方法としてPoint2Dクラスのオブジェクトを使用するコンストラクタも用意されています。 GradientPaint public GradientPaint(Point2D pt1, Color color1, Point2D pt2, Color color2, boolean cyclic)boolean パラメータに応じて、循環式または非循環式の GradientPaint オブジェクトを構築します。 パラメータ: pt1 - ユーザー空間で最初に指定された Point color1 - 最初に指定された Point の Color pt2 - ユーザー空間で 2 番目に指定された Point color2 - 2 番目に指定された Point の Color cyclic - グラデーションパターンが 2 色を繰り返し循環する場合は true、そうでない場合は false 例外: NullPointerException - カラーとポイントのいずれか 1 つが null の場合 Point2Dクラスは二次元空間における座標を表す2つの値を保持するためのクラスです。Point2Dクラスはabstractクラスであるため実際にはサブクラスであるPoint2D.DoubleクラスやPoint2D.Floatクラスを使います。詳しくは『Point2Dクラス』を参照して下さい。 具体的には次のように記述します。 public void paintComponent(Graphics g) { Graphics2D g2 = (Graphics2D)g; GradientPaint gradient = new GradientPaint( new Point2D.Double(50.0d, 50.0d), Color.ORANGE, new Point2D.Double(190.0f, 110.0f), Color.YELLOW, true ); g2.setPaint(gradient); g2.fill(new Rectangle2D.Double(20, 20, 200, 130)); } サンプルプログラム下記のサンプルを実行してみよう。/** * 循環式によるグラデーション表示 */ import javax.swing.*; import java.awt.Graphics; import java.awt.Graphics2D; import java.awt.RenderingHints; import java.awt.geom.*; import java.awt.Color; import java.awt.GradientPaint; public class PaintTest3 extends JPanel { public static void main(String[] args) { JFrame frame = new JFrame(); PaintTest3 app = new PaintTest3(); frame.getContentPane().add(app); frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); frame.setBounds(10, 10, 300, 200); frame.setTitle("タイトル"); frame.setVisible(true); } public void paintComponent(Graphics g) { Graphics2D g2 = (Graphics2D)g; g2.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON); GradientPaint gradient = new GradientPaint( 90.0f, 70.0f, Color.RED, 150.0f, 90.0f, Color.BLUE, true ); g2.setPaint(gradient); g2.fill(new Rectangle2D.Double(20, 20, 200, 130)); /* g2.setPaint(Color.black); g2.draw(new Ellipse2D.Double(85, 65, 10, 10)); g2.draw(new Ellipse2D.Double(145, 85, 10, 10)); */ } }上記をコンパイルした後で実行すると次のように表示されます。 ![]() 上記のサンプルでコメントとなっている部分があります。コメントを外すとグラデーションの基準となっている2つの点が円で表示されます。 ![]() 今回は循環式ですので、この2つの点の間にある領域はグラデーションとして表示されており、点よりも外側の領域も同じグラデーションが繰り返し適用されます。下記は循環式を非循環式にした場合です。比べてみて下さい。 ![]() |
主に塗りつぶし用としてテクスチャーを使って塗りつぶす方法を確認します。「setPaint」メソッドの引数にTexturePaintクラスのオブジェクトを指定します。 クラス図は次のようになっています。 java.lang.Object ⇒ java.awt.TexturePaint public class TexturePaint extends Object implements Paintコンストラクタは1つだけ用意されています。
1番目の引数に塗りつぶす元となる画像を表すBufferedImageクラスのオブジェクトを指定します。(BufferedImageクラスについては『BufferedImageの使い方』を参照して下さい)。 1番目の引数で指定した画像を塗りつぶす領域いっぱいに並べていくことであたかも画像を使って塗りつぶしたようにすることが出来ます。その時読み込んだ画像のオリジナルの大きさで使用するのではなく、2番目の引数で指定した大きさに調整した上で塗りつぶしが行われます。 2番目の引数であるRectangle2Dクラスは位置とサイズの情報を保存するためのクラスです。始点の座標(x, y)と大きさ(width, height)の情報を持ちます。Rectangle2Dクラスはabstractクラスであるため実際にはサブクラスであるRectangle2D.DoubleクラスやRectangle2D.Floatクラスを使います。詳しくは『Rectangle2Dクラス』を参照して下さい。 具体的には次のように記述します。 public void paintComponent(Graphics g) { Graphics2D g2 = (Graphics2D)g; BufferedImage img = new BufferedImage(45, 59, BufferedImage.TYPE_INT_RGB); File f = new File("./img/sample.png"); try { img = ImageIO.read(f); }catch (IOException ex) { ex.printStackTrace(); } Rectangle2D.Double rec = new Rectangle2D.Double(0, 0, img.getWidth(), img.getHeight()); g2.setPaint(new TexturePaint(img, rec)); g2.fill(new Rectangle2D.Double(20, 20, 200, 130)); }「setPaint」メソッドを実行した後で実行された「draw」メソッド及び「fill」メソッドで設定が反映されます。 サンプルプログラム下記のサンプルを実行してみよう。/** * TexturePaintクラスによるテクスチャーによる塗りつぶし */ import javax.swing.*; import java.awt.Graphics; import java.awt.Graphics2D; import java.awt.RenderingHints; import java.awt.geom.*; import java.awt.TexturePaint; import java.awt.image.BufferedImage; import java.io.File; import javax.imageio.ImageIO; import java.io.IOException; public class PaintTest4 extends JPanel { public static void main(String[] args) { JFrame frame = new JFrame(); PaintTest4 app = new PaintTest4(); frame.getContentPane().add(app); frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); frame.setBounds(10, 10, 300, 200); frame.setTitle("タイトル"); frame.setVisible(true); } public void paintComponent(Graphics g) { Graphics2D g2 = (Graphics2D)g; BufferedImage img = new BufferedImage(45, 59, BufferedImage.TYPE_INT_RGB); File f = new File("./img/uma_b1.gif"); try { img = ImageIO.read(f); }catch (IOException ex){ ex.printStackTrace(); } Rectangle2D.Double rec = new Rectangle2D.Double(0, 0, img.getWidth(), img.getHeight()); g2.setPaint(new TexturePaint(img, rec)); g2.fill(new Rectangle2D.Double(20, 20, 200, 130)); } }上記をコンパイルした後で実行すると次のように表示されます。 ![]() 今回はオリジナルの画像サイズのまま領域内に並べて表示しました。 ではもう1つ試してみます。同じ画像ファイルを使用していますが今度はサイズを1/2に縮小した状態で塗りつぶしてみます。 下記のサンプルを実行してみよう。 /** * TexturePaintクラスによるテクスチャーによる塗りつぶし(2) */ import javax.swing.*; import java.awt.Graphics; import java.awt.Graphics2D; import java.awt.RenderingHints; import java.awt.geom.*; import java.awt.TexturePaint; import java.awt.image.BufferedImage; import java.io.File; import javax.imageio.ImageIO; import java.io.IOException; public class PaintTest5 extends JPanel { public static void main(String[] args){ JFrame frame = new JFrame(); PaintTest5 app = new PaintTest5(); frame.getContentPane().add(app); frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); frame.setBounds(10, 10, 300, 200); frame.setTitle("タイトル"); frame.setVisible(true); } public void paintComponent(Graphics g) { Graphics2D g2 = (Graphics2D)g; BufferedImage img = new BufferedImage(45, 59, BufferedImage.TYPE_INT_RGB); File f = new File("./img/uma_b1.gif"); try { img = ImageIO.read(f); }catch (IOException ex){ ex.printStackTrace(); } Rectangle2D.Double rec = new Rectangle2D.Double(0, 0, img.getWidth() / 2, img.getHeight() / 2); g2.setPaint(new TexturePaint(img, rec)); g2.fill(new Rectangle2D.Double(20, 20, 200, 130)); } }上記をコンパイルした後で実行すると次のように表示されます。 ![]() |
主に塗りつぶし用としてグラデーションパターンを指定する方法を確認します。「setPaint」メソッドの引数にLinearGradientPaintクラスのオブジェクトを指定します。以前から使われていたGradientPaintクラスをより高度にした線形グラデーションの設定が行えます。 クラス図は次のようになっています。 java.lang.Object ⇒ java.awt.MultipleGradientPaint ⇒ java.awt.LinearGradientPaint public final class LinearGradientPaint extends MultipleGradientPaintコンストラクタは次の5つが用意されています。
LinearGradientPaintクラスでは始点と終点の2つの点を指定するのはGradientPaintクラスと同じですが、この2点間の間に任意の個数の色を指定してグラデーションの色分布を指定することが出来ます。 またグラデーション方法として非循環式の他に循環式(反射)と循環式(繰り返し)の3パターンから選択できます。(GradientPaintクラスで使っていた循環式は循環式(反射)と同じです)。 それでは2番目のコンストラクタを見てみます。 LinearGradientPaint public LinearGradientPaint(float startX, float startY, float endX, float endY, float[] fractions, Color[] colors, MultipleGradientPaint.CycleMethod cycleMethod)デフォルトの sRGB カラースペースを使用して、LinearGradientPaint を構築します。 パラメータ: startX - ユーザー空間でグラデーション軸の始点の X 座標 startY - ユーザー空間でグラデーション軸の始点の Y 座標 endX - ユーザー空間でグラデーション軸の終点の X 座標 endY - ユーザー空間でグラデーション軸の終点の Y 座標 fractions - 0.0 - 1.0 の範囲の数値。 グラデーションでの色分布を指定する colors - 各小数値に対応する色の配列 cycleMethod - NO_CYCLE、REFLECT、 REPEAT のいずれか 例外: NullPointerException - fractions 配列が null の場合、 colors 配列が null の場合、 または cycleMethod が null の場合 IllegalArgumentException - 始点と終点が同じ点である場合、 fractions.length != colors.length である場合、colors のサイズが 2 より小さい場合、 fractions の値が 0.0 より小さいか 1.0 より大きい 場合、 または fractions が厳密な昇順で指定されない場合 1番目と2番目の引数で始点座標を、3番目と4番目の引数で終点座標を指定します。 5番目の引数では区間内で色を設定したい位置を指定します。始点から終点までの区間に対して、始点を「0.0」終点を「1.0」と考えます。その区間に対して色を設定したい位置をfloat型の配列で指定します。 6番目の引数では5番目の引数で指定した色を設定する位置に対して実際の色をColorクラスのオブジェクトの配列で指定します。指定する色の数は5番目の数と同じである必要があります。 具体的には次のように記述します。 float[] dist = {0.2f, 0.4f, 1.0f}; Color[] colors = {Color.RED, Color.WHITE, Color.BLUE};この場合は区間内で合計3つの位置に色を指定していることになります。なお色を指定する位置で始点である「0.0f」や「1.0f」を指定しなかった場合は始点や終点に一番近い色が指定されたものとして扱われます。 例えば次のように記述した場合を考えてみます。 float[] dist = {0.2f, 0.4f, 1.0f}; Color[] colors = {Color.RED, Color.WHITE, Color.BLUE};この場合は次のように記述した場合と同じです。 float[] dist = {0.0f, 0.2f, 0.4f, 1.0f}; Color[] colors = {Color.RED, Color.RED, Color.WHITE, Color.BLUE};7番目の引数ではグラデーションの表示方法を指定します。指定できる値は次の3つです。
非循環式の場合は始点と終点の間の区間だけにグラデーションが適用されます。循環式(反射)の場合は始点と終点の外側の区間についてそれぞれの点に対して反射するようにグラデーションが適用されます。循環式(繰り返し)の場合は始点と終点の外側の区間についても始点と終点の間のグラデーションが繰り返し適用されます。 具体的には次のように記述します。 public void paintComponent(Graphics g) { Graphics2D g2 = (Graphics2D)g; float[] dist = {0.0f, 0.4f, 1.0f}; Color[] colors = {Color.RED, Color.WHITE, Color.BLUE}; LinearGradientPaint gradient = new LinearGradientPaint( 50.0f, 50.0f, 190.0f, 110.0f, dist, colors, MultipleGradientPaint.CycleMethod.NO_CYCLE ); g2.setPaint(gradient); g2.fill(new Rectangle2D.Double(20, 20, 200, 130)); }「setPaint」メソッドを実行した後で実行された「draw」メソッド及び「fill」メソッドで設定が反映されます。 Point2Dクラスによる座標指定2つの点の座標を指定する方法としてPoint2Dクラスのオブジェクトを使用するコンストラクタも用意されています。4番目のコンストラクタを見てみます。LinearGradientPaint public LinearGradientPaint(Point2D start, Point2D end, float[] fractions, Color[] colors, MultipleGradientPaint.CycleMethod cycleMethod)デフォルトの sRGB カラースペースを使用して、LinearGradientPaint を構築 します。 パラメータ: start - ユーザー空間内でグラデーション軸の始点を表す Point2D end - ユーザー空間内でグラデーション軸の終点を表す Point2D fractions - 0.0 - 1.0 の範囲の数値。 グラデーションでの色分布を指定する colors - 各小数値に対応する色の配列 cycleMethod - NO_CYCLE、REFLECT、 REPEAT のいずれか 例外: NullPointerException - 点のいずれかが null の場合、fractions 配列が null の場合、 colors 配列が null の場合、 または cycleMethod が null の場合 IllegalArgumentException - 始点と終点が同じ点である場合、 fractions.length != colors.length である場合、 colors のサイズが 2 より小さい場合、 fractions の値が 0.0 より小さいか 1.0 より大きい場 合、または fractions が厳密な昇順で指定されない場合 違いは始点と終点の座標をPoint2Dクラスのオブジェクトを使って指定している点だけです。 Point2Dクラスは二次元空間における座標を表す2つの値を保持するためのクラスです。Point2Dクラスはabstractクラスであるため実際にはサブクラスであるPoint2D.DoubleクラスやPoint2D.Floatクラスを使います。詳しくは『Point2Dクラス』を参照して下さい。 具体的には次のように記述します。 public void paintComponent(Graphics g) { Graphics2D g2 = (Graphics2D)g; float[] dist = {0.0f, 0.4f, 1.0f}; Color[] colors = {Color.RED, Color.WHITE, Color.BLUE}; LinearGradientPaint gradient = new LinearGradientPaint( new Point2D.Double(50.0d, 50.0d), new Point2D.Double(190.0f, 110.0f), dist, colors, MultipleGradientPaint.CycleMethod.NO_CYCLE ); g2.setPaint(gradient); g2.fill(new Rectangle2D.Double(20, 20, 200, 130)); } サンプルプログラム下記のサンプルを実行してみよう。/** * LinearGradientPaintクラスによるグラデーションの指定 */ import javax.swing.*; import java.awt.Graphics; import java.awt.Graphics2D; import java.awt.RenderingHints; import java.awt.geom.*; import java.awt.Color; import java.awt.LinearGradientPaint; import java.awt.MultipleGradientPaint; public class PaintTest6 extends JPanel { public static void main(String[] args) { JFrame frame = new JFrame(); PaintTest6 app = new PaintTest6(); frame.getContentPane().add(app); frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); frame.setBounds(10, 10, 300, 200); frame.setTitle("タイトル"); frame.setVisible(true); } public void paintComponent(Graphics g) { Graphics2D g2 = (Graphics2D)g; float[] dist = {0.0f, 0.4f, 1.0f}; Color[] colors = {Color.RED, Color.WHITE, Color.BLUE}; LinearGradientPaint gradient = new LinearGradientPaint( 50.0f, 50.0f, 100.0f, 110.0f, dist, colors, MultipleGradientPaint.CycleMethod.NO_CYCLE // MultipleGradientPaint.CycleMethod.REFLECT // MultipleGradientPaint.CycleMethod.REPEAT ); g2.setPaint(gradient); g2.fill(new Rectangle2D.Double(20, 20, 200, 130)); } }上記をコンパイルした後で実行すると次のように表示されます。 ![]() 今回はグラデーション方式として非循環式を設定しています。 それではグラデーション方式として「MultipleGradientPaint.CycleMethod.REFLECT」を設定した場合と「MultipleGradientPaint.CycleMethod.REPEAT」を設定した場合の結果だけ見ておきます。 MultipleGradientPaint.CycleMethod.REFLECT: ![]() MultipleGradientPaint.CycleMethod.REPEAT: ![]() |
主に塗りつぶし用としてグラデーションパターンを指定する方法を確認します。「setPaint」メソッドの引数にRadialGradientPaintクラスのオブジェクトを指定します。このグラデーションでは円放射状グラデーションパターンを使用します。 クラス図は次のようになっています。 java.lang.Object ⇒ java.awt.MultipleGradientPaint ⇒ java.awt.RadialGradientPaint public final class RadialGradientPaint extends MultipleGradientPaintコンストラクタは次の8つが用意されています。
RadialGradientPaintクラスでは円の中心と半径を指定し、別途指定した焦点と半径上の点の間に任意の個数の色を指定してグラデーションの色分布を指定することが出来ます。 またグラデーション方法として非循環式の他に循環式(反射)と循環式(繰り返し)の3パターンから選択できます。 それでは2番目のコンストラクタを見てみます。 RadialGradientPaint public RadialGradientPaint(float cx, float cy, float radius, float[] fractions, Color[] colors, MultipleGradientPaint.CycleMethod cycleMethod)焦点として中心点を使用して、デフォルトの SRGB カラースペースで RadialGradientPaint を構築します。 パラメータ: cx - グラデーションを定義する円の中心点の、ユーザー空間での X 座標。 グラデーションの最後の色は、この円の円周にマップされる cy - グラデーションを定義する円の中心点の、ユーザー空間での Y 座標。 グラデーションの最後の色は、この円の円周にマップされる radius - 色のグラデーションの広がりを定義する 円の半径 fractions - 0.0 - 1.0 の範囲の数値。 グラデーションでの色分布を指定する colors - グラデーションで使用される色の配列。最初の色は 焦点で使用さ れ、最後の色は 円周で使用される cycleMethod - NO_CYCLE、REFLECT、 REPEAT のいずれか 例外: NullPointerException - fractions 配列が null の場合、colors 配列が null の場合、 または cycleMethod が null の場合 IllegalArgumentException - radius が正でない場合、 fractions.length != colors.length である場合、 colors のサイズが 2 より小さい場合、 fractions の値が 0.0 より小さいか 1.0 より大きい場 合、 または fractions が厳密な昇順で指定されない場合 1番目と2番目の引数で円の中心を、3番目で半径を指定します。このコンストラクタの場合は焦点は円の中心点と同じ位置となります。 4番目の引数では区間内で色を設定したい位置を指定します。焦点を始点、円周上の点を終点とした場合の区間に対して、始点を「0.0」終点を「1.0」と考えます。その区間に対して色を設定したい位置をfloat型の配列で指定します。 5番目の引数では4番目の引数で指定した色を設定する位置に対して実際の色をColorクラスのオブジェクトの配列で指定します。指定する色の数は4番目の数と同じである必要があります。 具体的には次のように記述します。 float[] dist = {0.0f, 0.4f, 1.0f}; Color[] colors = {Color.RED, Color.WHITE, Color.BLUE};この場合は区間内で合計3つの位置に色を指定していることになります。なお色を指定する位置で始点である「0.0f」や「1.0f」を指定しなかった場合は始点や終点に一番近い色が指定されたものとして扱われます。 例えば次のように記述した場合を考えてみます。 float[] dist = {0.2f, 0.4f, 1.0f}; Color[] colors = {Color.RED, Color.WHITE, Color.BLUE};この場合は次のように記述した場合と同じです。 float[] dist = {0.0f, 0.2f, 0.4f, 1.0f}; Color[] colors = {Color.RED, Color.RED, Color.WHITE, Color.BLUE};6番目の引数ではグラデーションの表示方法を指定します。指定できる値は次の3つです。
非循環式の場合は始点と終点の間の区間だけにグラデーションが適用されます。円の外側は円周上の色が設定されます。循環式(反射)の場合は円の外側の区間について反射するようにグラデーションが適用されます。循環式(繰り返し)の場合は円の外側の区間についても始点と終点の間のグラデーションが繰り返し適用されます。 具体的には次のように記述します。 public void paintComponent(Graphics g) { Graphics2D g2 = (Graphics2D)g; float[] dist = {0.0f, 0.4f, 1.0f}; Color[] colors = {Color.RED, Color.WHITE, Color.BLUE}; RadialGradientPaint gradient = new RadialGradientPaint( 50.0f, 50.0f, 60.0f, dist, colors, MultipleGradientPaint.CycleMethod.NO_CYCLE ); g2.setPaint(gradient); g2.fill(new Rectangle2D.Double(20, 20, 200, 130)); }「setPaint」メソッドを実行した後で実行された「draw」メソッド及び「fill」メソッドで設定が反映されます。 Point2Dクラスによる座標指定中心点の座標を指定する方法としてPoint2Dクラスのオブジェクトを使用するコンストラクタも用意されています。5番目のコンストラクタを見てみます。RadialGradientPaint public RadialGradientPaint(float cx, float cy, float radius, float fx, float fy, float[] fractions, Color[] colors, MultipleGradientPaint.CycleMethod cycleMethod)デフォルトの SRGB カラースペースで RadialGradientPaint を構築します。 パラメータ: cx - グラデーションを定義する円の中心点の、ユーザー空間での X 座標。 グラデーションの最後の色は、この円の円周にマップされる cy - グラデーションを定義する円の中心点の、ユーザー空間での Y 座標。 グラデーションの最後の色は、この円の円周にマップされる radius - 色のグラデーションの広がりを定義する 円の半径 fx - 最初の色がマップされる、 ユーザー空間内の点の X 座標 fy - 最初の色がマップされる、 ユーザー空間内の点の Y 座標 fractions - 0.0 - 1.0 の範囲の数値。 グラデーションでの色分布を指定する colors - グラデーションで使用される色の配列。最初の色は 焦点で使用さ れ、最後の色は 円周で使用される cycleMethod - NO_CYCLE、REFLECT、 REPEAT のいずれか 例外: NullPointerException - fractions 配列が null の場合、colors 配列がnull の場合、 または cycleMethod が null の場合 IllegalArgumentException - radius が正でない場合、 fractions.length != colors.length である場合、 colors のサイズが 2 より小さい場合、 fractions の値が 0.0 より小さいか 1.0 より大きい場 合、 または fractions が厳密な昇順で指定されない場合 違いは始点である中心点の座標をPoint2Dクラスのオブジェクトを使って指定している点だけです。 Point2Dクラスは二次元空間における座標を表す2つの値を保持するためのクラスです。Point2Dクラスはabstractクラスであるため実際にはサブクラスであるPoint2D.DoubleクラスやPoint2D.Floatクラスを使います。詳しくは『Point2Dクラス』を参照して下さい。 具体的には次のように記述します。 public void paintComponent(Graphics g) { Graphics2D g2 = (Graphics2D)g; float[] dist = {0.0f, 0.4f, 1.0f}; Color[] colors = {Color.RED, Color.WHITE, Color.BLUE}; RadialGradientPaint gradient = new RadialGradientPaint( new Point2D.Double(50.0d, 50.0d), 60.0f, dist, colors, MultipleGradientPaint.CycleMethod.NO_CYCLE ); g2.setPaint(gradient); g2.fill(new Rectangle2D.Double(20, 20, 200, 130)); } サンプルプログラム下記のサンプルを実行してみよう。/** * RadialGradientPaintクラスによるグラデーションの指定 */ import javax.swing.*; import java.awt.Graphics; import java.awt.Graphics2D; import java.awt.RenderingHints; import java.awt.geom.*; import java.awt.Color; import java.awt.RadialGradientPaint; import java.awt.MultipleGradientPaint; public class PaintTest7 extends JPanel{ public static void main(String[] args){ JFrame frame = new JFrame(); PaintTest7 app = new PaintTest7(); frame.getContentPane().add(app); frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); frame.setBounds(10, 10, 300, 200); frame.setTitle("タイトル"); frame.setVisible(true); } public void paintComponent(Graphics g){ Graphics2D g2 = (Graphics2D)g; float[] dist = {0.0f, 0.4f, 1.0f}; Color[] colors = {Color.RED, Color.WHITE, Color.BLUE}; RadialGradientPaint gradient = new RadialGradientPaint( 100.0f, 80.0f, 60.0f, dist, colors, MultipleGradientPaint.CycleMethod.NO_CYCLE // MultipleGradientPaint.CycleMethod.REFLECT // MultipleGradientPaint.CycleMethod.REPEAT ); g2.setPaint(gradient); g2.fill(new Rectangle2D.Double(20, 20, 200, 130)); } }上記をコンパイルした後で実行すると次のように表示されます。 ![]() 今回はグラデーション方式として非循環式を設定しています。 それではグラデーション方式として「MultipleGradientPaint.CycleMethod.REFLECT」を設定した場合と「MultipleGradientPaint.CycleMethod.REPEAT」を設定した場合の結果だけ見ておきます。 MultipleGradientPaint.CycleMethod.REFLECT: ![]() MultipleGradientPaint.CycleMethod.REPEAT: ![]() |
RadialGradientPaintクラスを使って円放射状グラデーションパターンを使う場合、円の中心点とは異なる位置に始点である焦点を設定することができます。 焦点を別途設定するには3番目のコンストラクタを使います。 RadialGradientPaint public RadialGradientPaint(float cx, float cy, float radius, float fx, float fy, float[] fractions, Color[] colors, MultipleGradientPaint.CycleMethod cycleMethod)デフォルトの SRGB カラースペースで RadialGradientPaint を構築します。 パラメータ: cx - グラデーションを定義する円の中心点の、ユーザー空間での X 座標。 グラデーションの最後の色は、この円の円周にマップされる cy - グラデーションを定義する円の中心点の、ユーザー空間での Y 座標。 グラデーションの最後の色は、この円の円周にマップされる radius - 色のグラデーションの広がりを定義する 円の半径 fx - 最初の色がマップされる、ユーザー空間内の点の X 座標 fy - 最初の色がマップされる、ユーザー空間内の点の Y 座標 fractions - 0.0 - 1.0 の範囲の数値。 グラデーションでの色分布を指定する colors - グラデーションで使用される色の配列。最初の色は 焦点で使用さ れ、最後の色は 円周で使用される cycleMethod - NO_CYCLE、REFLECT、 REPEAT のいずれか 例外: NullPointerException - fractions 配列が null の場合、colors 配列がnull の場合、 または cycleMethod が null の場合 IllegalArgumentException - radius が正でない場合、 fractions.length != colors.length である場合、 colors のサイズが 2 より小さい場合、 fractions の値が 0.0 より小さいか 1.0 より大きい場 合、または fractions が厳密な昇順で指定されない場合 基本的な引数の設定については『RadialGradientPaintクラスによるグラデーションの指定』を参照して下さい。 異なる点は円の中心点とは別に始点となる焦点の座標を5番目と6番目の引数で指定している点です。グラデーションは焦点から円周上の各点に対して行われます。 具体的には次のように記述します。 public void paintComponent(Graphics g) { Graphics2D g2 = (Graphics2D)g; float[] dist = {0.0f, 0.4f, 1.0f}; Color[] colors = {Color.RED, Color.WHITE, Color.BLUE}; RadialGradientPaint gradient = new RadialGradientPaint( 50.0f, 50.0f, 60.0f, 40.0f, 40.0f, dist, colors, MultipleGradientPaint.CycleMethod.NO_CYCLE ); g2.setPaint(gradient); g2.fill(new Rectangle2D.Double(20, 20, 200, 130)); }etPaint」メソッドを実行した後で実行された「draw」メソッド及び「fill」メソッドで設定が反映されます。br> Point2Dクラスによる座標指定中心点及び焦点の座標を指定する方法としてPoint2Dクラスのオブジェクトを使用するコンストラクタも用意されています。6番目のコンストラクタを見てみます。RadialGradientPaint public RadialGradientPaint(Point2D center, float radius, Point2D focus, float[] fractions, Color[] colors, MultipleGradientPaint.CycleMethod cycleMethod)デフォルトの SRGB カラースペースで RadialGradientPaint を構築します。 パラメータ: center - ユーザー空間で、グラデーションを定義する円の 中心点。グラデー ションの最後の色は、 この円の円周にマップされる radius - 色のグラデーションの広がりを定義する 円の半径 focus - 最初の色がマップされるユーザー空間内の点 fractions - 0.0 - 1.0 の範囲の数値。 グラデーションでの色分布を指定する colors - グラデーションで使用される色の配列。最初の色は 焦点で使用さ れ、最後の色は 円周で使用される cycleMethod - NO_CYCLE、REFLECT、 REPEAT のいずれか 例外: NullPointerException - 点のいずれかが null の場合、fractions 配列がnull の場合、 colors 配列が null の場合、 または cycleMethod が null の場合 IllegalArgumentException - radius が正でない場合、 fractions.length != colors.length である場合、 colors のサイズが 2 より小さい場合、 fractions の値が 0.0 より小さいか 1.0 より大きい場 合、 または fractions が厳密な昇順で指定されない場合 違いは中心点及び焦点の座標をPoint2Dクラスのオブジェクトを使って指定している点だけです。 Point2Dクラスは二次元空間における座標を表す2つの値を保持するためのクラスです。Point2Dクラスはabstractクラスであるため実際にはサブクラスであるPoint2D.DoubleクラスやPoint2D.Floatクラスを使います。詳しくは『Point2Dクラス』を参照して下さい。 具体的には次のように記述します。 public void paintComponent(Graphics g) { Graphics2D g2 = (Graphics2D)g; float[] dist = {0.0f, 0.4f, 1.0f}; Color[] colors = {Color.RED, Color.WHITE, Color.BLUE}; RadialGradientPaint gradient = new RadialGradientPaint( new Point2D.Double(50.0d, 50.0d), 60.0f, new Point2D.Double(40.0d, 40.0d), dist, colors, MultipleGradientPaint.CycleMethod.NO_CYCLE ); g2.setPaint(gradient); g2.fill(new Rectangle2D.Double(20, 20, 200, 130)); } サンプルプログラム下記のサンプルを実行してみよう。/** * 焦点を中心点と異なる位置に設定する */ import javax.swing.*; import java.awt.Graphics; import java.awt.Graphics2D; import java.awt.RenderingHints; import java.awt.geom.*; import java.awt.Color; import java.awt.RadialGradientPaint; import java.awt.MultipleGradientPaint; public class PaintTest8 extends JPanel{ public static void main(String[] args){ JFrame frame = new JFrame(); PaintTest8 app = new PaintTest8(); frame.getContentPane().add(app); frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE); frame.setBounds(10, 10, 300, 200); frame.setTitle("タイトル"); frame.setVisible(true); } public void paintComponent(Graphics g){ Graphics2D g2 = (Graphics2D)g; float[] dist = {0.0f, 0.4f, 1.0f}; Color[] colors = {Color.RED, Color.WHITE, Color.BLUE}; RadialGradientPaint gradient = new RadialGradientPaint( 100.0f, 80.0f, 60.0f, 60.0f, 60.0f, dist, colors, MultipleGradientPaint.CycleMethod.NO_CYCLE // MultipleGradientPaint.CycleMethod.REFLECT // MultipleGradientPaint.CycleMethod.REPEAT ); g2.setPaint(gradient); g2.fill(new Rectangle2D.Double(20, 20, 200, 130)); } }上記をコンパイルした後で実行すると次のように表示されます。 ![]() 今回はグラデーション方式として非循環式を設定しています。 それではグラデーション方式として「MultipleGradientPaint.CycleMethod.REFLECT」を設定した場合と「MultipleGradientPaint.CycleMethod.REPEAT」を設定した場合の結果だけ見ておきます。 MultipleGradientPaint.CycleMethod.REFLECT: ![]() MultipleGradientPaint.CycleMethod.REPEAT: ![]() |
|