summaryrefslogtreecommitdiffstats
path: root/src/jrummikub/view
diff options
context:
space:
mode:
Diffstat (limited to 'src/jrummikub/view')
-rw-r--r--src/jrummikub/view/impl/Board.java12
-rw-r--r--src/jrummikub/view/impl/StonePainter.java148
2 files changed, 133 insertions, 27 deletions
diff --git a/src/jrummikub/view/impl/Board.java b/src/jrummikub/view/impl/Board.java
index dc26dd4..2e02f75 100644
--- a/src/jrummikub/view/impl/Board.java
+++ b/src/jrummikub/view/impl/Board.java
@@ -2,7 +2,9 @@ package jrummikub.view.impl;
import java.awt.Color;
import java.awt.Graphics;
+import java.awt.Graphics2D;
import java.awt.Insets;
+import java.awt.RenderingHints;
import java.util.Collections;
import java.util.Map;
@@ -18,6 +20,7 @@ public class Board extends JPanel implements IBoard {
private final static ImageIcon background = new ImageIcon(Board.class.getResource("/jrummikub/resource/wood.png"));
private Map<Stone, Position> stones = Collections.emptyMap();
+ private StonePainter stonePainter = new StonePainter(StonePainter.BOARD_SCALE);
Board() {
super(true);
@@ -26,10 +29,10 @@ public class Board extends JPanel implements IBoard {
}
@Override
- protected void paintComponent(Graphics g) {
+ protected void paintComponent(Graphics g1) {
Insets insets = getInsets();
int x = insets.left, y = insets.top, width = getWidth()-insets.left-insets.right, height = getHeight()-insets.top-insets.bottom;
- g = g.create(x, y, width, height);
+ Graphics2D g = (Graphics2D)g1.create(x, y, width, height);
for(int xpos = 0; xpos < width; xpos += background.getIconWidth()) {
background.paintIcon(this, g, xpos, 0);
@@ -38,8 +41,11 @@ public class Board extends JPanel implements IBoard {
background.paintIcon(this, g, xpos, 75);
}
+ g.setRenderingHint(RenderingHints.KEY_ANTIALIASING,
+ RenderingHints.VALUE_ANTIALIAS_ON);
+
for (Map.Entry<Stone, Position> stone : stones.entrySet()) {
- StonePainter.paintStone(g, stone.getKey(), stone.getValue(), StonePainter.BOARD_SCALE);
+ stonePainter.paintStone(g, stone.getKey(), stone.getValue());
}
}
diff --git a/src/jrummikub/view/impl/StonePainter.java b/src/jrummikub/view/impl/StonePainter.java
index e536e32..9e836e5 100644
--- a/src/jrummikub/view/impl/StonePainter.java
+++ b/src/jrummikub/view/impl/StonePainter.java
@@ -1,11 +1,12 @@
package jrummikub.view.impl;
+import java.awt.BasicStroke;
import java.awt.Color;
import java.awt.Font;
import java.awt.FontMetrics;
-import java.awt.Graphics;
import java.awt.Graphics2D;
-import java.awt.RenderingHints;
+import java.awt.Stroke;
+import java.awt.geom.GeneralPath;
import java.awt.geom.Rectangle2D;
import jrummikub.model.Position;
@@ -15,40 +16,53 @@ import jrummikub.model.StoneColor;
class StonePainter {
private static final float ASPECT_RATIO = 0.75f;
private static final float DEFAULT_WIDTH = 40;
- private static final float CIRCLE_WIDTH = 0.5f;
+ private static final float TEXT_POS = 0.275f;
+ private static final float FACE_WIDTH = 0.475f;
+ private static final float CIRCLE_POS = 0.725f;
+ private static final float CIRCLE_WIDTH = 0.45f;
+
private static final Color BACKGROUND_COLOR = new Color(0.9f, 0.9f, 0.6f);
public static final float BOARD_SCALE = 75.0f*ASPECT_RATIO/DEFAULT_WIDTH;
+ private float scale;
+
+
+ private static int even(float f) {
+ return 2*(int)(f/2);
+ }
+
private static Color getColor(StoneColor color) {
switch(color) {
case BLACK:
- return Color.BLACK;
+ return new Color(0.15f, 0.15f, 0.15f);
case BLUE:
- return Color.BLUE;
+ return new Color(0.0f, 0.0f, 1.0f);
case ORANGE:
- return new Color(1.0f, 0.6f, 0);
+ return new Color(1.0f, 0.6f, 0.0f);
case RED:
- return Color.RED;
+ return new Color(0.9f, 0.0f, 0.25f);
}
return null;
}
- public static void paintStone(Graphics g, Stone stone, Position p, float scale) {
- if (g instanceof Graphics2D) {
- ((Graphics2D)g).setRenderingHint(RenderingHints.KEY_ANTIALIASING,
- RenderingHints.VALUE_ANTIALIAS_ON);
- }
-
- int width = (int)(DEFAULT_WIDTH*scale);
- int height = (int)(DEFAULT_WIDTH*scale/ASPECT_RATIO);
-
- int x = (int)(p.getX()*width);
- int y = (int)(p.getY()*height);
-
+ public void setScale(float scale) {
+ this.scale = scale;
+ }
+
+ public float getScale() {
+ return scale;
+ }
+
+ StonePainter(float scale) {
+ this.scale = scale;
+ }
+
+ private void paintStoneBackground(Graphics2D g, int x, int y,
+ int width, int height) {
// Paint background
g.setColor(BACKGROUND_COLOR);
g.fillRect(x, y, width, height);
@@ -73,23 +87,109 @@ class StonePainter {
g.fillRect(x, y+height-1, width, 1);
g.setColor(BACKGROUND_COLOR.darker());
g.fillRect(x+1, y+height-2, width-2, 1);
+ }
+
+ private void paintJokerFace(Graphics2D g, int x, int y, int width, int height,
+ Stone stone) {
+ Stroke oldStroke = g.getStroke();
+
+ g.setStroke(new BasicStroke(2));
+ g.drawOval(x, y, width, height);
+
+ g.setStroke(new BasicStroke(1));
+ GeneralPath path = new GeneralPath();
+ // nose
+ path.moveTo(x+0.5f*width, y+0.45f*height);
+ path.lineTo(x+0.53f*width, y+0.6f*height);
+ path.lineTo(x+0.47f*width, y+0.6f*height);
+ path.closePath();
+ g.fill(path);
+
+ path.reset();
+ // mouth, left
+ path.moveTo(x+0.23f*width, y+0.75f*width);
+ path.lineTo(x+0.27f*width, y+0.65f*width);
+ // mouth, middle
+ path.moveTo(x+0.25f*width, y+0.7f*width);
+ path.lineTo(x+0.5f*width, y+0.8f*width);
+ path.lineTo(x+0.75f*width, y+0.7f*width);
+ // mouth, right
+ path.moveTo(x+0.77f*width, y+0.75f*width);
+ path.lineTo(x+0.73f*width, y+0.65f*width);
+ g.draw(path);
+
+ path.reset();
+ // left eye
+ path.moveTo(x+0.3f*width, y+0.41f*height);
+ path.lineTo(x+0.375f*width, y+0.375f*height);
+ path.lineTo(x+0.3f*width, y+0.34f*height);
+ path.lineTo(x+0.225f*width, y+0.375f*height);
+ path.closePath();
+ g.draw(path);
+
+ path.reset();
+ // right eye
+ path.moveTo(x+0.7f*width, y+0.41f*height);
+ path.lineTo(x+0.625f*width, y+0.375f*height);
+ path.lineTo(x+0.7f*width, y+0.34f*height);
+ path.lineTo(x+0.775f*width, y+0.375f*height);
+ path.closePath();
+ g.draw(path);
+
+ g.setStroke(oldStroke);
+ }
+
+ private void paintJoker(Graphics2D g, int x, int y, int width, int height,
+ Stone stone) {
+ int faceSize = even(FACE_WIDTH*width);
+ int pos = y + (int)(TEXT_POS*height);
+
+ g.setColor(getColor(stone.getColor()));
+ paintJokerFace(g, x+width/2-faceSize/2, pos-faceSize/2, faceSize, faceSize, stone);
+ }
+
+ private void paintStoneNumber(Graphics2D g, int x, int y, int width,
+ int height, Stone stone) {
+ int pos = y + (int)(TEXT_POS*height);
- // Paint number
g.setFont(new Font("SansSerif", Font.BOLD, height/4));
FontMetrics fm = g.getFontMetrics();
String value = Integer.toString(stone.getValue());
Rectangle2D stringRect = fm.getStringBounds(value, g);
g.setColor(getColor(stone.getColor()).darker());
- g.drawString(value, (int)(x+width/2-stringRect.getWidth()/2)+1, y+height/4+(fm.getAscent()-fm.getDescent())/2+1);
+ g.drawString(value, (int)(x+width/2-stringRect.getWidth()/2)+1, pos+(fm.getAscent()-fm.getDescent())/2+1);
g.setColor(getColor(stone.getColor()));
- g.drawString(value, (int)(x+width/2-stringRect.getWidth()/2), y+height/4+(fm.getAscent()-fm.getDescent())/2);
+ g.drawString(value, (int)(x+width/2-stringRect.getWidth()/2), pos+(fm.getAscent()-fm.getDescent())/2);
+ }
+
+ private void paintCircle(Graphics2D g, int x, int y, int width, int height) {
+ int size = even(width*CIRCLE_WIDTH);
+ int pos = y + (int)(CIRCLE_POS*height);
// Paint circle
g.setColor(BACKGROUND_COLOR.darker());
- g.drawArc((int)(x+width/2-width*CIRCLE_WIDTH/2), (int)(y+height*0.65f-width*CIRCLE_WIDTH/2), (int)(width*CIRCLE_WIDTH), (int)(width*CIRCLE_WIDTH), 50, 170);
+ g.drawArc(x+width/2-size/2, pos-size/2, size, size, 50, 170);
g.setColor(BACKGROUND_COLOR.brighter());
- g.drawArc((int)(x+width/2-width*CIRCLE_WIDTH/2), (int)(y+height*0.65f-width*CIRCLE_WIDTH/2), (int)(width*CIRCLE_WIDTH), (int)(width*CIRCLE_WIDTH), -130, 170);
+ g.drawArc((int)(x+width/2-size/2), pos-size/2, size, size, -130, 170);
+ }
+
+ public void paintStone(Graphics2D g, Stone stone, Position p) {
+ int width = even(DEFAULT_WIDTH*scale);
+ int height = (int)(DEFAULT_WIDTH*scale/ASPECT_RATIO);
+
+ int x = (int)(p.getX()*width);
+ int y = (int)(p.getY()*height);
+
+ paintStoneBackground(g, x, y, width, height);
+
+ if (stone.isJoker()) {
+ paintJoker(g, x, y, width, height, stone);
+ } else {
+ paintStoneNumber(g, x, y, width, height, stone);
+ }
+
+ paintCircle(g, x, y, width, height);
}
}