How to draw out a JLabel? - Java - java

I want to draw out a JLabel in a "public void paint(Graphics g) {}" and all that stuff. How do I take a JLabel from outside of the class (within the main method) and draw it out in the paint method?
static JLabel drawThisOut = new JLabel("draw this out");
public static void main(String[] args) {
class paintJLabel extends JComponent {
public void paint(Graphics g) {
//what goes here to draw the JLabel?????
}
}
}
And no, I cannot just use the regular JLabel instead of drawing it out. I need to draw something else over the JLabel and I assumed this was the most efficient way to do it. (Is there a more efficient way?) Any help at all would be greatly appreciated. Please be specific. Thanks!

In the "simplest" terms, you could use a Border of some kind, the following presents a custom rounded border, but the concept is relatively simple
import java.awt.Color;
import java.awt.Component;
import java.awt.Dimension;
import java.awt.EventQueue;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.GridBagLayout;
import java.awt.Insets;
import java.awt.RenderingHints;
import java.awt.geom.RoundRectangle2D;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.border.AbstractBorder;
public class Test {
public static void main(String[] args) {
new Test();
}
public Test() {
EventQueue.invokeLater(new Runnable() {
#Override
public void run() {
JFrame frame = new JFrame();
frame.add(new TestPane());
frame.pack();
frame.setLocationRelativeTo(null);
frame.setVisible(true);
}
});
}
public class TestPane extends JPanel {
public TestPane() {
setLayout(new GridBagLayout());
JLabel label = new JLabel("This is a test");
label.setBorder(new RoundedBorder(Color.BLACK, 20));
add(label);
}
}
public class RoundedBorder extends AbstractBorder {
private final Color color;
private final int gap;
public RoundedBorder(Color c, int g) {
color = c;
gap = g;
}
#Override
public void paintBorder(Component c, Graphics g, int x, int y, int width, int height) {
Graphics2D g2d = (Graphics2D) g.create();
g2d.setRenderingHint(RenderingHints.KEY_ALPHA_INTERPOLATION, RenderingHints.VALUE_ALPHA_INTERPOLATION_QUALITY);
g2d.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
g2d.setRenderingHint(RenderingHints.KEY_COLOR_RENDERING, RenderingHints.VALUE_COLOR_RENDER_QUALITY);
g2d.setRenderingHint(RenderingHints.KEY_DITHERING, RenderingHints.VALUE_DITHER_ENABLE);
g2d.setRenderingHint(RenderingHints.KEY_FRACTIONALMETRICS, RenderingHints.VALUE_FRACTIONALMETRICS_ON);
g2d.setRenderingHint(RenderingHints.KEY_INTERPOLATION, RenderingHints.VALUE_INTERPOLATION_BILINEAR);
g2d.setRenderingHint(RenderingHints.KEY_RENDERING, RenderingHints.VALUE_RENDER_QUALITY);
g2d.setRenderingHint(RenderingHints.KEY_STROKE_CONTROL, RenderingHints.VALUE_STROKE_PURE);
g2d.setColor(color);
g2d.draw(new RoundRectangle2D.Double(x, y, width - 1, height - 1, gap, gap));
g2d.dispose();
}
#Override
public Insets getBorderInsets(Component c) {
return (getBorderInsets(c, new Insets(gap, gap, gap, gap)));
}
#Override
public Insets getBorderInsets(Component c, Insets insets) {
insets.left = insets.top = insets.right = insets.bottom = gap / 2;
return insets;
}
#Override
public boolean isBorderOpaque() {
return false;
}
}
}
You could also use a custom component. This provides you with the added benefit of been able to "fill" the shape with your own background color, but is, otherwise, essentially the same thing
import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.Component;
import java.awt.EventQueue;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.GridBagLayout;
import java.awt.Insets;
import java.awt.RenderingHints;
import java.awt.geom.RoundRectangle2D;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.border.AbstractBorder;
import javax.swing.border.EmptyBorder;
public class Test {
public static void main(String[] args) {
new Test();
}
public Test() {
EventQueue.invokeLater(new Runnable() {
#Override
public void run() {
JFrame frame = new JFrame();
frame.add(new TestPane());
frame.pack();
frame.setLocationRelativeTo(null);
frame.setVisible(true);
}
});
}
public class TestPane extends JPanel {
public TestPane() {
setLayout(new GridBagLayout());
JLabel label = new JLabel("This is a test");
label.setBorder(new EmptyBorder(10, 10, 10, 10));
RoundedPane pane = new RoundedPane();
pane.add(label);
add(pane);
}
}
public class RoundedPane extends JPanel {
public RoundedPane() {
setLayout(new BorderLayout());
}
#Override
protected void paintComponent(Graphics g) {
super.paintComponent(g);
Graphics2D g2d = (Graphics2D) g.create();
g2d.setRenderingHint(RenderingHints.KEY_ALPHA_INTERPOLATION, RenderingHints.VALUE_ALPHA_INTERPOLATION_QUALITY);
g2d.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
g2d.setRenderingHint(RenderingHints.KEY_COLOR_RENDERING, RenderingHints.VALUE_COLOR_RENDER_QUALITY);
g2d.setRenderingHint(RenderingHints.KEY_DITHERING, RenderingHints.VALUE_DITHER_ENABLE);
g2d.setRenderingHint(RenderingHints.KEY_FRACTIONALMETRICS, RenderingHints.VALUE_FRACTIONALMETRICS_ON);
g2d.setRenderingHint(RenderingHints.KEY_INTERPOLATION, RenderingHints.VALUE_INTERPOLATION_BILINEAR);
g2d.setRenderingHint(RenderingHints.KEY_RENDERING, RenderingHints.VALUE_RENDER_QUALITY);
g2d.setRenderingHint(RenderingHints.KEY_STROKE_CONTROL, RenderingHints.VALUE_STROKE_PURE);
g2d.setColor(Color.BLACK);
g2d.draw(new RoundRectangle2D.Double(0, 0, getWidth() - 1, getHeight() - 1, 20, 20));
g2d.dispose();
}
}
}

