繁体   English   中英

Java GUI:在不同的JFrame之间共享值

[英]Java GUI: Sharing values across different JFrames

我正在编写一些实验性GUI代码。 我正在尝试进行设置,因此调用main生成两个窗口,每个窗口都有一个按钮和一个标签。 标签显示了单击按钮的次数。 但是,我想要这样,如果您单击一个窗口中的按钮,则其他窗口中的标签会更新。 我该怎么做?

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

@SuppressWarnings("serial")
public class TestGUI extends JFrame {

    private static int count;
    private JButton button = new JButton("odp"); 
    private JLabel label = new JLabel();

    public TestGUI() {
        setDefaultCloseOperation(EXIT_ON_CLOSE);
        add(button);
        setLayout(new FlowLayout(FlowLayout.RIGHT));

        labelUpdateText();
        add(label);

        button.addActionListener(new ActionListener() {
            public void actionPerformed(ActionEvent e) {
                count++;
                labelUpdateText();
            }
        });

        pack();
        setVisible(true);
    }

    private void labelUpdateText() {
        label.setText("Count: " + count);
    }

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

}

1-我宁愿避免扩展JFrame,因为您实际上并没有创建新的JFrame类。

因此,不必将整个类都作为JFrame的子类(不是),您可以创建它们的实例而无需添加更多行为。

2-如果您要有两个标签来反映同一“事物”的价值,则必须在它们之间共享该事物(或请他人为您更新该价值)

因此,您将需要使用著名的MVC

  • 对要在两个标签中显示的计数器建模

  • 查看显示模型的标签

  • 控制器在它们之间进行交易的东西。

它们都属于应用程序,它们是应用程序的实例属性。

要查看它们如何组合在一起,我在这里粘贴代码:

import javax.swing.*;
import java.awt.event.ActionListener;
import java.awt.event.ActionEvent;
import java.util.*;

 // TwoWindows is the Application 
public class TwoWindows {
    // shared state ( model ) 
    private int clickCount = 0;

    // UI
    private List<JLabel> toUpdate = new ArrayList<JLabel>();

    // listener ( listens for clicks on buttons kind of controller  )
    private ActionListener actionListener = new ActionListener() {

        // Each time update the UI 
        public void actionPerformed( ActionEvent e ) {
            clickCount++; 
            for( JLabel label : toUpdate ) {
                label.setText( "Count: " + ( clickCount ) );
            }
        }
    };

    // Createsa winddow with a label and a button
    public void showWindow( String named ) {
        JFrame f = new JFrame( named );
        f.add( createButtonAndLabel() );
        f.pack();
        f.setVisible( true );
    }

    // Creates the label and button and adds this.actionListener
    // to each button. 
    private JComponent  createButtonAndLabel() {
        JPanel panel = new JPanel();
        JLabel label =  new JLabel("Count: 0");
        JButton clickMe = new JButton("Click me");
        // adding the label to a "view" list.
        toUpdate.add( label );
        // adding the listener to each button 
        clickMe.addActionListener( actionListener );
        panel.add( label );
        panel.add( clickMe );
        return panel;
    }

    // Run the app
    public static void main( String [] args ) {
        TwoWindows t = new TwoWindows();
        t.showWindow("A");
        t.showWindow("B");
    }
 }

这样,您可以拥有一个共享模型并根据需要更新尽可能多的视图。

替代文字http://img387.imageshack.us/img387/1106/capturadepantalla200910d.png

您将需要设置一个eventListener,并让按钮触发一个事件,该事件将更新共享变量(想到了AtomicInteger)并在捕获到该事件时更新按钮文本。

我将从不扩展JFrame并避免可变的静态变量开始。

最简单的进行方法是将施工分解为多个阶段。 首先创建两个标签。 然后构造其余部分。 每帧调用两次构造函数方法,每次将标签作为不同的参数。

更复杂的是要有一个模型。 动作侦听器(控制器)更新模型,并且该模型触发状态更改事件,该事件与另一个框架中的标签关联的侦听器(视图)侦听。

您可以执行以下操作:

在主要方法中:

TestGUI a, b;
a = new TestGUI(b);
b = new TestGUI(a);

然后添加到构造函数中:

public TestGUI(TestGUI other)

然后从任一GUI执行:

other.labelUpdateText();

您真的需要2个JFrame吗?

相反,您可以有一个主控和一个从属:一个可以是JFrame,另一个可以是非模式对话框。

(非模态,以便在最小化之前不会窃取并保持焦点)

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM