この質問は、フレーム、Javaおよび Processing についてです。
この質問はかなり複雑に聞こえますが、実際はそうではありません。私はこれをシンプルな最小値に保つようにします。私は迷路ゲームで小さなボールを作成して、物理学とレンダリングに頭を悩ませています。今までは良い経験でしたが、レンガの壁に少しぶつかりました。
私が決定した一般的なレイアウトは、AWTフレーム内にPAppletを含み、フレームを閉じることでした。これは、一度に1つのパプレットのみを使用するように言われたためです。
PApplet
は、レンダリングライブラリである Processing のApplet
クラスです。
ここにはメインを含む3つのクラスがあります
public class Menu extends PApplet
{
//images and buttons
PImage background, playbtn1, playbtn2, hsbtn1, hsbtn2, abbtn1, abbtn2, exbtn1, exbtn2;
FBox pBtn, hBtn, eBtn;
FWorld menu;
//simple constructor
public Menu()
{
}
public void setup()
{
size(600, 400);
smooth();
Fisica.init(this);
menu = new FWorld();
//loading and placing images
background = loadImage("MenuAlt.jpg");
System.out.println(background);
playbtn1 = loadImage("play1.gif");
playbtn2 = loadImage("play2.gif");
hsbtn1 = loadImage("high1.gif");
hsbtn2 = loadImage("high2.gif");
exbtn1 = loadImage("exit1.gif");
exbtn2 = loadImage("exit2.gif");
//loading and placing buttons
pBtn = new FBox(120, 150);
pBtn.setPosition(135, 215);
pBtn.setDrawable(false);
hBtn = new FBox(120, 150);
hBtn.setPosition(295, 215);
hBtn.setDrawable(false);
eBtn = new FBox(120, 150);
eBtn.setPosition(455, 215);
eBtn.setDrawable(false);
//add item to world
menu.add(pBtn);
menu.add(hBtn);
menu.add(eBtn);
}
public void draw()
{
image(background, 0, 0);
image(playbtn1, 80, 140);
image(hsbtn1, 237, 135);
image(exbtn1, 400, 140);
mouseOver();
menu.draw();
}
//close this frame an open a new level, high score or exit
//depending on what the use clicks
public void mousePressed()
{
FBody pressed = menu.getBody(mouseX, mouseY);
if (pressed == pBtn)
{
System.out.println("play game");
this.getParent().getParent().getParent().getParent().setVisible(false);
ExampleFrame x = new ExampleFrame(new Level("level1.txt"));
x.setLocation(this.getParent().getParent().getParent().getParent().getLocation());
}
if (pressed == hBtn)
{
System.out.println("high scores");
this.getParent().getParent().getParent().getParent().setVisible(false);
/* these are just for finding the parent
System.out.println(this.getName());
System.out.println(this.getParent().getName());
System.out.println(this.getParent().getParent().getName());
System.out.println(this.getParent().getParent().getParent().getName());
System.out.println(this.getParent().getParent().getParent().getParent().getName());
*/
ExampleFrame x = new ExampleFrame(new HighScores()); //for testing, you can change this to new menu()
x.setLocation(this.getParent().getParent().getParent().getParent().getLocation());
}
if (pressed == eBtn)
{
System.out.println("exit");
System.exit(0);
}
}
exampleFrameクラス
public class ExampleFrame extends JFrame
{
PApplet app;
public ExampleFrame(PApplet emApp)
{
super("Ball Maze Game");
this.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
this.setLocation(200, 200);
app = emApp;
setSize(615,438);
setVisible(true);
setLayout(new BorderLayout());
add(app, BorderLayout.CENTER);
app.init();
}
}
メイン
public class Main
{
public static void main(String[] args)
{
ExampleFrame x = new ExampleFrame(new Menu());
}
}
MousePressed == ebtnがフレーム内のすべてのものであるときに発生する必要があることは削除され、ハイスコア画面がロードされます。ハイスコアはメニューとほとんど同じです。ここには十分な数があるので、コードを投稿する必要はありません。
2番目のクラスは、フレームとして機能し、PAppletを保持するクラスです
結論として、PAppletからFrameメソッドを呼び出す方法、またはすべてのPAppletsコンテンツを削除して別のPAppletをロードする別の方法を誰かが知っていますか?
答えるためにPAppletからFrameメソッドを呼び出す方法は?、コードスニペットを最小限に変更しました。この変更されたバージョンでは、ユーザーがマウスボタンをクリックすると、_System.out
_が発生します。
これで、Frame
オブジェクトにアクセスする方法が2つあります。ただし、その前に、次の2つの点を述べておきます。
new ExampleFrame(new Menu());
のようなPAppletを作成し、JFrame
にこのadd(app, BorderLayout.CENTER);
のように追加すると、ウィンドウ/パネルの複雑な階層が作成されます。これのように:
_javax.swing.JPanel
javax.swing.JLayeredPane
javax.swing.JRootPane
test.ExampleFrame
_
PApplet
は、フレームオブジェクトを設定およびアクセスするためのパブリックフィールドを提供します。そして驚くべきことに、それはframe
:)と呼ばれています。 app.init();
を呼び出す前に設定できます>>コード
**コード内のコメントをチェックしてください**
Modified ExampleFrame.Java
_import Java.awt.BorderLayout;
import javax.swing.JFrame;
import processing.core.PApplet;
public class ExampleFrame extends JFrame
{
private static final long serialVersionUID = 4792534036194728580L;
PApplet app;
public ExampleFrame(PApplet emApp)
{
super("Ball Maze Game");
this.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
this.setLocation(200, 200);
app = emApp;
setSize(615,438);
setVisible(true);
setLayout(new BorderLayout());
add(app, BorderLayout.CENTER);
// Setting my frame object
app.frame = this;
app.init();
}
// Sample Method
public void sampleMethod(String msg)
{
System.out.println("I think '"+ msg +"' called me !!");
}
}
_
Modified Menu.Java
_import Java.awt.Container;
import processing.core.PApplet;
import processing.core.PImage;
public class Menu extends PApplet
{
private static final long serialVersionUID = -6557167654705489372L;
PImage background;
static String tab = "";
//simple constructor
public Menu()
{
}
public void setup()
{
size(600, 400);
smooth();
background = loadImage("C:/temp/background.jpg");
}
public void draw()
{
image(background, 0, 0);
}
public void mousePressed()
{
Container p = getParent();
tab = "";
// FIRST WAY OF ACCESSING PARENT FRAME
while(p != null)
{
//printParentTree(p);
if(p instanceof ExampleFrame)
{
ExampleFrame myframe = (ExampleFrame)p;
myframe.sampleMethod("First Way");
break;
}
p = p.getParent();
}
// SECOND WAY OF ACCESSING PARENT FRAME
if(frame != null && (frame instanceof ExampleFrame))
{
ExampleFrame myframe = (ExampleFrame)p;
myframe.sampleMethod("Second Way");
}
}
void printParentTree(Container p)
{
System.out.println(tab+p.getClass().getName());
tab +='\t';
}
}
_
public void mousePressed()
メソッドをチェックアウトします。
完全を期すために、Main.Javaも含めています。
_public class Main {
public static void main(String[] args){
new ExampleFrame(new Menu());
}
}
_
ここで答えますすべてのPAppletsのコンテンツを削除し、別のPAppletをロードします
まあ私はそれをテストしていません。ただし、JPanel
をJApplet
に追加して、すべての描画を実行できます。つまり、子コントロールを作成します。再描画したい場合は、JPanel.removeAll()
を呼び出します。 javadocによると:
このコンテナからすべてのコンポーネントを削除します。このメソッドは、removeLayoutComponentメソッドを介してこのコンテナーのレイアウトからコンポーネントを削除するようにレイアウトマネージャーにも通知します。
この後、repaint
でJPanel
を呼び出します。それを試してみてください、それはうまくいくかもしれません:)。
MousePressed == ebtnがフレーム内のすべてのものであるときに発生する必要があることは削除され、ハイスコア画面がロードされます
デモ。ネストされたCardLayout
の下に、ActionListener
ではなくMouseListener
を追加します。両方のマウスに反応しますおよびキーボード入力。
同じ画面スペースに複数のGUI要素を含める方法は他にも多数あります。頭上から、JTabbedPane
、JSplitPane
、JDesktopPane
/JInternalFrame
、ハイスコアをJDialog
またはJOptionPane
..
import Java.awt.*;
import Java.awt.event.*;
import javax.swing.*;
class CardLayoutDemo {
public static void main(String[] args) {
Runnable r = new Runnable () {
public void run() {
final JRadioButton game = new JRadioButton("Game", true);
JRadioButton highScores = new JRadioButton("High Scores");
ButtonGroup bg = new ButtonGroup();
bg.add( game );
bg.add( highScores );
JPanel buttons = new JPanel(new
FlowLayout(FlowLayout.CENTER, 5, 5));
buttons.add( game );
buttons.add( highScores );
JPanel gui = new JPanel(new BorderLayout(5,5));
gui.add(buttons, BorderLayout.SOUTH);
final CardLayout cl = new CardLayout();
final JPanel cards = new JPanel(cl);
gui.add(cards);
cards.add(new JLabel("Level 1"), "game");
cards.add(new JLabel("High Scores"), "scores");
ActionListener al = new ActionListener(){
public void actionPerformed(ActionEvent ae) {
if (game.isSelected()) {
cl.show(cards, "game");
} else {
cl.show(cards, "scores");
}
}
};
game.addActionListener(al);
highScores.addActionListener(al);
JOptionPane.showMessageDialog(null, gui);
}
};
SwingUtilities.invokeLater(r);
}
}