Java – move background image in swing
Hello, I'm a novice programmer. We have a project We created a simple racing game with a moving background, but I insisted on my code and I didn't know what to do I need a moving background at the beginning of the game. Please help me I'm begging t_ T
This is my code:
public class Game extends JFrame implements KeyListener,ActionListener {
Random s = new Random();
int x = 0,y = 50,a = 0,b = 250,f = 900,a1 = 0,b2 = 350,a2 = 0,b3 = 150;
int Move;
int value;
JLabel spriteLabel1 = new JLabel(new ImageIcon("ss.gif"));
JLabel spriteLabel2 = new JLabel(new ImageIcon("ss.gif"));
JLabel spriteLabel3 = new JLabel(new ImageIcon("ss.gif"));
JLabel spriteLabel4 = new JLabel(new ImageIcon("ss.gif"));
JLabel background = new JLabel(new ImageIcon("geren.png"));
Timer T1 = new Timer(5000,this);
Timer T = new Timer(5,this);
public static void main(String args[]) {
new Game();
}
public Game() {
Container c = getContentPane();
c.setLayout(null);
c.add(spriteLabel1);
c.add(spriteLabel2);
c.add(spriteLabel3);
c.add(spriteLabel4);
c.add(background);
background.setBounds(0,1024,768);
addKeyListener(this);
setSize(1000,750);
setVisible(true);
}
public void paint(Graphics g) {
super.paint(g);
spriteLabel1.setBounds(x,y,60,1000);
spriteLabel2.setBounds(a,b,800);
spriteLabel3.setBounds(a1,b2,500);
spriteLabel4.setBounds(a2,b3,650);
}
public void keyPressed(KeyEvent e) {
String k = e.getKeyText(e.getKeyCode());
if (k.equals("D")) {
if (a != f) {
x = x + 15;
spriteLabel1.setIcon(new ImageIcon("ss.gif"));
repaint();
if (x > f) {
x = f;
spriteLabel1.setIcon(new ImageIcon("ss.gif"));
//JOptionPane.showMessageDialog(null,"Congratulations!!
//Sanji wins!","Result",JOptionPane.PLAIN_MESSAGE,//new ImageIcon("evolve sanji.gif"));
//System.exit(0);
}
repaint();
}
}
T.stop();
}
if(k.equals (
"D"))
{
if (x != f) {
T.start();
Move = 3;
}
}
public void keyReleased(KeyEvent e) {
}
public void keyTyped(KeyEvent e) {
}
public void actionPerformed(ActionEvent e) {
if (Move == 3) {
a = a + (s.nextInt(3));
a = a + value;
if (a > f) {
a = f;
}
spriteLabel2.setIcon(new ImageIcon("ss.gif"));
spriteLabel2.setBounds(a,100,800);
}
if (a == f) {
if (Move == 3) {
a1 = a1 + (s.nextInt(3));
a1 = a1 + value;
if (a1 > f) {
a1 = f;
}
spriteLabel3.setIcon(new ImageIcon("ss.gif"));
spriteLabel3.setBounds(a1,500);
}
if (Move == 3) {
a2 = a2 + (s.nextInt(5));
a2 = a2 + value;
if (a2 > f) {
a2 = f;
}
spriteLabel4.setIcon(new ImageIcon("ss.gif"));
spriteLabel4.setBounds(a2,650);
}
}
}
}
Solution
This is the spoiler
This is meat
I see you did something wrong:
>Keep creating new images Just use the same image. > Instead of using labels, I will just draw an image / bufferedimage on the painting surface. > Forget two timers You can use an expiration date That's the way you run your country. > Do not make any logic in the paint method In your current situation, you don't even need it because you don't even draw anything In my example, although I drew an image. > Do not paint on JFrame and overwrite the paint Instead, overwrite paintcomponent in JPanel and add the panel to the frame. > Finally, key components, usage (from graphics) –
public abstract boolean drawImage(Image img,int dx1,int dy1,int dx2,int dy2,int sx1,int sy1,int sx2,int sy2,ImageObserver observer)
You can get a better explanation in this post Basically, point s is the source image, so you can move SX1 and SX2 during the animation, which draws part of the moving image on the d-point painting surface
If you don't know how to make custom painting, I suggest you use performing custom painting
This is a complete example
(note that my image for the background is 2000 × 350)
import java.awt.Color;
import java.awt.Dimension;
import java.awt.FlowLayout;
import java.awt.Graphics;
import java.awt.Image;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import java.awt.image.BufferedImage;
import javax.imageio.ImageIO;
import javax.swing.ImageIcon;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.SwingUtilities;
import javax.swing.Timer;
public class MovingBackgroundDemo {
public MovingBackgroundDemo() {
JFrame frame = new JFrame();
frame.setDefaultCloSEOperation(JFrame.EXIT_ON_CLOSE);
frame.add(new AnimatingPanel());
frame.pack();
frame.setLocationRelativeTo(null);
frame.setVisible(true);
}
private class AnimatingPanel extends JPanel {
private static final int DIM_W = 350;
private static final int DIM_H = 350;
private static final int INCREMENT = 10;
private BufferedImage backgroundImage;
private Image runnerImage;
private int dx1,dy1,dx2,dy2;
private int srcx1,srcy1,srcx2,srcy2;
private int IMAGE_WIDTH;
public AnimatingPanel() {
initImages();
initImagePoints();
Timer timer = new Timer(40,new ActionListener() {
public void actionPerformed(ActionEvent e) {
moveBackground();
repaint();
}
});
timer.start();
FlowLayout layout = (FlowLayout)getLayout();
layout.setHgap(0);
layout.setVgap(0);
}
@Override
protected void paintComponent(Graphics g) {
super.paintComponent(g);
g.setColor(Color.WHITE);
g.fillRect(0,getWidth(),getHeight());
g.drawImage(backgroundImage,dx1,dy2,srcx1,srcy2,this);
g.drawImage(runnerImage,getHeight(),this);
}
@Override
public Dimension getPreferredSize() {
return new Dimension(350,350);
}
private void initImagePoints() {
dx1 = 0;
dy1 = 0;
dx2 = DIM_W;
dy2 = DIM_H;
srcx1 = 0;
srcy1 = 0;
srcx2 = DIM_W;
srcy2 = DIM_H;
}
private void initImages() {
try {
runnerImage = new ImageIcon(getClass().getResource("runner.gif")).getImage();
backgroundImage = ImageIO.read(getClass().getResource(
"background.png"));
IMAGE_WIDTH = backgroundImage.getWidth();
System.out.println(IMAGE_WIDTH);
} catch (Exception ex) {
ex.printStackTrace();
}
}
private void moveBackground() {
if (srcx1 > IMAGE_WIDTH) {
srcx1 = 0 - DIM_W;
srcx2 = 0;
} else {
srcx1 += INCREMENT;
srcx2 += INCREMENT;
}
}
}
public static void main(String[] args) {
SwingUtilities.invokelater(new Runnable() {
public void run() {
new MovingBackgroundDemo();
}
});
}
}