Related

Raisd border in JPanel

I need to Override a JPanel and make it Raisd. See my Code please.
public class CustomJPanel extends JPanel {
public CustomJPanel(int size){
setForeground(Color.black); // foreground will be black
setOpaque(false);
}
#Override
protected void paintBorder(Graphics myGraphics){
myGraphics.setColor(Color.black);
myGraphics.drawRoundRect(0, 0, getWidth()-1, getHeight()-1, 20, 20);
}
}
Actually, i need to have a JPanel Raisd with rounded corners
Border
It's pretty basic, but it gets the idea across...
import java.awt.BasicStroke;
import java.awt.Color;
import java.awt.Component;
import java.awt.Dimension;
import java.awt.EventQueue;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.Insets;
import java.awt.RenderingHints;
import java.awt.Shape;
import java.awt.geom.AffineTransform;
import java.awt.geom.Arc2D;
import java.awt.geom.Path2D;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.UIManager;
import javax.swing.UnsupportedLookAndFeelException;
import javax.swing.border.Border;
public class Test {
public static void main(String[] args) {
new Test();
}
public Test() {
EventQueue.invokeLater(new Runnable() {
#Override
public void run() {
try {
UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
} catch (ClassNotFoundException | InstantiationException | IllegalAccessException | UnsupportedLookAndFeelException ex) {
ex.printStackTrace();
}
JFrame frame = new JFrame("Testing");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.add(new TestPane());
frame.pack();
frame.setLocationRelativeTo(null);
frame.setVisible(true);
}
});
}
public class TestPane extends JPanel {
public TestPane() {
setBorder(new MyRoundedBorder());
}
#Override
public Dimension getPreferredSize() {
return new Dimension(200, 200);
}
protected void paintComponent(Graphics g) {
super.paintComponent(g);
Graphics2D g2d = (Graphics2D) g.create();
g2d.dispose();
}
}
public static class MyRoundedBorder implements Border {
protected static final Insets DEFAULT_INSETS = new Insets(4, 4, 4, 4);
#Override
public void paintBorder(Component c, Graphics g, int x, int y, int width, int height) {
Graphics2D g2d = (Graphics2D) g.create();
g2d.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
g2d.setRenderingHint(RenderingHints.KEY_INTERPOLATION, RenderingHints.VALUE_INTERPOLATION_BICUBIC);
g2d.setRenderingHint(RenderingHints.KEY_ALPHA_INTERPOLATION, RenderingHints.VALUE_ALPHA_INTERPOLATION_QUALITY);
g2d.setRenderingHint(RenderingHints.KEY_COLOR_RENDERING, RenderingHints.VALUE_COLOR_RENDER_QUALITY);
g2d.setRenderingHint(RenderingHints.KEY_DITHERING, RenderingHints.VALUE_DITHER_ENABLE);
g2d.setRenderingHint(RenderingHints.KEY_RENDERING, RenderingHints.VALUE_RENDER_QUALITY);
g2d.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
g2d.setRenderingHint(RenderingHints.KEY_INTERPOLATION, RenderingHints.VALUE_INTERPOLATION_BILINEAR);
g2d.setRenderingHint(RenderingHints.KEY_INTERPOLATION, RenderingHints.VALUE_INTERPOLATION_BICUBIC);
g2d.setStroke(new BasicStroke(3, BasicStroke.CAP_ROUND, BasicStroke.JOIN_ROUND));
g2d.setColor(Color.WHITE);
Shape corner = new RoundedShape(width - 8, height - 8, 40);
g2d.translate(x + 2, y + 2);
g2d.draw(corner);
g2d.transform(AffineTransform.getRotateInstance(Math.toRadians(180), (width - 8) / 2, (height - 8) / 2));
g2d.setColor(Color.LIGHT_GRAY);
g2d.draw(corner);
g2d.dispose();
}
#Override
public Insets getBorderInsets(Component c) {
return DEFAULT_INSETS;
}
#Override
public boolean isBorderOpaque() {
return true;
}
public class RoundedShape extends Path2D.Float {
public RoundedShape(int width, int height, int size) {
moveTo(0, height - size);
append(new Arc2D.Float(0, height - size, size, size, 180, 45, Arc2D.CHORD), false);
lineTo(0, size);
curveTo(0, 0, 0, 0, size, 0);
lineTo(width - size / 2, 0);
append(new Arc2D.Float(width - size, 0, size, size, 90, -45, Arc2D.CHORD), false);
}
}
}
}
Custom Graphics
The problem with borders is you can't fill them, not really, it's kind of messy.
This leaves you with a problem with you want a non-rectangular component. Instead, you need to get a little more creative.
The following makes use of to "clipped" areas to paint a RoundRectangle2D in two different colors
import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.Dimension;
import java.awt.EventQueue;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.RenderingHints;
import java.awt.Shape;
import java.awt.geom.GeneralPath;
import java.awt.geom.RoundRectangle2D;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.UIManager;
import javax.swing.UnsupportedLookAndFeelException;
import javax.swing.border.EmptyBorder;
public class Test {
public static void main(String[] args) {
new Test();
}
public Test() {
EventQueue.invokeLater(new Runnable() {
#Override
public void run() {
try {
UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
} catch (ClassNotFoundException | InstantiationException | IllegalAccessException | UnsupportedLookAndFeelException ex) {
ex.printStackTrace();
}
JFrame frame = new JFrame("Testing");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
JPanel panel = new JPanel(new BorderLayout());
panel.setBorder(new EmptyBorder(10, 10, 10, 10));
panel.setBackground(Color.RED);
frame.setContentPane(panel);
frame.add(new TestPane());
frame.pack();
frame.setLocationRelativeTo(null);
frame.setVisible(true);
}
});
}
public class TestPane extends JPanel {
public TestPane() {
setOpaque(false);
}
#Override
public Dimension getPreferredSize() {
return new Dimension(200, 200);
}
protected void paintComponent(Graphics g) {
super.paintComponent(g);
Graphics2D g2d = (Graphics2D) g.create();
g2d.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
g2d.setRenderingHint(RenderingHints.KEY_INTERPOLATION, RenderingHints.VALUE_INTERPOLATION_BICUBIC);
g2d.setRenderingHint(RenderingHints.KEY_ALPHA_INTERPOLATION, RenderingHints.VALUE_ALPHA_INTERPOLATION_QUALITY);
g2d.setRenderingHint(RenderingHints.KEY_COLOR_RENDERING, RenderingHints.VALUE_COLOR_RENDER_QUALITY);
g2d.setRenderingHint(RenderingHints.KEY_DITHERING, RenderingHints.VALUE_DITHER_ENABLE);
g2d.setRenderingHint(RenderingHints.KEY_RENDERING, RenderingHints.VALUE_RENDER_QUALITY);
g2d.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
g2d.setRenderingHint(RenderingHints.KEY_INTERPOLATION, RenderingHints.VALUE_INTERPOLATION_BILINEAR);
g2d.setRenderingHint(RenderingHints.KEY_INTERPOLATION, RenderingHints.VALUE_INTERPOLATION_BICUBIC);
Shape border = new RoundRectangle2D.Double(0, 0, getWidth() - 1, getHeight() - 1, 20, 20);
g2d.setColor(getBackground());
g2d.fill(border);
GeneralPath upperClip = new GeneralPath();
upperClip.moveTo(0, 0);
upperClip.lineTo(getWidth() - 1, 0);
upperClip.lineTo(0, getHeight() - 1);
Graphics2D clipped = (Graphics2D) g2d.create();
clipped.setClip(upperClip);
clipped.setColor(Color.WHITE);
clipped.draw(border);
clipped.dispose();
GeneralPath lowerClip = new GeneralPath();
lowerClip.moveTo(0, getHeight());
lowerClip.lineTo(getWidth(), 0);
lowerClip.lineTo(getWidth(), getHeight());
clipped = (Graphics2D) g2d.create();
clipped.setClip(lowerClip);
clipped.setColor(Color.black);
clipped.draw(border);
clipped.dispose();
g2d.dispose();
}
}
}
LinearGradientPaint
A technique I've used in the past is to paint a RoundRectangle2D with a LinearGradientPaint, this gives a "slight" effect off shading which can produce a desirable result, if you're willing to play around with the properties
Try setting border while JPanel object is being created.
public CustomJPanel(int size){
setForeground(Color.black); // foreground will be black
setOpaque(false);
setBorder(new BevelBorder(BevelBorder.RAISED)); // Set Border Type
}

