I'm working on a game in which you have to click an object, if you clicked right you get 1 score and so on.
If you miss clicked the object you get -1 score.
Now I would like to repaint the image after clicking it, It now just goes on when clicked, only the score changes.
This is my code:
(Note: I left the imports out, because than it will be a mess in the OP)
public class Gamevenster extends JPanel implements Runnable {
public String Gamestatus = "active";
private Thread thread;
//public Main game;
public int random(int min, int max) {
int range = (max - min) + 1;
return (int)(Math.random() * range) + min;
}
public class TestComponent extends JComponent implements MouseListener {
/**
*
*/
private static final long serialVersionUID = 1L;
public TestComponent() {
this.addMouseListener(this);
}
#Override
public void mouseClicked(MouseEvent e) {
int clickedX = e.getX();
int clickedY = e.getY();
System.out.println("User Clicked: " + clickedX + ", " + clickedY);
}
#Override
public void mousePressed(MouseEvent e) {}
#Override
public void mouseReleased(MouseEvent e) {}
#Override
public void mouseEntered(MouseEvent e) {}
#Override
public void mouseExited(MouseEvent e) {}
}
Random rand = new Random();
private int x = 0;
private int y = 0;
Timer timer = new Timer(850, new ActionListener(){
#Override
public void actionPerformed(ActionEvent e) {
x = rand.nextInt(400);
y = rand.nextInt(330);
repaint();
}
});
public void paintComponent(Graphics g) {
super.paintComponent(g);
g.drawImage(achtergrond, 0, 0, this.getWidth(), this.getHeight(), null);
//g.drawImage(muisje, 10, 10, null);
g.drawImage(muisje, x, y, 100, 100, this);
}
private static final long serialVersionUID = 1L;
private JLabel scoreLabel = new JLabel("SCORE: " + "0");
private int score = 0;
Image achtergrond, muisje;
//JTextField invoer;
JButton raden;
JButton menu;
JButton restartBtn;
Gamevenster() { // CONSTRUCTOR
timer.start();
setLayout(null);
scoreLabel.setFont(new Font("Open Sans", Font.PLAIN, 30));
scoreLabel.setForeground(Color.WHITE);
scoreLabel.setBounds(20, 455, 200, 100);
add(scoreLabel);
addMouseListener(new MouseAdapter(){
#Override
public void mouseClicked(MouseEvent e) {
Point p = e.getPoint();
int clickX = (int)p.getX();
int clickY = (int)p.getY();
if(clickX > x && clickX < x + 100 && clickY > y && clickY < y + 100) {
score++;
scoreLabel.setText("SCORE: " + score);
repaint();
}else{
score = Math.max(0, score -1);
scoreLabel.setText("SCORE: " + score);
}
}
});
ImageIcon icon = new ImageIcon(this.getClass().getResource("assets/achtergrondspel.png"));
achtergrond = icon.getImage();
ImageIcon icon2 = new ImageIcon(this.getClass().getResource("assets/muisje.png"));
muisje = icon2.getImage();
//Get the default toolkit
Toolkit toolkit = Toolkit.getDefaultToolkit();
//Load an image for the cursor
Image image = toolkit.getImage("src/assets/hand.png");
//Create the hotspot for the cursor
Point hotSpot = new Point(0,0);
//Create the custom cursor
Cursor cursor = toolkit.createCustomCursor(image, hotSpot, "Hand");
//Use the custom cursor
setCursor(cursor);
// setLayout( null );
// Invoer feld
//invoer = new JTextField(10);
//invoer.setLayout(null);
//invoer.setBounds(150, 474, 290, 60); // Verander positie onder aan scherm is int 1
// Button voor raden
raden = new JButton("Raden");
raden.setLayout(null);
raden.setBounds(10, 474, 130, 60);
raden.setFont(new Font("Dialog", 1, 20));
raden.setForeground(Color.white);
raden.setBackground(new Color(46, 204, 113));
raden.setPreferredSize(new Dimension(130, 60));
// Menu knop
menu = new JButton("Menu");
menu.setLayout(null);
menu.setBounds(450, 474, 130, 60);
menu.setFont(new Font("Dialog", 1, 20));
menu.setForeground(Color.white);
menu.setBackground(new Color(46, 204, 113));
menu.setPreferredSize(new Dimension(130, 60));
// Toevoegen aan screen
//add(invoer);
//add(raden);
add(menu);
menu.addActionListener(new ActionListener() {
public void actionPerformed(ActionEvent e) {
String i = menu.getText();
System.out.println("Er is gedrukt! " + i);
}
});
}
public void start(){
thread = new Thread(this,"spelloop");
thread.start();
}
public void run() {
while(Gamestatus=="active"){
System.out.println("Gameloop werkt");
}
}
}
Related
I'm new to Java applets and I have to make a program where the pupils of two eyes follow a cursor.
There is a box around the face and when I enter the box with the cursor the "eyes" are supposed to center. I can't get the MouseListener mouseEntered to work right and fire when I drag the cursor over a component.
Thanks for any help you can give.
import javax.swing.*;
import java.awt.*;
import java.awt.event.*;
public class LookingProgram extends JApplet {
//
private int currentX = 0;
private int currentY = 0;
//Pupil sizes:
//PUPIL ONE
private int pupilOneX = 350;
private int pupilOneYheightY = 350;
//PUPIL TWO
private int pupilTwoX = 500;
private int pupilTwoY = 350;
//Left
private int leftRightP1 = pupilOneX - 15;
private int widthRightP2 = pupilTwoX - 15;
//Up
private int heightUpP1 = pupilOneYheightY - 30;
private int heightUpP2 = pupilTwoY - 30;
//Down
private int heightDownP1 = pupilOneYheightY + 30;
private int heightDownP2 = pupilTwoY + 30;
//Right
private int LookRightP1 = pupilOneX + 10;
private int LookRightP2 = pupilTwoX + 10;
private int widthDownP1Y = pupilOneYheightY + 30;
private boolean isEntered;
private boolean exited;
/**
* Init method
*/
public void init()
{
// Sets the background color to white.
getContentPane().setBackground(Color.white);
//Motion listener
addMouseMotionListener(new MyMouseMotionListener());
//Mouse Listener
addMouseListener(new MyMouseListener());
}
/**
* paint method
*/
public void paint(Graphics g)
{
// Call the super class paint method
super.paint(g);
//Black bordered rectangle
g.setColor(Color.black);
g.drawRect(200, 200, 500, 500);
g.fillOval(pupilOneX, pupilOneYheightY, 65, 50);
g.fillOval(pupilTwoX, pupilTwoY, 65, 50);
g.fillOval(450, 450, 25, 25);
g.drawOval(330, 295, 100, 150);
g.drawOval(480, 295, 100, 150);
g.drawLine(550, 550, 350, 550);
}
private class MyMouseListener implements MouseListener
{
public void mousePressed(MouseEvent e)
{
}
public void mouseClicked(MouseEvent e)
{
}
public void mouseReleased(MouseEvent e)
{
}
public void mouseEntered(MouseEvent e )
{
pupilOneX = 350;
pupilOneYheightY = 350;
pupilTwoX = 500;
pupilTwoY = 350;
repaint();
}
public void mouseExited(MouseEvent e)
{
}
}
private class MyMouseMotionListener implements MouseMotionListener
{
public void mouseDragged(MouseEvent arg0) {
}
public void mouseMoved(MouseEvent e)
{
currentX = e.getX();
currentY = e.getY();
// Look left
if(currentX < 350)
{
pupilOneX = leftRightP1;
pupilTwoX = widthRightP2;
}
//Look Right
if(currentX > 450)
{
pupilOneX = LookRightP1;
pupilTwoX = LookRightP2;
}
//Look Up
if(currentY < 150)
{
pupilOneYheightY = heightUpP1;
pupilTwoY = heightUpP2;
}
// Look down
if(currentY > 500)
{
pupilOneYheightY = widthDownP1Y;
pupilTwoY = heightDownP2;
}
repaint();
}
}
}
I have created a simple program that fills a meter by how many times you press a button, eventually resulting into a "Mash the button to win" style game. I have it set up where every time the spacebar is pressed, the meter fills by 10/440, and if you reach the maximum, 440, you win. The issue I am having is how to make the increments added smoother, and less abrupt; as if you are pumping a bike tire up: continuous, less incrememntal.
Here is the problematic code:
import javax.swing.JOptionPane;
import javax.swing.*;
import java.util.*;
import static java.lang.System.*;
import static java.lang.Math.*;
import java.awt.*;
import java.awt.event.*;
import java.io.*; //for files
public class MyClicker
{
public static void main(String args[])
{
new Clicker(); //Make a window
}
}
class Clicker extends Frame implements KeyListener, MouseListener
{
// global variables
private final static int SCHEIGHT=768,SCWIDTH=1024;
// direction constants
final static int N = 0,NE = 1,E = 2,SE = 3, S = 4, SW = 5, W = 6, NW =7,STILL = 8;
// movement change constants
final int X = 0,Y = 1,Z = 2;
final int TITLE = 30, STATUS = 40;
final static int size = 2;
Image myPic;
private boolean gameNotOver = true;
private boolean keyPressed = false;
private Image myScreen;
private int whichScreen;
private int timePassed;
private int numScreen;
private int maxAmt=450;
private int timer;
private int amt;
public Clicker()
{
setSize(SCWIDTH,SCHEIGHT);
addWindowListener(new WindowAdapter()
{
public void windowClosing(WindowEvent e)
{
System.exit(0);
}
});
timer = -1;
this.setVisible(true);
out.println(amt);
this.addKeyListener(this);
gameLoop();
}
public void gameLoop()
{
do
{
if (keyPressed)
{
amt = amt + 50;
out.println(keyPressed + " " +gameNotOver+" "+ "Time "+timer);
this.repaint();
keyPressed = false;
}
if(amt >= 400)
gameNotOver = false;
pause(1000);
timer++;
this.setVisible(true);
//this.repaint();
pause(0);
if(amt > maxAmt - 10)
amt = maxAmt - 10;
}
while (gameNotOver);
if(!gameNotOver)
{
pause(5000);
System.exit(0);
}
}
public int getAmt()
{
return amt;
}
public void paint(Graphics pen)
{
if(whichScreen==0)
{
pen.drawImage(myPic,100,200,506,279,this); //Draws the image
pen.setFont(new Font("Timesroman", Font.ITALIC, 50));
pen.drawString("Welcome to the Clicker Test", 200, 75);
pen.setFont(new Font("Timesroman", Font.ITALIC, 40));
pen.drawString("Created by Cody Coulter",150,150);
pen.setFont(new Font("Timesroman", Font.ITALIC, 25));
pause(200); // 2000 final
whichScreen++;
doubleBuffer(pen);
}
else
{
myScreen =createImage(getSize().width,getSize().height);
Graphics o = myScreen.getGraphics();
doubleBuffer(o);
pen.drawImage(myScreen,0,0,this);
}
}
public void doubleBuffer(Graphics pen) // Draws the window
{
pause (500);
numScreen++;
if (numScreen > 0)
{
setBounds(0,0,SCWIDTH,SCHEIGHT);
Color HPRed = new Color(213, 0, 0);
pen.setColor(Color.BLACK);
setTitle("Clicker Test -- Cody Coulter."+
"To click, press the space bar");
pen.setFont(new Font("Timesroman",Font.PLAIN,48));
pen.drawString("Clicker Test ",350,75);
pen.setFont(new Font("TimesRoman",Font.BOLD,33));
pen.fillRect((SCWIDTH/4), (SCHEIGHT/3), 50, maxAmt);
pen.drawString(""+timer, 350, 150);
pen.setColor(HPRed);
pen.fillRect((SCWIDTH/4)+5, (SCHEIGHT/3)+5, 40, amt);
if(!gameNotOver)
{
if(amt >= maxAmt-10)
{
pen.setColor(HPRed);
pen.fillRect(SCWIDTH/4-75, SCHEIGHT/3, SCWIDTH/2+150, SCHEIGHT/3-60);
pen.setColor(Color.GRAY);
pen.fillRect(SCWIDTH/4-65, SCHEIGHT/3+10, SCWIDTH/2+130, SCHEIGHT/3-80);
pen.setColor(Color.YELLOW);
pen.setFont(new Font("Verdana", Font.BOLD, 40));
pen.drawString("You got it!", SCWIDTH/2-290, SCHEIGHT/2-20);
}
}
this.repaint();
}
}
public void keyPressed(KeyEvent e)
{
keyPressed = true;
setTitle(""+ KeyEvent.getKeyText(e.getKeyCode()));
System.out.println("hit + "+ KeyEvent.getKeyText(e.getKeyCode())+ " " + keyPressed);
switch(e.getKeyCode())
{
case KeyEvent.VK_SPACE: if(amt < maxAmt - 10)
amt= amt + 10;
break;
case KeyEvent.VK_A: if(amt < maxAmt - 10)
amt = amt + 10;
break;
}
}
public void mouseClicked(MouseEvent m)
{
}
public void mouseEntered(MouseEvent m)
{
}
public void mouseExited(MouseEvent m)
{
}
public void mousePressed(MouseEvent m)
{
}
public void mouseReleased(MouseEvent m)
{
}
public void keyReleased(KeyEvent e)
{
}
public void keyTyped(KeyEvent e)
{
}
public void update(Graphics G)
{
paint(G);
}
public static void pause (long r)
{
try
{
Thread.sleep(r);
}
catch (Exception e)
{
out.println(" sleep error " + e);
}
}
} //end class
And here is the entirely up to date code:
import javax.swing.JOptionPane;
import javax.swing.*;
import java.util.*;
import static java.lang.System.*;
import static java.lang.Math.*;
import java.awt.*;
import java.awt.event.*;
import java.io.*; //for files
public class MyClicker
{
public static void main(String args[])
{
new Clicker(); //Make a window
}
}
class Clicker extends Frame implements KeyListener, MouseListener
{
// global variables
private final static int SCHEIGHT=768,SCWIDTH=1024;
// direction constants
final static int N = 0,NE = 1,E = 2,SE = 3, S = 4, SW = 5, W = 6, NW =7,STILL = 8;
// movement change constants
final int X = 0,Y = 1,Z = 2;
final int TITLE = 30, STATUS = 40;
final static int size = 2;
Image myPic;
private boolean gameNotOver = true;
private boolean keyPressed = false;
private Image myScreen;
private int whichScreen;
private int timePassed;
private int numScreen;
private int maxAmt=450;
private int dispAmt;
private int actAmt;
private double timer;
public Clicker()
{
setSize(SCWIDTH,SCHEIGHT);
addWindowListener(new WindowAdapter()
{
public void windowClosing(WindowEvent e)
{
System.exit(0);
}
});
timer = -1;
this.setVisible(true);
this.addKeyListener(this);
gameLoop();
}
public void gameLoop()
{
do
{
if (keyPressed)
{
out.println(keyPressed + " " +gameNotOver+" "+ "Time "+timer);
keyPressed = false;
}
if(dispAmt > maxAmt-10)
dispAmt = maxAmt;
if(actAmt >= maxAmt-10 || dispAmt >= maxAmt-10)
gameNotOver = false;
if(dispAmt < actAmt)
dispAmt++;
timer++;
this.setVisible(true);
// this.repaint();
// pause(0);
// if(actAmt > maxAmt - 10 || dispAmt > maxAmt - 10)
// actAmt = maxAmt - 10;
this.repaint();
}
while (gameNotOver);
if(!gameNotOver)
{
pause(5000);
System.exit(0);
}
}
public int getAmt()
{
return actAmt;
}
public void paint(Graphics pen)
{
if(whichScreen==0)
{
pen.drawImage(myPic,100,200,506,279,this); //Draws the image
pen.setFont(new Font("Timesroman", Font.ITALIC, 50));
pen.drawString("Welcome to the Clicker Test", 200, 75);
pen.setFont(new Font("Timesroman", Font.ITALIC, 40));
pen.drawString("Created by Cody Coulter",150,150);
pen.setFont(new Font("Timesroman", Font.ITALIC, 25));
pause(200); // 2000 final
whichScreen++;
doubleBuffer(pen);
}
else
{
myScreen =createImage(getSize().width,getSize().height);
Graphics o = myScreen.getGraphics();
doubleBuffer(o);
pen.drawImage(myScreen,0,0,this);
}
}
public void doubleBuffer(Graphics pen) // Draws the window
{
numScreen++;
if (numScreen > 0)
{
setBounds(0,0,SCWIDTH,SCHEIGHT);
Color HPRed = new Color(213, 0, 0);
pen.setColor(Color.BLACK);
setTitle("Clicker Test -- Cody Coulter."+
"To click, press the space bar");
pen.setFont(new Font("Timesroman",Font.PLAIN,48));
pen.drawString("Clicker Test ",350,75);
pen.setFont(new Font("TimesRoman",Font.BOLD,33));
pen.fillRect((SCWIDTH/4), (SCHEIGHT/3), 50, maxAmt);
pen.drawString(""+timer/1000, 350, 150);
pen.drawString(""+dispAmt+" / "+actAmt, 350, 200);
pen.setColor(HPRed);
pen.fillRect((SCWIDTH/4)+5, (SCHEIGHT/3)+5, 40, dispAmt);
if(!gameNotOver)
{
if(actAmt >= maxAmt-10)
{
pen.setColor(HPRed);
pen.fillRect(SCWIDTH/4-75, SCHEIGHT/3, SCWIDTH/2+150, SCHEIGHT/3-60);
pen.setColor(Color.GRAY);
pen.fillRect(SCWIDTH/4-65, SCHEIGHT/3+10, SCWIDTH/2+130, SCHEIGHT/3-80);
pen.setColor(Color.YELLOW);
pen.setFont(new Font("Verdana", Font.BOLD, 40));
pen.drawString("You got it!", SCWIDTH/2-290, SCHEIGHT/2-20);
}
}
this.repaint();
}
}
public void keyPressed(KeyEvent e)
{
keyPressed = true;
setTitle(""+ KeyEvent.getKeyText(e.getKeyCode()));
System.out.println("hit + "+ KeyEvent.getKeyText(e.getKeyCode())+ " " + keyPressed);
switch(e.getKeyCode())
{
case KeyEvent.VK_SPACE:actAmt = actAmt+10;
break;
case KeyEvent.VK_A: actAmt = actAmt+10;
break;
}
this.repaint();
}
public void mouseClicked(MouseEvent m)
{
}
public void mouseEntered(MouseEvent m)
{
}
public void mouseExited(MouseEvent m)
{
}
public void mousePressed(MouseEvent m)
{
}
public void mouseReleased(MouseEvent m)
{
}
public void keyReleased(KeyEvent e)
{
}
public void keyTyped(KeyEvent e)
{
}
public void update(Graphics G)
{
paint(G);
}
public static void pause (long r)
{
try
{
Thread.sleep(r);
}
catch (Exception e)
{
out.println(" sleep error " + e);
}
}
} //end class
Get rid of pause(1000) you can maybe make it pause(10) or something around that.
Call this.repaint() every time in your loop (outside of the if statement).
Split amt into two variables: the actual amount, and the displayed amount. Only draw the displayed amount, and have key presses only increase the actual amount.
Each frame, if displayed amount is less than actual amount increase it by 1.
Updated...
Remove pause(500) from the double buffer routine, and pause(200) from paint. In general, don't pause unless you need to do "nothing". Games never do "nothing", they almost always have a core loop that's at least rendering.
I have a gradient background and I want, slowly, for it to change colors, basically for it to go through different colors. The color has to blend through all the colors, I do not want it to flick through colors, is this possible? Please enlighten me with a solution, thanks.
Also consider java.awt.image.MemoryImageSource and a javax.swing.Timer, illustrated here and below.
Really too hard to say anything (whatever clever) to my defense, (try & enjoy)
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.image.BufferedImage;
import java.util.LinkedList;
import java.util.Queue;
import java.util.Random;
import javax.swing.*;
public class GradientPaintWithSwingTimerAndRunnable extends JFrame implements Runnable {
private static final long serialVersionUID = 1L;
private Queue<Icon> iconQueue = new LinkedList<Icon>();
private JLabel label = new JLabel();
private Random random = new Random();
private JPanel buttonPanel = new JPanel();
private JPanel labelPanel = new JPanel();
private Timer backTtimer;
private Timer labelTimer;
private JLabel one = new JLabel("one");
private JLabel two = new JLabel("two");
private JLabel three = new JLabel("three");
private final String[] petStrings = {"Bird", "Cat", "Dog",
"Rabbit", "Pig", "Fish", "Horse", "Cow", "Bee", "Skunk"};
private boolean runProcess = true;
private int index = 1;
private int index1 = 1;
public static void main(String[] args) {
SwingUtilities.invokeLater(new Runnable() {
#Override
public void run() {
GradientPaintWithSwingTimerAndRunnable t = new GradientPaintWithSwingTimerAndRunnable();
}
});
}
public GradientPaintWithSwingTimerAndRunnable() {
iconQueue.add(UIManager.getIcon("OptionPane.errorIcon"));
iconQueue.add(UIManager.getIcon("OptionPane.informationIcon"));
iconQueue.add(UIManager.getIcon("OptionPane.warningIcon"));
iconQueue.add(UIManager.getIcon("OptionPane.questionIcon"));
one.setFont(new Font("Dialog", Font.BOLD, 24));
one.setHorizontalAlignment(javax.swing.SwingConstants.CENTER);
two.setFont(new Font("Dialog", Font.BOLD, 24));
two.setHorizontalAlignment(javax.swing.SwingConstants.CENTER);
three.setFont(new Font("Dialog", Font.BOLD, 10));
three.setHorizontalAlignment(javax.swing.SwingConstants.CENTER);
labelPanel.setLayout(new GridLayout(0, 3, 4, 4));
labelPanel.add(one);
labelPanel.add(two);
labelPanel.add(three);
//labelPanel.setBorder(new LineBorder(Color.black, 1));
labelPanel.setOpaque(false);
JButton button0 = createButton();
JButton button1 = createButton();
JButton button2 = createButton();
JButton button3 = createButton();
buttonPanel.setLayout(new GridLayout(0, 4, 4, 4));
buttonPanel.add(button0);
buttonPanel.add(button1);
buttonPanel.add(button2);
buttonPanel.add(button3);
//buttonPanel.setBorder(new LineBorder(Color.black, 1));
buttonPanel.setOpaque(false);
label.setLayout(new BorderLayout());
label.add(labelPanel, BorderLayout.NORTH);
label.add(buttonPanel, BorderLayout.SOUTH);
Dimension d = Toolkit.getDefaultToolkit().getScreenSize();
label.setPreferredSize(new Dimension(d.width / 3, d.height / 3));
add(label, BorderLayout.CENTER);
setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
pack();
setVisible(true);
startBackground();
startLabel2();
new Thread(this).start();
printWords(); // generating freeze Swing GUI durring EDT
}
private JButton createButton() {
JButton button = new JButton();
button.setBorderPainted(false);
button.setBorder(null);
button.setFocusable(false);
button.setMargin(new Insets(0, 0, 0, 0));
button.setContentAreaFilled(false);
button.setIcon(nextIcon());
button.setRolloverIcon(nextIcon());
button.setPressedIcon(nextIcon());
button.setDisabledIcon(nextIcon());
nextIcon();
return button;
}
private Icon nextIcon() {
Icon icon = iconQueue.peek();
iconQueue.add(iconQueue.remove());
return icon;
}
// Update background at 4/3 Hz
private void startBackground() {
backTtimer = new javax.swing.Timer(750, updateBackground());
backTtimer.start();
backTtimer.setRepeats(true);
}
private Action updateBackground() {
return new AbstractAction("Background action") {
private static final long serialVersionUID = 1L;
#Override
public void actionPerformed(ActionEvent e) {
label.setIcon(new ImageIcon(getImage()));
}
};
}
// Update Label two at 2 Hz
private void startLabel2() {
labelTimer = new javax.swing.Timer(500, updateLabel2());
labelTimer.start();
labelTimer.setRepeats(true);
}
private Action updateLabel2() {
return new AbstractAction("Label action") {
private static final long serialVersionUID = 1L;
#Override
public void actionPerformed(ActionEvent e) {
two.setText(petStrings[index]);
index = (index + 1) % petStrings.length;
}
};
}
// Update lable one at 3 Hz
#Override
public void run() {
while (runProcess) {
SwingUtilities.invokeLater(new Runnable() {
#Override
public void run() {
one.setText(petStrings[index1]);
index1 = (index1 + 1) % petStrings.length;
}
});
try {
Thread.sleep(300);
} catch (Exception e) {
e.printStackTrace();
}
}
}
// Note: blocks EDT
private void printWords() {
for (int i = 0; i < petStrings.length; i++) {
String word = petStrings[i].toString();
System.out.println(word);
try {
Thread.sleep(100);
} catch (InterruptedException e) {
e.printStackTrace();
}
three.setText(word);
}
three.setText("<html> Concurency Issues in Swing<br>"
+ " never to use Thread.sleep(int) <br>"
+ " durring EDT, simple to freeze GUI </html>");
}
public BufferedImage getImage() {
int w = label.getWidth();
int h = label.getHeight();
GradientPaint gp = new GradientPaint(0f, 0f, new Color(
127 + random.nextInt(128),
127 + random.nextInt(128),
127 + random.nextInt(128)),
w, w,
new Color(random.nextInt(128), random.nextInt(128), random.nextInt(128)));
BufferedImage bi = new BufferedImage(w, h, BufferedImage.TYPE_INT_RGB);
Graphics2D g2d = bi.createGraphics();
g2d.setPaint(gp);
g2d.fillRect(0, 0, w, h);
g2d.setColor(Color.BLACK);
return bi;
}
}
I am using per-pixel transparency using AWTUtilities.setWindowOpaque() on JFrame, that contains JScrollPane. When transparency is on, the scrolling in that pane is very slow and laggy, without it is not. Trying this on Windows 7 and JDK 6.
public class MainFrame extends JFrame {
super();
setUndecorated(true);
AWTUtilities.setWindowOpaque(this, false); //this turns JScrollPane inside of this JFrame slow and laggy
}
Have anyone issued this? Thanks!
I can't see any scrolling issue, nor to create testing scenario for code that is based on good Swing rules, this code is quite too hard for processor(s) and GPU, Java6, Win7 64b
from code
import com.sun.awt.AWTUtilities;
import java.awt.*;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.image.BufferedImage;
import javax.swing.*;
import javax.swing.event.ChangeEvent;
import javax.swing.event.ChangeListener;
import javax.swing.table.TableModel;
public class ViewPortFlickeringOriginal {
private JFrame frame = new JFrame("Table");
private JViewport viewport = new JViewport();
private Rectangle RECT = new Rectangle();
private Rectangle RECT1 = new Rectangle();
private JTable table = new JTable(50, 3);
private javax.swing.Timer timer;
private int count = 0;
private GradientViewPortOriginal tableViewPort;
private static boolean loggerOpacity;
private JPanel panel = new JPanel();
private static JButton button;
public ViewPortFlickeringOriginal() {
tableViewPort = new GradientViewPortOriginal(table);
viewport = tableViewPort.getViewport();
viewport.addChangeListener(new ChangeListener() {
#Override
public void stateChanged(ChangeEvent e) {
if (tableViewPort.bolStart) {
RECT = table.getCellRect(0, 0, true);
RECT1 = table.getCellRect(table.getRowCount() - 1, 0, true);
Rectangle viewRect = viewport.getViewRect();
if (viewRect.intersects(RECT)) {
System.out.println("Visible RECT -> " + RECT);
tableViewPort.paintBackGround(new Color(250, 150, 150));
} else if (viewRect.intersects(RECT1)) {
System.out.println("Visible RECT1 -> " + RECT1);
tableViewPort.paintBackGround(new Color(150, 250, 150));
} else {
System.out.println("Visible RECT1 -> ???? ");
tableViewPort.paintBackGround(new Color(150, 150, 250));
}
}
}
});
frame.add(tableViewPort);
button = new JButton("Change Opacity for Java6 / Win7");
button.setBounds(100, 100, 50, 50);
button.setVisible(true);
panel.add(button);
loggerOpacity = true;
button.addActionListener(new ActionListener() {
#Override
public void actionPerformed(ActionEvent evt) {
Object src = evt.getSource();
if (src == button && loggerOpacity) {
AWTUtilities.setWindowOpacity(frame, 0.80f);
}
}
});
frame.add(panel, BorderLayout.SOUTH);
frame.setPreferredSize(new Dimension(600, 300));
frame.pack();
frame.setLocation(50, 100);
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
RepaintManager.setCurrentManager(new RepaintManager() {
#Override
public void addDirtyRegion(JComponent c, int x, int y, int w, int h) {
Container con = c.getParent();
while (con instanceof JComponent) {
if (!con.isVisible()) {
return;
}
if (con instanceof GradientViewPortOriginal) {
c = (JComponent) con;
x = 0;
y = 0;
w = con.getWidth();
h = con.getHeight();
}
con = con.getParent();
}
super.addDirtyRegion(c, x, y, w, h);
}
});
frame.setVisible(true);
start();
}
private void start() {
timer = new javax.swing.Timer(100, updateCol());
timer.start();
}
public Action updateCol() {
return new AbstractAction("text load action") {
private static final long serialVersionUID = 1L;
#Override
public void actionPerformed(ActionEvent e) {
System.out.println("updating row " + (count + 1));
TableModel model = table.getModel();
int cols = model.getColumnCount();
int row = 0;
for (int j = 0; j < cols; j++) {
row = count;
table.changeSelection(row, 0, false, false);
timer.setDelay(100);
Object value = "row " + (count + 1) + " item " + (j + 1);
model.setValueAt(value, count, j);
}
count++;
if (count >= table.getRowCount()) {
timer.stop();
table.changeSelection(0, 0, false, false);
java.awt.EventQueue.invokeLater(new Runnable() {
#Override
public void run() {
table.clearSelection();
tableViewPort.bolStart = true;
}
});
}
}
};
}
public static void main(String[] args) {
java.awt.EventQueue.invokeLater(new Runnable() {
#Override
public void run() {
ViewPortFlickeringOriginal viewPortFlickering = new ViewPortFlickeringOriginal();
}
});
}
}
class GradientViewPortOriginal extends JScrollPane {
private static final long serialVersionUID = 1L;
private final int h = 50;
private BufferedImage img = null;
private BufferedImage shadow = new BufferedImage(1, h, BufferedImage.TYPE_INT_ARGB);
private JViewport viewPort;
public boolean bolStart = false;
public GradientViewPortOriginal(JComponent com) {
super(com);
viewPort = this.getViewport();
viewPort.setScrollMode(JViewport.BLIT_SCROLL_MODE);
viewPort.setScrollMode(JViewport.BACKINGSTORE_SCROLL_MODE);
viewPort.setScrollMode(JViewport.SIMPLE_SCROLL_MODE);
paintBackGround(new Color(250, 150, 150));
}
public void paintBackGround(Color g) {
Graphics2D g2 = shadow.createGraphics();
g2.setPaint(g);
g2.fillRect(0, 0, 1, h);
g2.setComposite(AlphaComposite.DstIn);
g2.setPaint(new GradientPaint(0, 0, new Color(0, 0, 0, 0f), 0, h,
new Color(0.1f, 0.8f, 0.8f, 0.5f)));
g2.fillRect(0, 0, 1, h);
g2.dispose();
}
#Override
public void paint(Graphics g) {
if (img == null || img.getWidth() != getWidth() || img.getHeight() != getHeight()) {
img = new BufferedImage(getWidth(), getHeight(), BufferedImage.TYPE_INT_ARGB);
}
Graphics2D g2 = img.createGraphics();
super.paint(g2);
Rectangle bounds = getViewport().getVisibleRect();
g2.scale(bounds.getWidth(), -1);
int y = (getColumnHeader() == null) ? 0 : getColumnHeader().getHeight();
g2.drawImage(shadow, bounds.x, -bounds.y - y - h, null);
g2.scale(1, -1);
g2.drawImage(shadow, bounds.x, bounds.y + bounds.height - h + y, null);
g2.dispose();
g.drawImage(img, 0, 0, null);
}
}
but I'm able to demonstrating lazy scrolling for JScrollPane contains others JComponents as is JTable or JList or JTextArea or JTextPane
import java.awt.Color;
import java.awt.Component;
import java.awt.GridLayout;
import java.awt.event.AdjustmentEvent;
import java.awt.event.AdjustmentListener;
import javax.swing.*;
public class ListPanel extends JFrame {
private static final long serialVersionUID = 1L;
public ListPanel() {
setLayout(new GridLayout(0, 2, 10, 10));
DefaultListModel model = new DefaultListModel();
model.addElement(createButtons("one"));
model.addElement(createButtons("two"));
model.addElement(createButtons("three"));
model.addElement(createButtons("four"));
model.addElement(createButtons("five"));
model.addElement(createButtons("six"));
model.addElement(createButtons("seven"));
model.addElement(createButtons("eight"));
model.addElement(createButtons("nine"));
model.addElement(createButtons("ten"));
model.addElement(createButtons("eleven"));
model.addElement(createButtons("twelwe"));
JList list = new JList(model);
list.setCellRenderer(new PanelRenderer());
JScrollPane scroll1 = new JScrollPane(list);
final JScrollBar scrollBar = scroll1.getVerticalScrollBar();
scrollBar.addAdjustmentListener(new AdjustmentListener() {
#Override
public void adjustmentValueChanged(AdjustmentEvent e) {
System.out.println("JScrollBar's current value = " + scrollBar.getValue());
}
});
add(scroll1);
JScrollPane scroll2 = new JScrollPane(createPanel());
add(scroll2);
final JScrollBar scrollBar1 = scroll2.getVerticalScrollBar();
scrollBar1.addAdjustmentListener(new AdjustmentListener() {
#Override
public void adjustmentValueChanged(AdjustmentEvent e) {
System.out.println("JScrollBar's current value = " + scrollBar1.getValue());
}
});
}
public static JPanel createPanel() {
JPanel panel = new JPanel();
panel.setLayout(new GridLayout(0, 1, 1, 1));
panel.add(createButtons("one"));
panel.add(createButtons("two"));
panel.add(createButtons("three"));
panel.add(createButtons("four"));
panel.add(createButtons("five"));
panel.add(createButtons("six"));
panel.add(createButtons("seven"));
panel.add(createButtons("eight"));
panel.add(createButtons("nine"));
panel.add(createButtons("ten"));
panel.add(createButtons("eleven"));
panel.add(createButtons("twelwe"));
return panel;
}
public static JButton createButtons(String text) {
JButton button = new JButton(text);
return button;
}
public static void main(String[] args) {
SwingUtilities.invokeLater(new Runnable() {
#Override
public void run() {
ListPanel frame = new ListPanel();
frame.setDefaultCloseOperation(EXIT_ON_CLOSE);
//frame.pack();
frame.setSize(270, 200);
frame.setVisible(true);
}
});
}
class PanelRenderer implements ListCellRenderer {
#Override
public Component getListCellRendererComponent(JList list, Object value, int index, boolean isSelected, boolean cellHasFocus) {
JButton renderer = (JButton) value;
renderer.setBackground(isSelected ? Color.red : list.getBackground());
return renderer;
}
}
}
Is it possible to add multiple GlassPanes for a single JFrame, or do I have to use the uncomfortable LayeredPane with the Opacity attribute.
I have attached some code that shows what I want to do (provided by #camickr).
import java.awt.*;
import java.awt.event.*;
import java.util.*;
import javax.swing.*;
import javax.swing.border.*;
public class MultiplayGlassPane {
private static final long serialVersionUID = 1L;
private JFrame frame = new JFrame("frameTitle");
private JPanel fPanel = new JPanel();
private Random random = new Random();
private final static Border MESSAGE_BORDER = new EmptyBorder(10, 10, 10, 10);
private JLabel message = new JLabel();
private ArrayList<Star> stars = new ArrayList<Star>();
public MultiplayGlassPane() {
MyGlassPane glass = new MyGlassPane();
for (int i = 0; i < 35; i++) {
Star star = new Star(new Point(random.nextInt(580), random.nextInt(550)));
star.setColor(Color.orange);
star.setxIncr(-3 + random.nextInt(7));
star.setyIncr(-3 + random.nextInt(7));
glass.add(star);
}
frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
frame.add(glass, BorderLayout.CENTER);
frame.setLocation(20, 20);
frame.pack();
frame.setVisible(true);
DisabledGlassPane1 glassPane = new DisabledGlassPane1();
JRootPane rootPane = SwingUtilities.getRootPane(frame);
rootPane.setGlassPane(glassPane);
glassPane.activate("");
}
private class MyGlassPane extends JLabel {
private static final long serialVersionUID = 1L;
private ArrayList<Star> stars = new ArrayList<Star>();
private javax.swing.Timer timer = new javax.swing.Timer(20, new ActionListener() {
#Override
public void actionPerformed(ActionEvent e) {
for (Star star : stars) {
star.move();
}
repaint();
}
});
public void stopAnimation() {
if (timer.isRunning()) {
timer.stop();
}
}
public void startAnimation() {
if (!timer.isRunning()) {
timer.start();
}
}
#Override
public void addNotify() {
super.addNotify();
timer.start();
}
#Override
public void removeNotify() {
super.removeNotify();
timer.stop();
}
#Override
public Dimension getPreferredSize() {
return new Dimension(new Dimension(620, 620));
}
public MyGlassPane() {
this.setPreferredSize(new Dimension(620, 620));
}
public void add(Star star) {
stars.add(star);
}
#Override
public void paintComponent(Graphics g) {
super.paintComponent(g);
((Graphics2D) g).setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
for (Star star : stars) {
g.setColor(star.getColor());
g.fillPolygon(star);
}
}
}
class DisabledGlassPane1 extends JComponent implements KeyListener {
private static final long serialVersionUID = 1L;
public DisabledGlassPane1() {
setOpaque(false);
Color base = UIManager.getColor("inactiveCaptionBorder");
Color background = new Color(base.getRed(), base.getGreen(), base.getBlue(), 128);
setBackground(background);
setLayout(new GridBagLayout());
add(message, new GridBagConstraints());
message.setOpaque(true);
message.setBorder(MESSAGE_BORDER);
addMouseListener(new MouseAdapter() {
});
addMouseMotionListener(new MouseMotionAdapter() {
});
addKeyListener(this);
setFocusTraversalKeysEnabled(false);
Random random = new Random();
for (int i = 0; i < 50; i++) {
Star star = new Star(new Point(random.nextInt(490), random.nextInt(490)));
star.setColor(Color.magenta);
star.setxIncr(-3 + random.nextInt(7));
star.setyIncr(-3 + random.nextInt(7));
add(star);
}
}
#Override
protected void paintComponent(Graphics g) {
super.paintComponent(g);
((Graphics2D) g).setRenderingHint(RenderingHints.KEY_ANTIALIASING, RenderingHints.VALUE_ANTIALIAS_ON);
for (Star star : stars) {
g.setColor(star.getColor());
g.fillPolygon(star);
}
}
#Override
public void setBackground(Color background) {
super.setBackground(background);
Color messageBackground = new Color(background.getRGB());
message.setBackground(messageBackground);
}
public void keyPressed(KeyEvent e) {
e.consume();
}
public void keyTyped(KeyEvent e) {
}
public void keyReleased(KeyEvent e) {
e.consume();
}
public void activate(String text) {
if (text != null && text.length() > 0) {
message.setVisible(true);
message.setText(text);
message.setForeground(getForeground());
} else {
message.setVisible(false);
}
setVisible(true);
//setCursor(Cursor.getPredefinedCursor(Cursor.WAIT_CURSOR));
requestFocusInWindow();
}
public void deactivate() {
setCursor(null);
setVisible(false);
}
private javax.swing.Timer timer = new javax.swing.Timer(15, new ActionListener() {
#Override
public void actionPerformed(ActionEvent e) {
for (Star star : stars) {
star.move();
}
repaint();
}
});
public void stopAnimation() {
if (timer.isRunning()) {
timer.stop();
}
}
public void startAnimation() {
if (!timer.isRunning()) {
timer.start();
}
}
#Override
public void addNotify() {
super.addNotify();
timer.start();
}
#Override
public void removeNotify() {
super.removeNotify();
timer.stop();
}
public void add(Star star) {
stars.add(star);
}
}
private class Star extends Polygon {
private static final long serialVersionUID = 1L;
private Point location = null;
private Color color = Color.YELLOW;
private int xIncr, yIncr;
static final int WIDTH = 600, HEIGHT = 600;
Star(Point location) {
int x = location.x;
int y = location.y;
this.location = location;
this.addPoint(x, y + 8);
this.addPoint(x + 8, y + 8);
this.addPoint(x + 11, y);
this.addPoint(x + 14, y + 8);
this.addPoint(x + 22, y + 8);
this.addPoint(x + 17, y + 12);
this.addPoint(x + 21, y + 20);
this.addPoint(x + 11, y + 14);
this.addPoint(x + 3, y + 20);
this.addPoint(x + 6, y + 12);
}
public void setColor(Color color) {
this.color = color;
}
public void move() {
if (location.x < 0 || location.x > frame.getContentPane().getWidth() - 20) {
xIncr = -xIncr;
}
if (location.y < 0 || location.y > frame.getContentPane().getHeight() - 20) {
yIncr = -yIncr;
}
translate(xIncr, yIncr);
location.setLocation(location.x + xIncr, location.y + yIncr);
}
public void setxIncr(int xIncr) {
this.xIncr = xIncr;
}
public void setyIncr(int yIncr) {
this.yIncr = yIncr;
}
public Color getColor() {
return color;
}
}
public static void main(String[] args) {
SwingUtilities.invokeLater(new Runnable() {
#Override
public void run() {
MultiplayGlassPane Mpgp = new MultiplayGlassPane();
}
});
}
}
Look at http://docs.oracle.com/javase/tutorial/uiswing/components/rootpane.html for an explanation on Root panes and what the Glass pane actually is.
The glass pane is just a convenient way to add a component which has the size of the Root Pane, and which blocks all input events. This allows you to catch any interaction with your components to create a "Please wait..." screen.
There is only a single glass pane per root container. You cannot layer glass panes.
You can replace the contents of the glass pane by something else if you want to layer something over the current glass pane. You can also set a JPanel as a glass pane, which allows you to layout multiple components in the glass pane.
Usually, you should only use the glass pane to block user input (and, if necessary, display some kind of "please wait" message). Can you provide a use case of why you want to put glass panes on top of one another?