2

好的,我知道以前有人问过这个问题,但我似乎无法在其他人的帖子的帮助下让我的应用程序正常工作。

我只是想用我制作的图片制作一个屏幕,然后是 3 个按钮(就像游戏菜单一样)。我已经完成了图像,现在我正在尝试制作这样的 3 个按钮。

屏幕

我现在的代码是这样的:

public class Test {
   static int WIDTH = 700;
   static int HEIGHT = 600;

   public static void main(String[] args) {
      JLabel label = new JLabel();
      JFrame f = new JFrame();
      JPanel panel = new JPanel();
      JButton button = new JButton("hello again");
      button.addActionListener ((ActionListener) new Action1());

      label.setIcon(new ImageIcon("C:\\Users\\barney\\workspace\\game\\res\\background.jpg"));
      f.add(panel);
      f.add(label);
      f.setVisible(true);
      f.setDefaultCloseOperation(f.EXIT_ON_CLOSE);
      f.setSize(WIDTH, HEIGHT);
      f.setResizable(false);
      f.setLocationRelativeTo(null);
      f.setTitle("2d platformer v1.1");
      f.setVisible(true);
   }
}

那么我将如何添加图片中的按钮

你能告诉我我是否把我的代码设置错了,因为我是java新手。

谢谢。

4

3 回答 3

5

我会因为这个被打脸...

label.setLayout(new GridBagLayout());
GridBagConstraints gbc = GridBagConstraints();
gbc.insets = new Insets(4, 0, 4, 0);
gbc.gridwidth = GridBagConstraints.REMAINDER;

label.add(button, gbc);
// add the other buttons

更新

就个人而言,我会创建一个 custom JPanel,它会绘制背景,然后使用GridBagLayout上面的

更新

这个问题的问题是“取决于”

这取决于您希望如何实现实际按钮。因为您留下了“空白”空间,所以我假设您打算在图像上渲染一些按钮。我个人会渲染一个完整的图像,然后添加一些普通按钮,但这是你的项目,不是我的。

如果您想使用类似JButton(或任何其他Component)的东西,您将需要一个自定义布局管理器来帮助您将组件与您留下的间隙对齐。因此,我会简单地做一个漂亮的背景并使用类似的东西GridBagLayout......

抱歉,我可能有点过火了,但我玩得很开心。

在此处输入图像描述

import java.awt.BorderLayout;
import java.awt.Color;
import java.awt.Dimension;
import java.awt.EventQueue;
import java.awt.FontMetrics;
import java.awt.Graphics;
import java.awt.Graphics2D;
import java.awt.Point;
import java.awt.RadialGradientPaint;
import java.awt.Rectangle;
import java.awt.event.MouseAdapter;
import java.awt.event.MouseEvent;
import java.awt.geom.RoundRectangle2D;
import java.awt.image.BufferedImage;
import java.io.IOException;
import javax.imageio.ImageIO;
import javax.swing.JFrame;
import javax.swing.JPanel;
import javax.swing.UIManager;
import javax.swing.UnsupportedLookAndFeelException;

public class ButtonImage {

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