JButton border set with setBackground()?

So I have some code to change the background color of a button, but when I use the code, it sets the background color and border color.
Is there a way to not make this happen?
Thanks!
Code:
public void highlight(ArrayList<JButton> buttons){
for (JButton j : buttons) {
j.setBorder(new JButton().getBorder());
j.setBackground(Color.GREEN);
j.setForeground(Color.WHITE);
j.setOpaque(true);
j.setBorderPainted(false);
j.setFocusPainted(false);
j.setBorderPainted(false);
}
}
Okay, so this is a hacked version and is based on the idea that you want to maintain the current "look and feel" of the button, but want to use a different fill color
This simply applies a "highlight" color over the button...
import java.awt.AlphaComposite;
import java.awt.Color;
import java.awt.EventQueue;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.GraphicsConfiguration;
import java.awt.GraphicsEnvironment;
import java.awt.GridBagLayout;
import java.awt.Insets;
import java.awt.RenderingHints;
import java.awt.Transparency;
import java.awt.image.BufferedImage;
import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.UIManager;
import javax.swing.UnsupportedLookAndFeelException;
import org.kaizen.core.ui.ImageUtilities;
public class Main {
public static void main(String[] args) {
new Main();
}
public Main() {
EventQueue.invokeLater(new Runnable() {
#Override
public void run() {
try {
UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
} catch (ClassNotFoundException | InstantiationException | IllegalAccessException | UnsupportedLookAndFeelException ex) {
ex.printStackTrace();
}
JFrame frame = new JFrame("Testing");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.add(new TestPane());
frame.pack();
frame.setLocationRelativeTo(null);
frame.setVisible(true);
}
});
}
public class TestPane extends JPanel {
public TestPane() {
setLayout(new GridBagLayout());
HighlightButton btn = new HighlightButton("Help");
btn.setMargin(new Insets(20, 20, 20, 20));
btn.setHighlight(new Color(255, 0, 0, 64));
add(btn);
btn = new HighlightButton("Help");
btn.setMargin(new Insets(20, 20, 20, 20));
btn.setHighlight(new Color(0, 255, 0, 64));
add(btn);
btn = new HighlightButton("Help");
btn.setMargin(new Insets(20, 20, 20, 20));
btn.setHighlight(new Color(0, 0, 255, 64));
add(btn);
btn = new HighlightButton("Help");
btn.setMargin(new Insets(20, 20, 20, 20));
add(btn);
}
}
public class HighlightButton extends JButton {
private Color highlight;
public HighlightButton() {
setOpaque(false);
}
public HighlightButton(String text) {
super(text);
setOpaque(false);
}
public void setHighlight(Color color) {
if (color != highlight) {
Color old = highlight;
this.highlight = color;
firePropertyChange("highlight", old, highlight);
repaint();
}
}
public Color getHighlight() {
return highlight;
}
#Override
protected void paintComponent(Graphics g) {
Color highlight = getHighlight();
if (highlight != null) {
BufferedImage img = createCompatibleImage(getWidth(), getHeight(), Transparency.TRANSLUCENT);
Graphics2D g2d = img.createGraphics();
super.paintComponent(g2d);
g2d.dispose();
BufferedImage mask = generateMask(img, getHighlight(), 1f);
g.drawImage(img, 0, 0, this);
g.drawImage(mask, 0, 0, this);
} else {
super.paintComponent(g);
}
}
}
public static BufferedImage createCompatibleImage(int width, int height, int transparency) {
BufferedImage image = getGraphicsConfiguration().createCompatibleImage(width, height, transparency);
image.coerceData(true);
return image;
}
public static GraphicsConfiguration getGraphicsConfiguration() {
return GraphicsEnvironment.getLocalGraphicsEnvironment().getDefaultScreenDevice().getDefaultConfiguration();
}
public static BufferedImage generateMask(BufferedImage imgSource, Color color, float alpha) {
int imgWidth = imgSource.getWidth();
int imgHeight = imgSource.getHeight();
BufferedImage imgMask = createCompatibleImage(imgWidth, imgHeight, Transparency.TRANSLUCENT);
Graphics2D g2 = imgMask.createGraphics();
applyQualityRenderingHints(g2);
g2.drawImage(imgSource, 0, 0, null);
g2.setComposite(AlphaComposite.getInstance(AlphaComposite.SRC_IN, alpha));
g2.setColor(color);
g2.fillRect(0, 0, imgSource.getWidth(), imgSource.getHeight());
g2.dispose();
return imgMask;
}
public static void applyQualityRenderingHints(Graphics2D g2d) {
g2d.setRenderingHint(RenderingHints.KEY_ALPHA_INTERPOLATION, RenderingHints.VALUE_ALPHA_INTERPOLATION_QUALITY);
g2d.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
g2d.setRenderingHint(RenderingHints.KEY_COLOR_RENDERING, RenderingHints.VALUE_COLOR_RENDER_QUALITY);
g2d.setRenderingHint(RenderingHints.KEY_DITHERING, RenderingHints.VALUE_DITHER_ENABLE);
g2d.setRenderingHint(RenderingHints.KEY_FRACTIONALMETRICS, RenderingHints.VALUE_FRACTIONALMETRICS_ON);
g2d.setRenderingHint(RenderingHints.KEY_INTERPOLATION, RenderingHints.VALUE_INTERPOLATION_BILINEAR);
g2d.setRenderingHint(RenderingHints.KEY_RENDERING, RenderingHints.VALUE_RENDER_QUALITY);
g2d.setRenderingHint(RenderingHints.KEY_STROKE_CONTROL, RenderingHints.VALUE_STROKE_PURE);
}
}
Basically, what this does, is paints a "masked" image, colored in the highlighted color OVER the top of the button. This is important to remember. The higher the alpha value of the color becomes, the less likely you are to see the text.
I've not tested this on windows, so I can't guarantee the results.
The content filling is performed by the look and feel delegate and generally ignores the color properties of the class (yeah, I know, awesome), so if you want to try and do something which was a little more robust, you'd need to define your own look and feel delegate and take over the painting process, no simple task.
Of course, you could just dispense with the content filling and borders used by the look and feel delegate and paint your own (overriding the paintComponent method), but this will not take advantage of the look and feel settings, so that's a balancing act you need to decide on

