Background not changing color

1.4k views Asked by At

So I'm trying to change the background on a full screen game I'm making from a tutorial, I'm trying to change the background to green, but it stays black, what's wrong with the code?

Screen.java

package debels;

import java.awt.*;
import javax.swing.JFrame;

public class Screen {
    private GraphicsDevice vc;

    public Screen(){
        GraphicsEnvironment env = GraphicsEnvironment.getLocalGraphicsEnvironment();
        vc = env.getDefaultScreenDevice();
    }

    public void setFullScreen(DisplayMode dm, JFrame window){
        window.setUndecorated(true);
        window.setResizable(false);
        vc.setFullScreenWindow(window);

        if (dm != null && vc.isDisplayChangeSupported()){
            try{
                vc.setDisplayMode(dm);
            }catch (Exception e){}
        }
    }

    public Window getFullScreen(){
        return vc.getFullScreenWindow();
    }

    public void restoreScreen(){
        Window w = vc.getFullScreenWindow();
        if (w != null){
            w.dispose();
        }
        vc.setFullScreenWindow(null);
    }
}

Main.java

package debels;

import java.awt.*;
import javax.swing.*;

public class Main extends JFrame{
    private static final long serialVersionUID = -7498470134154894036L;

    public static void main(String[] args){
        DisplayMode dm = new DisplayMode(800, 600, 16, DisplayMode.REFRESH_RATE_UNKNOWN);
        Main m = new Main();
        m.run(dm);
    }

    public void run(DisplayMode dm){
        setBackground(Color.GREEN);
        setForeground(Color.BLUE);
        setFont(new Font("Arial", Font.PLAIN, 24));

        Screen s = new Screen();
        try{
            s.setFullScreen(dm, this);
            try{
                Thread.sleep(5000);
            }catch(Exception e){}
        }finally{
            s.restoreScreen();
        }
    }

    public void paint(Graphics g){
        g.drawString("Hello",  200, 200);
    }
}
3

There are 3 answers

5
MadProgrammer On BEST ANSWER

Your first problem is going to be your paint method...

public void paint(Graphics g){
    g.drawString("Hello",  200, 200);
}

Part of the responsibility of the paint method is to paint...the background. But since you're not calling super.paint this can't happen.

You should avoid overriding paint on top level containers, like JFrame and instead use a custom component, like JPanel for example, and override their paintComponent method (not forgetting to call super.paintComponent).

Another area of potential issue is the use of Thread.sleep, this could be causing the Event Dispatching Thread to be halted, preventing from processing new paint requests. A better solution might be to use a javax.swing.Timer, which will pause in the background and provide notification (via a ActionListener) within the context of the EDT...

For example

enter image description here

import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.DisplayMode;
import java.awt.EventQueue;
import java.awt.Font;
import java.awt.FontMetrics;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.GraphicsDevice;
import java.awt.GraphicsEnvironment;
import java.awt.Window;
import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.Timer;
import javax.swing.UIManager;
import javax.swing.UnsupportedLookAndFeelException;

public class TestFullScreen {

    public static void main(String[] args) {
        new TestFullScreen();
    }

    public TestFullScreen() {
        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 TestPane());

                final Screen s = new Screen();
                DisplayMode dm = new DisplayMode(800, 600, 16, DisplayMode.REFRESH_RATE_UNKNOWN);
                s.setFullScreen(dm, frame);

                Timer timer = new Timer(5000, new ActionListener() {
                    @Override
                    public void actionPerformed(ActionEvent e) {
                        s.restoreScreen();
                    }
                });
                timer.start();
            }
        });
    }

    public class TestPane extends JPanel {

        public TestPane() {
            setBackground(Color.GREEN);
            setForeground(Color.WHITE);
            setFont(new Font("Arial", Font.PLAIN, 24));
        }

        @Override
        protected void paintComponent(Graphics g) {
            super.paintComponent(g);
            Graphics2D g2d = (Graphics2D) g.create();
            int width = getWidth();
            int height = getHeight();
            FontMetrics fm = g2d.getFontMetrics();
            String text = "It's not easy to be green";
            int x = (width - fm.stringWidth(text)) / 2;
            int y = ((height - fm.getHeight()) / 2) + fm.getAscent();
            System.out.println(width + "x" + height);
            System.out.println(x + "x" + y);
            g2d.drawString(text, x, y);
            g2d.dispose();
        }
    }

    public class Screen {

        private GraphicsDevice vc;

        public Screen() {
            GraphicsEnvironment env = GraphicsEnvironment.getLocalGraphicsEnvironment();
            vc = env.getDefaultScreenDevice();
        }

        public void setFullScreen(DisplayMode dm, JFrame window) {
            window.setUndecorated(true);
            window.setResizable(false);
            vc.setFullScreenWindow(window);

            if (dm != null && vc.isDisplayChangeSupported()) {
                try {
                    vc.setDisplayMode(dm);
                } catch (Exception e) {
                }
            }
        }

        public Window getFullScreen() {
            return vc.getFullScreenWindow();
        }

        public void restoreScreen() {
            Window w = vc.getFullScreenWindow();
            if (w != null) {
                w.dispose();
            }
            vc.setFullScreenWindow(null);
        }
    }
}
0
Uduak Akpan On

This is what I did to overcome the challenge. I removed the setBackground, setForeground, and setFont from the run method in the Main class and added them to the setFullScreen method in the Screen class:

    window.getContentPane().setBackground(Color.PINK);
    window.setForeground(Color.BLUE);
    window.setFont(new Font ("Arial", Font.PLAIN, 24));

Thereafter, I added "super.paint(g);" as the first line of the paint method in the Main class

0
Akshay Ashok On

You just need to make 3 little changes and it will work. Follow these steps:

Step-1:Add getContentPane() to setBackgroud() which is present in the run() method

getContentPane().setBackground(Color.GREEN);

Step-2: Cut & paste below lines from run() method to paint() method.

getContentPane().setBackground(Color.GREEN);
setForeground(Color.BLUE);
setFont(new Font("Arial", Font.PLAIN, 24));

step-3: Add super.paint(g) in the starting of paint() method. the whole paint() method will look like this;

public void paint(Graphics g){
        super.paint(g);
        getContentPane().setBackground(Color.GREEN);
        setForeground(Color.BLUE);
        setFont(new Font("Arial", Font.PLAIN, 24));
        g.drawString("Hello",  200, 200);
       }

if it still doesn't work let me know in the comment! #YNWA