Java - GUI,面板和数据访问

时间:2010-10-04 05:13:48

标签: java class subclass jframe jpanel

我正在制作一个包含三个主要面板和一些子面板的游戏,我对如何“连接”面板及其数据感到困惑。

我有我的主类,它扩展了JFrame并添加了三个JPanel。这些面板中的每一个都是JPanel的子类。 (例如:JPanel gameControlPanel = new GameControlPanel(),其中GameControlPanel是我创建的用于扩展JPanel的类。)

现在,所有游戏数据(例如游戏状态,以及两个保存已保存玩家并保存得分的arraylists)都在游戏面板中。但我需要从其他两个面板中获取并设置该数据。如何做到这一点正在躲避我。

**所以我的问题是:我该怎么做?如何从另一个JPanel子类(具有相同的父JFrame)访问一个JPanel子类中的数据?


如果有帮助,这是扩展的JFrame类的代码,我添加了三个面板......:

    JPanel controlButtonsPanel = new GameControlButtons();
    controlButtonsPanel.setPreferredSize(new Dimension(801,60));
    controlButtonsPanel.setBorder(new LineBorder(Color.white, 1));
    constraints.anchor = GridBagConstraints.NORTHWEST;
    constraints.weightx = 2;
    constraints.weighty = 0.3;
    this.add(controlButtonsPanel, constraints);

    JPanel gameDataPanel = new GameDataPanel();
    gameDataPanel.setPreferredSize(new Dimension(500,838));
    gameDataPanel.setBorder(new LineBorder(Color.white, 2));
    constraints.anchor = GridBagConstraints.NORTHEAST;
    constraints.weightx = 1;
    constraints.weighty = 2;
    this.add(gameDataPanel, constraints);

    JPanel graphicsPanel = new RoofRunnerGame("Ken");
    constraints.anchor = GridBagConstraints.SOUTHWEST;
    constraints.weightx = 2;
    constraints.weighty = 1;
    graphicsPanel.setBorder(new LineBorder(Color.white, 1));
    graphicsPanel.setPreferredSize(new Dimension(800,800));
    graphicsPanel.requestFocus();
    this.add(graphicsPanel, constraints);       

graphicsPanel包含所有这些数据:

private ArrayList<Player> savedPlayers;                                     // Holds saved data for player's who paused and exited game.
private ArrayList<Player> savedScores;                                      // Holds high scores from player's who played game and died.
private ArrayList<Birds> birdList = new ArrayList<Birds>();                 // Not serialized due to its randomness and unimportance to player.
private ArrayList<Clouds> cloudList = new ArrayList<Clouds>();              // Not serialized due to its randomness and unimportance to player.
private Player gamePlayer;                                                  // Player object that holds all data for a game instance.

我想从其他两个面板(gameDataPanel的类和gameControlButton的类)中访问该数据。

3 个答案:

答案 0 :(得分:3)

研究Model View Controller模式。将游戏状态和数据存储到模型中,并使用Observers或侦听器向UI组件通知数据中的更改。

例如,如果您按照Swing的实现方式进行操作,请定义一个如下的侦听器界面:

public interface PlayersListener {
    void playerSaved(Player player);
}

然后,您可以使用类似于此的类Players代替savedPlayers列表:

public class Players {
    private List<PlayersListener> listeners = ...;
    private List<Player> players = ...;

    public void addPlayersListener(PlayersListener listener) {
        if (!listeners.contains(listener)) {
            listeners.add(listener);
        }
    }

    public voi removePlayerListener(PlayerListener listener) {
        listeners.remove(listener);
    }

    public voi savePlayer(Player player) {
        players.add(player);
        for (PlayerListener listener : listeners) {
            listener.playerSaved(player);
        }

当您创建一个需要观察已保存玩家的新Panel时,您只需将Players类的实例传递给构造函数中的面板:

controlButtonsPanel = new GameControlButtons(players);
..
gameDataPanel = new GameDataPanel(players);

在构造函数中,只需将面板注册为players的监听器。

这样,只要某事保存了一个玩家,无论它是哪个组件/类,所有感兴趣的各方都会收到通知。并确保将Players的同一个实例传递给所有面板。

这实际上是Swing组件的工作原理,如果你看一下例如JPanel,它有许多不同的addSomethingListener方法。侦听器是实现特定侦听器接口的类。并且模型可以在许多组件中交换,例如JTable使用TableModel,而TableModel又被定义为接口。但是在您的情况下,您可能不需要能够使用不同的模型实现。

答案 1 :(得分:0)

数据应存储在UI部件之间共享的模型中,仅使用UI面板进行演示。使用观察者模式通知UI演示模型中的更改。

答案 2 :(得分:0)

你说你想在多个面板中显示一些信息吗? 您可以使Global类静态保存此数据,然后使用get...();set...();方法从其他类访问此信息。

示例:

public class Global
 {
     private static Object objectName;

     public Object getObjectName()
     {
         return objectName;
     }

     public void setObjectName(Object objectName)
     {
         this.objectName = objectName;
     }
}

如果我需要进一步阐述,请告诉我。