paintComponent does not work on the East Panel, on West is ok

i have no idea why paintComponent gets called for the WestPanel, but wont work for the East Panel... even if the code is similar. Pls some help.
public class MyFrame extends JFrame{
public static final int WIDTH = 1664;
public static final int HEIGHT= 1088;
public static final int TILE_W = 64;
public static final int TILE_H = 64;
private CenterPanel cP;
private WestPanel wP;
private EastPanel eP;
/*private NorthPanel nP;
private SouthPanel sP;*/
public MyFrame(){
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
setSize(WIDTH, HEIGHT);
setTitle("Chuta");
setResizable(false);
setLocationRelativeTo(null);
cP = new CenterPanel();
add(cP, BorderLayout.CENTER);
wP = new WestPanel();
add(wP, BorderLayout.WEST);
eP = new EastPanel();
add(eP, BorderLayout.EAST);
setVisible(true);
}
public static void main(String[] args) {
MyFrame f = new MyFrame();
}
This west panel is drawing .
package frame;
import java.awt.BasicStroke;
import java.awt.Color;
import java.awt.Dimension;
import java.awt.Graphics;
import java.awt.Graphics2D;
import javax.swing.JPanel;
import static frame.MyFrame.*;
public class WestPanel extends JPanel {
private int wCP;
public WestPanel(){
wCP=3*TILE_W;
Dimension size = getPreferredSize();
size.width = wCP;
setPreferredSize(size);
setBackground(new Color(0, 115, 102));
new CardGrid(TILE_W/2);
}
#Override
public void paintComponent(Graphics g){
super.paintComponent(g);
Graphics2D g2d = (Graphics2D) g;
g2d.setStroke(new BasicStroke(5));
g2d.setColor(Color.white);
for (int y = TILE_H ; y < TILE_H*15; y+=TILE_H*3) {
g2d.drawRect(TILE_W / 2, y, 120, TILE_H * 3);
}
}
This East panel is not drawing
import static frame.MyFrame.TILE_W;
import static frame.MyFrame.TILE_H;
import java.awt.BasicStroke;
import java.awt.Color;
import java.awt.Dimension;
import java.awt.Graphics;
import java.awt.Graphics2D;
import javax.swing.JPanel;
public class EastPanel extends JPanel {
private int eCP;
public EastPanel(){
eCP=3*TILE_W;
Dimension size = getPreferredSize();
size.width = eCP;
setPreferredSize(size);
setBackground(new Color(0, 112, 102));
new CardGrid(MyFrame.WIDTH-120-TILE_W/2);
}
#Override
public void paintComponent(Graphics g) {
super.paintComponent(g);
Graphics2D g2d = (Graphics2D) g;
g2d.setStroke(new BasicStroke(5));
g2d.setColor(Color.white);
for (int y = TILE_H ; y < TILE_H*15; y+=TILE_H*3) {
g2d.drawRect(MyFrame.WIDTH- 120 -TILE_W / 2, y, 120, TILE_H * 3);
}
}
}
The Graphics context is automatically configured so that position 0x0 represents the top/left corner of the component
This means when you using something like MyFrame.WIDTH - 120, you will be painting beyond the visible bounds of the component.
Remember, a component has its own area of context, 0x0xwidthxheight. You shouldn't be using MyFrame.WIDTH in you components

Creating a JLabel with a Gradient

I'm new to Java and I'm trying to create a heading using a JLabel and for its fill to be a gradient. I cannot get it to work and I've been trying for a while. I've been grabbing bits of come from here and other websites and cannot seem to make this work, nor make sense of other peoples more complex code that does work. Here are my two classes so far:
import java.awt.Color;
import java.awt.Component;
import java.awt.Dimension;
import java.awt.Font;
import java.awt.Graphics;
import java.awt.Graphics2D;
import javax.swing.BorderFactory;
import javax.swing.BoxLayout;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.border.EtchedBorder;
public class Test {
public static void main(String[] args) {
new Test().setupGUI();
}
public void setupGUI() {
//set up frames and buttons etc.
JFrame theFrame = new JFrame ("Crystal Ball");
theFrame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
JPanel background = new JPanel();
background.setBackground(Color.BLUE);
background.setLayout(new BoxLayout(background, BoxLayout.PAGE_AXIS));
theFrame.setSize(500,1000);
DLabel heading = new DLabel("Guess a Number");
heading.setText("GUESS A NUMBER");
heading.setPreferredSize(new Dimension(theFrame.getWidth(),100));
heading.setFont(new Font("Serif", Font.PLAIN, 40));
heading.setAlignmentX(Component.CENTER_ALIGNMENT);
//heading.setBackground(Color.YELLOW);
heading.setBorder(BorderFactory.createEtchedBorder(EtchedBorder.RAISED));
background.add(heading);
theFrame.getContentPane().add(background);
theFrame.pack();
theFrame.setVisible(true);
//startGame();
}
}
import java.awt.Color;
import java.awt.Dimension;
import java.awt.GradientPaint;
import java.awt.Graphics;
import java.awt.Graphics2D;
import javax.swing.BorderFactory;
import javax.swing.JLabel;
public class DLabel extends JLabel
{
Dimension size = new Dimension(70, 80);
public DLabel(String name)
{
this.setPreferredSize(size);
this.setText(name);
this.setBorder(BorderFactory.createBevelBorder(TOP, Color.white, Color.black));
this.setOpaque(true);
}
public void paintComponent(Graphics g) {
// super.paintComponent(g); // *** commented
Graphics2D g2d = (Graphics2D) g;
Color color1 = Color.YELLOW;
Color color2 = color1.brighter();
int w = getWidth();
int h = getHeight();
GradientPaint gp = new GradientPaint(0, 0, color1, 0, h, color2);
g2d.setPaint(gp);
g2d.fillRect(0, 0, w, h);
super.paintComponent(g); // *** added
}
}
There is one little "trick" you can actually do, by leaving the label transparent, you can actually paint under the text by painting BEFORE you call super.paintComponent, for example...
import java.awt.Color;
import java.awt.EventQueue;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.LinearGradientPaint;
import java.awt.Point;
import java.awt.Rectangle;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.UIManager;
import javax.swing.UnsupportedLookAndFeelException;
public class TestLabel101 {
public static void main(String[] args) {
new TestLabel101();
}
public TestLabel101() {
EventQueue.invokeLater(new Runnable() {
#Override
public void run() {
try {
UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
} catch (ClassNotFoundException | InstantiationException | IllegalAccessException | UnsupportedLookAndFeelException ex) {
ex.printStackTrace();
}
JFrame frame = new JFrame("Testing");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.add(new TestPane());
frame.pack();
frame.setLocationRelativeTo(null);
frame.setVisible(true);
}
});
}
public class TestPane extends JLabel {
public TestPane() {
setText("Happy, Happy");
setForeground(Color.WHITE);
setHorizontalAlignment(CENTER);
}
#Override
protected void paintComponent(Graphics g) {
Graphics2D g2d = (Graphics2D) g.create();
LinearGradientPaint lgp = new LinearGradientPaint(
new Point(0, 0),
new Point(0, getHeight()),
new float[]{0.142f, 0.284f, 0.426f, 0.568f, 0.71f, 0.852f, 1f},
new Color[]{Color.PINK, Color.MAGENTA, Color.BLUE, Color.GREEN, Color.YELLOW, Color.ORANGE, Color.RED});
g2d.setPaint(lgp);
g2d.fill(new Rectangle(0, 0, getWidth(), getHeight()));
g2d.dispose();
super.paintComponent(g);
}
}
}
nb: I should point out that this process is inefficient, as the RepaintManager will still want to paint under the component
There is another trick, but my two year old daughter wants to check to see if Santa is here ;)
Updated
The other trick involves understanding how the paint process actually works. When you call super.paintComponent, it calls the update method on the ComponentUI (look and feel delegate), this is actually the method that fills the background if the component is opaque, this method then calls the look and feels delegate's paint method, which actually does the base painting...
We can circumvent the process slightly and instead of calling super.paintComponent, we can call the look and feels delegate's paint method directly...
public class TestPane extends JLabel {
public TestPane() {
setText("Happy, Happy");
setForeground(Color.WHITE);
setHorizontalAlignment(CENTER);
setOpaque(true);
}
#Override
protected void paintComponent(Graphics g) {
Graphics2D g2d = (Graphics2D) g.create();
LinearGradientPaint lgp = new LinearGradientPaint(
new Point(0, 0),
new Point(0, getHeight()),
new float[]{0.142f, 0.284f, 0.426f, 0.568f, 0.71f, 0.852f, 1f},
new Color[]{Color.PINK, Color.MAGENTA, Color.BLUE, Color.GREEN, Color.YELLOW, Color.ORANGE, Color.RED});
g2d.setPaint(lgp);
g2d.fill(new Rectangle(0, 0, getWidth(), getHeight()));
g2d.dispose();
getUI().paint(g, this);
}
}
This is more efficient then the previous example, as it doesn't require the RepaintManager to paint the area underneath this component, but it might not work with all look and feels
The problem is that you made the JLabel opaque, which means it will paint the background. So the call to super.paintComponent(...) over paints the gradient background. So get rid of:
//this.setOpaque(true);
Another problem with the code is that color1.brighter() doesn't work. Try something like:
Color color2 = Color.RED;
Also, You should not change the Graphics object, since that object is also used to paint other Swing components. Instead you should use g.create() to get a copy of the Graphics object. Make your changes to that object, do the painting and then dispose() the object.
So the (untested) code would be something like:
Graphics2D g2d = (Graphics2D)g.create();
...
g2d.fillRect(...);
g2d.dispose();
super.paintCompoenent(g);
You should set your gradientPaint object to your Graphics and then pass that into super.paintComponent
try this:
public void paintComponent(Graphics g) {
Graphics2D g2d = (Graphics2D) g;
Color color1 = Color.YELLOW;
Color color2 = color1.brighter();
int w = getWidth();
int h = getHeight();
GradientPaint gp = new GradientPaint(0, 0, color1, 0, h, color2);
g2d.setPaint(gp);
super.paintComponent(g2d);
}

Assigning a image to a String

Is there any way that I could assign a specific image to a String so that the output would be something like this (im using the String with a JLabel):
The basic process is to create an outline of the text and render it...easy ;)
This uses the TextLayout class to generate a Shape of the text, which can filled and drawn.
import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.Dimension;
import java.awt.EventQueue;
import java.awt.Font;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.Rectangle;
import java.awt.RenderingHints;
import java.awt.Shape;
import java.awt.font.FontRenderContext;
import java.awt.font.TextLayout;
import java.awt.geom.AffineTransform;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.UIManager;
import javax.swing.UnsupportedLookAndFeelException;
public class TextOutline {
public static void main(String[] args) {
new TextOutline();
}
public TextOutline() {
EventQueue.invokeLater(new Runnable() {
#Override
public void run() {
try {
UIManager.setLookAndFeel(UIManager.getSystemLookAndFeelClassName());
} catch (ClassNotFoundException | InstantiationException | IllegalAccessException | UnsupportedLookAndFeelException ex) {
}
JFrame frame = new JFrame("Testing");
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.setLayout(new BorderLayout());
frame.add(new FontPaint());
frame.pack();
frame.setLocationRelativeTo(null);
frame.setVisible(true);
}
});
}
class FontPaint extends JPanel {
public FontPaint() {
setFont(getFont().deriveFont(Font.BOLD, 48f));
}
#Override
public Dimension getPreferredSize() {
return new Dimension(300, 200);
}
#Override
public void paintComponent(Graphics g) {
super.paintComponent(g);
int w = getWidth();
int h = getHeight();
Graphics2D g2d = (Graphics2D) g;
FontRenderContext fontRendContext = g2d.getFontRenderContext();
// Not required, but it will make it look nice
g2d.setRenderingHint(RenderingHints.KEY_ALPHA_INTERPOLATION, RenderingHints.VALUE_ALPHA_INTERPOLATION_QUALITY);
g2d.setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
g2d.setRenderingHint(RenderingHints.KEY_COLOR_RENDERING, RenderingHints.VALUE_COLOR_RENDER_QUALITY);
g2d.setRenderingHint(RenderingHints.KEY_DITHERING, RenderingHints.VALUE_DITHER_ENABLE);
g2d.setRenderingHint(RenderingHints.KEY_FRACTIONALMETRICS, RenderingHints.VALUE_FRACTIONALMETRICS_ON);
g2d.setRenderingHint(RenderingHints.KEY_INTERPOLATION, RenderingHints.VALUE_INTERPOLATION_BILINEAR);
g2d.setRenderingHint(RenderingHints.KEY_RENDERING, RenderingHints.VALUE_RENDER_QUALITY);
g2d.setRenderingHint(RenderingHints.KEY_STROKE_CONTROL, RenderingHints.VALUE_STROKE_PURE);
String st = "Hello World.";
// Create an layout of the text
TextLayout text = new TextLayout(st, getFont(), fontRendContext);
// Generate a shape of the layout
Shape shape = text.getOutline(null);
// Align the shape to the center
Rectangle rect = shape.getBounds();
AffineTransform affineTransform = new AffineTransform();
affineTransform = g2d.getTransform();
affineTransform.translate(w / 2 - (rect.width / 2), h / 2
+ (rect.height / 2));
g2d.transform(affineTransform);
// Fill in blue
g2d.setColor(Color.BLUE);
g2d.fill(shape);
// Outline in red
g2d.setColor(Color.red);
g2d.draw(shape);
g2d.dispose();
}
}
}

Categories