    public ButtonImage() {
        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 MenuPane());
                frame.pack();
                frame.setLocationRelativeTo(null);
                frame.setVisible(true);
            }
        });
    }

    public static class MenuPane extends JPanel {

        public static final Rectangle NEW_GAME_BOUNDS = new Rectangle(221, 157, 262, 85);
        public static final Rectangle LOAD_GAME_BOUNDS = new Rectangle(221, 276, 262, 85);
        public static final Rectangle EXIT_GAME_BOUNDS = new Rectangle(221, 396, 262, 85);
        private BufferedImage img;
        private Rectangle selectedBounds;

        public MenuPane() {
            try {
                img = ImageIO.read(getClass().getResource("/vtr1a.jpg"));
            } catch (IOException ex) {
                ex.printStackTrace();
            }
            MouseAdapter mouseHandler = new MouseAdapter() {
                @Override
                public void mouseMoved(MouseEvent e) {
                    if (getNewGameBounds().contains(e.getPoint())) {
                        System.out.println("in new");
                        selectedBounds = getNewGameBounds();
                    } else if (getLoadGameBounds().contains(e.getPoint())) {
                        System.out.println("in load");
                        selectedBounds = getLoadGameBounds();
                    } else if (getExitGameBounds().contains(e.getPoint())) {
                        System.out.println("in exit");
                        selectedBounds = getExitGameBounds();
                    } else {
                        selectedBounds = null;
                    }
                    repaint();
                }

                @Override
                public void mouseClicked(MouseEvent e) {
                    if (getNewGameBounds().contains(e.getPoint())) {
                        System.out.println("New Game");
                    } else if (getLoadGameBounds().contains(e.getPoint())) {
                        System.out.println("Load Game");
                    } else if (getExitGameBounds().contains(e.getPoint())) {
                        System.out.println("Exit Game");
                    }
                }
            };
            addMouseListener(mouseHandler);
            addMouseMotionListener(mouseHandler);
        }

        @Override
        public Dimension getPreferredSize() {
            return img == null ? super.getPreferredSize() : new Dimension(img.getWidth(), img.getHeight());
        }

        protected Point getImageOffset() {

            Point p = new Point();
            if (img != null) {
                p.x = (getWidth() - img.getWidth()) / 2;
                p.y = (getHeight() - img.getHeight()) / 2;
            }

            return p;

        }

        @Override
        protected void paintComponent(Graphics g) {
            super.paintComponent(g);

            if (img != null) {
                Graphics2D g2d = (Graphics2D) g.create();

                Point p = getImageOffset();

                g2d.drawImage(img, p.x, p.y, this);

                drawText(g2d, "New Game", getNewGameBounds());
                drawText(g2d, "Load Game", getLoadGameBounds());
                drawText(g2d, "Exit Game", getExitGameBounds());

                g2d.dispose();
            }
        }

        protected void drawText(Graphics2D g2d, String text, Rectangle bounds) {

            FontMetrics fm = g2d.getFontMetrics();

            g2d.setColor(Color.GRAY);
            if (selectedBounds != null) {
                if (bounds.contains(selectedBounds)) {
                    RadialGradientPaint rpg = new RadialGradientPaint(
                            new Point(bounds.x + (bounds.width / 2), bounds.y + (bounds.height / 2)),
                            Math.min(bounds.width, bounds.height), 
                            new float[]{0f, 1f},
                            new Color[]{new Color(252, 180, 42), new Color(97, 205, 181)}
                            );
                    g2d.setPaint(rpg);
                    RoundRectangle2D fill = new RoundRectangle2D.Float(bounds.x, bounds.y, bounds.width, bounds.height, 22, 22);
                    g2d.fill(fill);
                    g2d.setColor(Color.WHITE);
                }
            }

            g2d.drawString(
                    text,
                    bounds.x + ((bounds.width - fm.stringWidth(text)) / 2),
                    bounds.y + ((bounds.height - fm.getHeight()) / 2) + fm.getAscent());

        }

        protected Rectangle getNewGameBounds() {
            return getButtonBounds(NEW_GAME_BOUNDS);
        }

        protected Rectangle getLoadGameBounds() {
            return getButtonBounds(LOAD_GAME_BOUNDS);
        }

        protected Rectangle getExitGameBounds() {
            return getButtonBounds(EXIT_GAME_BOUNDS);
        }

        protected Rectangle getButtonBounds(Rectangle masterBounds) {
            Rectangle bounds = new Rectangle(masterBounds);
            Point p = getImageOffset();
            bounds.translate(p.x, p.y);
            return bounds;
        }
    }
}

您可以轻松地为每个按钮使用单独的图像,而不是渲染文本/图形,而是在所需位置渲染图像。

查看自定义绘画2D 图形了解更多信息。

于 2013-03-11T19:55:05.093 回答
4

我猜你没有添加 ButtonJFrame

f.add(button)
于 2013-03-11T19:52:05.787 回答
1

由于您需要与 Swing 按钮不同的按钮,为了使事情更简单,您可以在 JPanel 中绘制按钮(使用 paintComponent 方法和 Java 2D)。每个 JPanel 都是一个按钮。他们,您将使用一些鼠标事件来检测点击等。另一种方法是对您的背景做同样的事情(几个带有图像的 JLabel)并在每个标签中注册鼠标事件。您还可以为您的按钮创建自己的外观和感觉,但这并不是那么简单。当然,您需要更改布局管理器以适合您的按钮。

于 2013-03-11T19:54:52.570 回答