3

我需要将所有字段与各自的标签对齐,

在此处输入图像描述

这是我的代码:

     public class Progress extends JPanel implements ActionListener {

 public JLabel ClientIP; JTextField ip;
 JLabel ClientPassword; JTextField pass;
 JLabel Videoname; JTextField vname;
 JLabel perccomplete; JTextField percent;
 JLabel PacketsSent; JTextField pacsent;
 JLabel Connectiontype; JTextField conntype;
 JLabel noofvideossent; JTextField videosend;
 JButton disconnect; JButton refresh;
 JButton ok;

 public Progress() {
 ClientIP = new JLabel("Client's IP:");
 ClientPassword = new JLabel("Clients Password:");
 Videoname = new JLabel("Video being Transfered:");
 perccomplete = new JLabel("% of transfer Complete:");
 PacketsSent = new JLabel("No of Packets sent:");
 Connectiontype = new JLabel("Connection Type:");
 noofvideossent = new JLabel("No of Videos Sent:");
 String Ipad,Ipass,Iselvid;
 if(ClientIPAddr==null || ClientIPAddr.equals("")){
     Ipad="Not Connected";
 }else Ipad=ClientIPAddr.toString();
 if(vFilePassword ==null || vFilePassword.equals("")){
     Ipass="No Password";
 }else Ipass=vFilePassword;
 if(selected_video==null || selected_video.equals("")){
     Iselvid="Not Selected";
 }else Iselvid=selected_video;

 ip = new JTextField(Ipad);
 ip.setColumns(20);
 pass = new JTextField(Ipass);
 pass.setColumns(20);
 vname = new JTextField(Iselvid);
 vname.setColumns(20);
 percent = new JTextField("10%");
 percent.setColumns(20);
 pacsent =new JTextField(String.valueOf(RTSPSeqNb));
 pacsent.setColumns(20);
 String c;
 if(clientConnected==true)
     c="TCP";
 else c="not Connected";
 conntype = new JTextField(c);
 conntype.setColumns(20);
 videosend = new JTextField(String.valueOf(videocount));
 videosend.setColumns(20);

     //Tell accessibility tools about label/textfield pairs.
 ClientIP.setLabelFor(ip);
 ClientPassword.setLabelFor(pass);
 Videoname.setLabelFor(vname);
 perccomplete.setLabelFor(percent);
 PacketsSent.setLabelFor(pacsent);
 Connectiontype.setLabelFor(conntype);
 noofvideossent.setLabelFor(videosend);

 //Lay out the labels in a panel.
    JPanel labelPane = new JPanel(new GridLayout(0,1));
    labelPane.add(ClientIP);
    labelPane.add(ClientPassword);
    labelPane.add(Videoname);
    labelPane.add(perccomplete);
    labelPane.add(PacketsSent);
    labelPane.add(Connectiontype);
    labelPane.add(noofvideossent);

     //Layout the text fields in a panel.
    JPanel fieldPane = new JPanel(new GridLayout(0,1));
    fieldPane.add(ip);
    fieldPane.add(pass);
    fieldPane.add(vname);
    fieldPane.add(percent);
    fieldPane.add(pacsent);
    fieldPane.add(conntype);
    fieldPane.add(videosend);
    //Put the panels in this panel, labels on left,
    //text fields on right.
    //setBorder(BorderFactory.createEmptyBorder(20, 20, 20, 20));


    JPanel buttonPane = new JPanel(new GridLayout(0,1));
    disconnect = new JButton("Disconnect Client");
    disconnect.setActionCommand("Disconnect");
    disconnect.addActionListener(this);
    refresh = new JButton("Refresh Details");
    refresh.setActionCommand("refresh");
    refresh.addActionListener(this);
    ok = new JButton("OK");
    ok.setActionCommand("ok");
    ok.addActionListener(this);
    buttonPane.add(refresh);
    buttonPane.add(disconnect);
    buttonPane.add(ok);
    add(labelPane, BorderLayout.CENTER);
    add(fieldPane, BorderLayout.LINE_END);
    add(buttonPane, BorderLayout.AFTER_LAST_LINE);
 }


  private void createAndShowGUI() {
    //Create and set up the window.
    frame = new JFrame("Connected Client's Details");
    //frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);


    //Add contents to the window.
    frame.add(new Progress());
    //Display the window.
    frame.pack();
    frame.setVisible(true);
}

我尝试通过引用它来实现它,但它不起作用,有什么建议吗?

4

6 回答 6

2

查看给出的示例GroupLayout(来自链接的图片):

在此处输入图像描述

您的代码应该与链接中的代码非常相似。

于 2013-04-17T22:23:48.343 回答
1

根据经验,永远不要扩展JPanel/JFrame除非你真的在扩展它们的功能,总是 倾向于组合而不是继承

对于一个 swing 布局管理器,我强烈推荐miglayout,简单易上手,你必须下载jar并将其添加到你的CLASSPATH.

制作此GUI原型的完整代码

在此处输入图像描述

将很简单:

import java.awt.event.ActionEvent;
import java.awt.event.ActionListener;
import javax.swing.JButton;
import javax.swing.JFrame;
import javax.swing.JLabel;
import javax.swing.JPanel;
import javax.swing.JTextField;
import net.miginfocom.swing.MigLayout;

/**
 * Hello world!
 *
 */
public class App {

    private JPanel panel;

    private JLabel cilentIPLabel= new JLabel();
    private JLabel clientPWLabel= new JLabel();
    private JTextField clientIPTextField= new JTextField();
    private JTextField clientPWTextField= new JTextField();
    private JButton printButton = new JButton();

    public App() {
        initComponents();
    }


    private void initComponents() {
        cilentIPLabel.setText("Client IP :");
        clientPWLabel.setText("Client Password :");
        printButton.setText("print");
        printButton.addActionListener(new ActionListener() {
            public void actionPerformed(ActionEvent e) {        
                System.out.println("The ID of the clinet is " + clientIPTextField.getText());
            }
        });
    }

    public JPanel getPanel() {

        if (panel == null) {
            panel= new JPanel(new MigLayout("gap 10","[100]10[100, left, fill, grow]","[][]20[]"));
            panel.add(cilentIPLabel);
            panel.add(clientIPTextField, "wrap");
            panel.add(clientPWLabel);
            panel.add(clientPWTextField, "wrap");
            panel.add(printButton, "skip, tag apply");
        }
        return panel;       
    }


    public static void main(String[] args) {
        JFrame frame= new JFrame("SO demo");
        frame.setSize(400, 150);
        frame.setContentPane(new App().getPanel());
        frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
        frame.setVisible(true);

    }
}
于 2013-04-17T23:27:19.943 回答
1

几个选项:

于 2013-04-18T08:56:32.207 回答
0

使标签及其相应字段正确排列的唯一可靠方法是将它们放在同一个面板中并使用布局管理器的单个实例来排列它们。

网格布局

最简单的方法是使用两列网格布局:

JPanel fieldPane = new JPanel(new GridLayout(0, 2));
fieldPane.add(ClientIP);
fieldPane.add(ip);
fieldPane.add(ClientPassword);
fieldPane.add(pass);
fieldPane.add(Videoname);
fieldPane.add(vname);
fieldPane.add(perccomplete);
fieldPane.add(percent);
fieldPane.add(PacketsSent);
fieldPane.add(pacsent);
fieldPane.add(Connectiontype);
fieldPane.add(conntype);
fieldPane.add(noofvideossent);
fieldPane.add(videosend);

这具有一个缺点,即所有单元的大小都相同。具体来说,所有标签单元格将与字段单元格具有相同的宽度。在这种特定情况下,这可能无关紧要,但在更一般的情况下,您可能希望使用不同的布局,允许第一列保持窄,并将所有剩余宽度提供给第二列。

网格包布局

这是我使用 GridBagLayout 的方法:

JPanel fieldPane = new JPanel(new GridBagLayout());
Insets insets = new Insets(2, 2, 2, 2);
GridBagConstraints label = new GridBagConstraints(
    0, 0, 1, 1, 0.0, 0.0,
    GridBagConstraints.BASELINE_LEADING, GridBagConstraints.NONE,
    insets, 2, 2);
GridBagConstraints value = new GridBagConstraints(
    1, 0, 1, 1, 0.0, 0.0,
    GridBagConstraints.BASELINE_LEADING, GridBagConstraints.HORIZONTAL,
    insets, 2, 2);
fieldPane.add(ClientIP, label);
fieldPane.add(ip, value);
label.gridy++;
value.gridy++;
fieldPane.add(ClientPassword, label);
fieldPane.add(pass, value);
label.gridy++;
value.gridy++;
fieldPane.add(Videoname, label);
fieldPane.add(vname, value);
label.gridy++;
value.gridy++;
fieldPane.add(perccomplete, label);
fieldPane.add(percent, value);
label.gridy++;
value.gridy++;
fieldPane.add(PacketsSent, label);
fieldPane.add(pacsent, value);
label.gridy++;
value.gridy++;
fieldPane.add(Connectiontype, label);
fieldPane.add(conntype, value);
label.gridy++;
value.gridy++;
fieldPane.add(noofvideossent, label);
fieldPane.add(videosend, value);

因为我经常使用 GridBagLayout,所以我将 GridBagConstraints 子类化以使我的生活更轻松一些。我的子类除其他外具有以下方法:

public SuperGBC at(int x, int y) {
    gridx = x;
    gridy = y;
    return this;
}

它具有类似的方法anchor()fill()并且insets()无需指定所有值即可进行自身初始化。这使得上面的代码更加紧凑:

JPanel fieldPane = new JPanel(new GridBagLayout());
Insets insets = new Insets(2, 2, 2, 2);
SuperGBC label = new SuperGBC()
    .anchor(SuperGBC.BASELINE_LEADING)
    .insets(insets);
SuperGBC value = new SuperGBC()
    .anchor(SuperGBC.BASELINE_LEADING)
    .insets(insets)
    .fill(GridBagConstraints.HORIZONTAL, 0.0, 0.0);
fieldPane.add(ClientIP, label.at(0, 0));
fieldPane.add(ip, value.at(1, 0));
fieldPane.add(ClientPassword, label.at(0, 1));
fieldPane.add(pass, value.at(1, 1));
fieldPane.add(Videoname, label.at(0, 2));
fieldPane.add(vname, value.at(1, 2));
fieldPane.add(perccomplete, label.at(0, 3));
fieldPane.add(percent, value.at(1, 3));
fieldPane.add(PacketsSent, label.at(0, 4));
fieldPane.add(pacsent, value.at(1, 4));
fieldPane.add(Connectiontype, label.at(0, 5));
fieldPane.add(conntype, value.at(1, 5));
fieldPane.add(noofvideossent, label.at(0, 6));
fieldPane.add(videosend, value.at(1, 6));
于 2014-07-31T22:56:15.767 回答
0

非常感谢你的帮助。我修改了代码如下,它工作..

GroupLayout layout = new GroupLayout(getContentPane());
         getContentPane().setLayout(layout);
         layout.setAutoCreateGaps(true);
         layout.setAutoCreateContainerGaps(true);

         // Turn on automatically creating gaps between components that touch
         // the edge of the container and the container.
         layout.setAutoCreateContainerGaps(true);

         GroupLayout.SequentialGroup hGroup = layout.createSequentialGroup();
         hGroup.addGroup(layout.createParallelGroup(Alignment.LEADING).
                 addComponent(ClientIP).addComponent(ClientPassword).addComponent(Videoname).addComponent(perccomplete).addComponent(PacketsSent).addComponent(Connectiontype).addComponent(noofvideossent));

         hGroup.addGroup(layout.createParallelGroup(Alignment.LEADING).
                 addComponent(ip).addComponent(pass).addComponent(vname).addComponent(percent).
                 addComponent(pacsent).addComponent(conntype).addComponent(videosend).addComponent(disconnect).addComponent(refresh).addComponent(ok));
         layout.setHorizontalGroup(hGroup);


         GroupLayout.SequentialGroup vGroup = layout.createSequentialGroup();

         vGroup.addGroup(layout.createParallelGroup(Alignment.LEADING).addComponent(ClientIP).addComponent(ip)).addGroup(layout.createParallelGroup(Alignment.LEADING).addComponent(ClientPassword).addComponent(pass)).addGroup(layout.createParallelGroup(Alignment.LEADING).addComponent(Videoname).addComponent(vname)).addGroup(layout.createParallelGroup(Alignment.LEADING).addComponent(perccomplete).addComponent(percent)).addGroup(layout.createParallelGroup(Alignment.LEADING).addComponent(PacketsSent).addComponent(pacsent)).addGroup(layout.createParallelGroup(Alignment.LEADING).addComponent(Connectiontype).addComponent(conntype)).addGroup(layout.createParallelGroup(Alignment.LEADING).addComponent(noofvideossent).addComponent(videosend));

         vGroup.addGroup(layout.createParallelGroup(Alignment.LEADING).addComponent(disconnect)).addGroup(layout.createParallelGroup(Alignment.LEADING).addComponent(refresh)).addGroup(layout.createParallelGroup(Alignment.LEADING).addComponent(ok));
         layout.setVerticalGroup(vGroup);
于 2013-04-18T10:51:25.067 回答
0

经过一些发现 - MigLayout 看起来是我的最佳选择

代码如下:

JPanel parentPanel = new JPanel(new MigLayout("wrap 2")); //Autowrap after each 2 elements
parentPanel.add(label1);
parentPanel.add(field1);
parentPanel.add(label2);
parentPanel.add(field2);
...

无需手动指定索引或创建一些巨大的布局基础设施 - 简单的代码即可获得概念上简单的结果。请参阅快速入门指南: http: //www.miglayout.com/QuickStart.pdf

您可以将其插入或直接从 Maven 下载:https ://mvnrepository.com/artifact/com.miglayout/miglayout

于 2018-04-05T11:27:14.910 回答