• Swing-布局管理器应用--WIN7上计算器的UI实现


    学完了Swing布局管理器,为了加深理解我决定做一些UI的实现,那就从WIN7上的计算器开始吧!首先,我们来研究一下它的UI。该计算器的UI主要有3个,分别是标准型、科学型和程序员型,如下图所示。

     

     

     标准型UI

     

     

    科学型UI

     

     

    程序员型UI

     

    首先分析标准型UI:

     

    标准型UI分析

    该UI除菜单栏外,分两部分。考虑到它们在不同的UI中都会复用,我们将其分别使用screenPanel和standardPanel来进行实现。screenPanel没什么好说的,使用一个按钮独占整个面板,并设置按钮文字右对齐即可。为了实现按钮的充满效果,srceenPanel需要使用BorderLayout,并将按钮位置设置为CENTER。

    standardPanel则是标准的GridBagLayout样式,“MC”按钮位置为(0,0),“=”按钮独占2行1列,“0”按钮独占1行2列,其余按钮各只占1行1列。可以使用一个二维数组来定义这些键位,并在for循环中添加这些按钮。

     

    接下来分析科学型UI:

     

    科学型UI分析

    窗体的整体布局和layout不变,而且显示部分不变,复用screePanel即可。下部为一个mainPanel,它内含scitificFunctionPanel和standardNumPanel。而scitificFunctionPanel又内含一个angelPanel。mainPanel也采用GridBagLayout,位置分别位于(0,0)和(1,0)。当然也可以采用BorderLayout,这两个子面板分别放置在WEST和CENTER,那么这样有一个问题,全屏放大后缩放比例是不一样的,如下图:

     

    使用BorderLayout时的UI放大效果图

     

    而使用GridBagLayout就可以保证这两个子面板的缩放是完全平等的,缩放效果如下图:

     

    使用GridBagLayout时的UI放大效果图

     

     

    接下来分析程序员型UI:

     

    程序员型UI分析

    screenPanel保持不变,而mainPanel这次被划分成3部分,分别是binaryPanel、programFunctionPanel和standardNumPanel。它们分别使用GridBagLayout来实现。

    bitPanel的布局分解如下:

     

    bitPanel布局分析

    整个界面可分割为32个bitPanel;其中,第0、2行的bitPanel由4个label组成(因为每一位数均具有独立的事件响应);第1、3行的bitPanel只包含1个label。

    programFunctionPanel的布局分解如下:

     

    programFunctionPanel布局分析

    可见,除(0,0)和(0,3)的位置上各为1个占据3行1列的panel外,其余位置均为1个button。Panel内包含4个combobox。

     好啦,到现在所有的布局都分析完毕啦。下面是最终效果图:

    标准型效果

     

    标准型放大效果

     

    科学型效果

     

    科学型放大效果

     

    程序员型效果

     

    程序员型放大效果

    具体的代码:

    CalculatorUI.java

    import java.awt.BorderLayout;
    import java.awt.GridBagConstraints;
    import java.awt.GridBagLayout;
    import java.awt.event.ActionEvent;
    import java.awt.event.ActionListener;
    import javax.swing.BorderFactory;
    import javax.swing.JButton;
    import javax.swing.JFrame;
    import javax.swing.JMenu;
    import javax.swing.JMenuBar;
    import javax.swing.JMenuItem;
    import javax.swing.JPanel;
    import javax.swing.SwingConstants;
    
    /*
     * 主UI
     */
    public class CalculatorUI extends JFrame {
        JPanel contentPane;
        private JMenuBar menuBar = new JMenuBar();// 菜单栏
        private JButton screenButton = new JButton("0");// 结果显示栏
        String[] menuViewItemNames = { "标准型", "科学型", "程序员" };
        String[] menuNames = { "查看", "编辑", "帮助" };
    
        MenuItemHandler menuItemHandler = new MenuItemHandler();
    
        public CalculatorUI() {
            // 设置窗体属性
            setTitle("计算器");
            setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
            setLocationRelativeTo(null);
    
            // 添加菜单栏和菜单
            setJMenuBar(menuBar);
            for (String name : menuNames) {
                JMenu menu = new JMenu(name);
                menuBar.add(menu);
            }
    
            // “查看”菜单添加菜单项
            for (String name : menuViewItemNames) {
                JMenuItem menuItem = new JMenuItem(name);
                menuItem.addActionListener(menuItemHandler);
                menuBar.getMenu(0).add(menuItem);
            }
        }
    
        public void setBasicPane() {
            System.out.println("setBasicFrame called");
            // 设为窗体默认面板
            contentPane = new JPanel();
            contentPane.setLayout(new GridBagLayout());
            setContentPane(contentPane);
    
            // 添加显示按钮
            JPanel srceenPanel = new JPanel();
            srceenPanel.setBorder(BorderFactory.createEmptyBorder(3, 3, 3, 3));
            srceenPanel.setLayout(new BorderLayout());
            srceenPanel.add(screenButton, BorderLayout.CENTER);
            screenButton.setHorizontalAlignment(SwingConstants.RIGHT);// 文字右对齐
    
            // 添加显示面板
            contentPane.add(
                    srceenPanel,
                    new GBC(0, 0).setFill(GridBagConstraints.BOTH).setWeight(100,
                            100));
        }
    
        public void setStandardMode() {
            System.out.println("切换到标准型");
            setTitle("计算机-标准型");
            setBasicPane();
            StandardNumPanel standardPanel = new StandardNumPanel();
            getContentPane().add(
                    standardPanel,
                    new GBC(0, 1).setFill(GridBagConstraints.BOTH).setWeight(100,
                            100));
            showFrame();
        }
    
        public void setScitificMode() {
            System.out.println("切换到科学型");
            setTitle("计算机-科学型");
            setBasicPane();
            JPanel mainPanel = new JPanel();
            mainPanel.setLayout(new GridBagLayout());
            ScitificFunctionPanel scitificFunctionPanel = new ScitificFunctionPanel();
            StandardNumPanel standardNumPanel = new StandardNumPanel();
            mainPanel.add(
                    scitificFunctionPanel,
                    new GBC(0, 0).setFill(GridBagConstraints.BOTH).setWeight(100,
                            100));
            mainPanel.add(
                    standardNumPanel,
                    new GBC(1, 0).setFill(GridBagConstraints.BOTH).setWeight(100,
                            100));
            getContentPane().add(
                    mainPanel,
                    new GBC(0, 1).setFill(GridBagConstraints.BOTH).setWeight(100,
                            100));
            showFrame();
        }
    
        public void setProgramerMode() {
            System.out.println("切换到程序员型");
            setBasicPane();
            setTitle("计算机-程序员型");
            // 添加binaryPanel
            JPanel binaryPanel = new BinaryPanel();
            getContentPane().add(
                    binaryPanel,
                    new GBC(0, 1).setFill(GridBagConstraints.BOTH).setWeight(100,
                            100).setInsets(5));
            //构造mainPanel,使用ProgramFunctionPanel和StandardNumPanel填充
            JPanel mainPanel = new JPanel();
            mainPanel.setLayout(new GridBagLayout());
            mainPanel.add(new ProgramFunctionPanel(), new GBC(0,0).setFill(GridBagConstraints.BOTH).setWeight(100,
                            100).setInsets(5));
            mainPanel.add(new StandardNumPanel(), new GBC(1,0).setFill(GridBagConstraints.BOTH).setWeight(100,
                    100).setInsets(5));
            //添加mainPanel
            getContentPane().add(
                    mainPanel,
                    new GBC(0, 2).setFill(GridBagConstraints.BOTH).setWeight(100,
                            100));        
            showFrame();
        }
    
        public void calculateBinary() {
    
        }
    
        public void showFrame() {
            pack();
            setVisible(true);
        }
    
        public static void main(String[] args) {
            // TODO Auto-generated method stub
    
            CalculatorUI frame = new CalculatorUI();
            // frame.setScitificMode();
            frame.setProgramerMode();
            // frame.setStandardMode();
            // frame.setSize(200, 200);
            // frame.setVisible(true);
        }
    
        class MenuItemHandler implements ActionListener {
            public void actionPerformed(ActionEvent e) {
                if (e.getSource() instanceof JMenuItem) {
                    JMenuItem menuItem = (JMenuItem) e.getSource();
                    String name = menuItem.getText();
                    if (name != null && name.equals("标准型")) {
    
                        setStandardMode();
                    } else if (name != null && name.equals("科学型")) {
                        setScitificMode();
                    } else if (name != null && name.equals("程序员")) {
                        setProgramerMode();
                        // System.out.println("切换到程序员");
                    }
                }
            }
        }
    
        class BitButtonHandler implements ActionListener {
            public void actionPerformed(ActionEvent e) {
                if (e.getSource() instanceof JButton) {
                    JButton button = (JButton) e.getSource();
                    String text = button.getText();
                    String newText = text.equals("0") ? "1" : "0";
                    button.setText(newText);
                    // 计算数值并更新显示屏
                    calculateBinary();
                }
            }
        }
    }

    StandardNumPanel.java

    import java.awt.GridBagConstraints;
    import java.awt.GridBagLayout;
    import javax.swing.JButton;
    import javax.swing.JPanel;
    
    public class StandardNumPanel extends JPanel {
    
        public StandardNumPanel() {
            // 设置窗体layout
            setLayout(new GridBagLayout());
    
            // add buttons
            String[][] btnStrings = { { "MC", "MR", "MS", "M+", "M-" },
                    { "←", "CE", "C", "+-", "sqrt" },
                    { "7", "8", "9", "/", "%" }, { "4", "5", "6", "*", "1/x" },
                    { "1", "2", "3", "-", "=" }, { "0", "0", ".", "+", "=" } };
    
            boolean isBtnEqualsNeedsAdded = true;
            boolean isBtnPlusNeedsAdded = true;
    
            for (int i = 0; i < btnStrings.length; i++) {
                for (int j = 0; j < btnStrings[0].length; j++) {
                    if (btnStrings[i][j].equals("=") && isBtnEqualsNeedsAdded) {
                        add(new JButton(btnStrings[i][j]), new GBC(j, i , 1, 2)
                                .setFill(GridBagConstraints.BOTH).setInsets(3)
                                .setWeight(100, 100));
                        isBtnEqualsNeedsAdded = false;
                        continue;
                    }
                    if (btnStrings[i][j].equals("0") && isBtnPlusNeedsAdded) {
                        add(new JButton(btnStrings[i][j]), new GBC(j, i , 2, 1)
                                .setFill(GridBagConstraints.BOTH).setInsets(3)
                                .setWeight(100, 100));
                        isBtnPlusNeedsAdded = false;
                        continue;
                    }
                    add(new JButton(btnStrings[i][j]), new GBC(j, i , 1, 1)
                            .setFill(GridBagConstraints.BOTH).setInsets(3)
                            .setWeight(100, 100));
                }
            }
        }
    
        public static void main(String[] args) {
            // TODO Auto-generated method stub
        }
    }

    ScitificFunctionPanel.java

    import java.awt.BorderLayout;
    import java.awt.GridBagConstraints;
    import java.awt.GridBagLayout;
    import javax.swing.BorderFactory;
    import javax.swing.Box;
    import javax.swing.BoxLayout;
    import javax.swing.ButtonGroup;
    import javax.swing.JButton;
    import javax.swing.JPanel;
    import javax.swing.JRadioButton;
    
    public class ScitificFunctionPanel extends JPanel {
    
        public ScitificFunctionPanel() {
            // 设置窗体layout
            setLayout(new GridBagLayout());
    
            // 用于放置“度”、“弧度”、“梯度”这三个按钮
            JPanel angelPanel = new JPanel();
            BoxLayout boxLayout = new BoxLayout(angelPanel, BoxLayout.X_AXIS);
            angelPanel.setLayout(boxLayout);
            angelPanel.setBorder(BorderFactory.createEtchedBorder());
            JRadioButton angelButton = new JRadioButton("度");
            JRadioButton radianButton = new JRadioButton("弧度");
            JRadioButton gradientButton = new JRadioButton("梯度");
    
            ButtonGroup buttonGroup = new ButtonGroup();
            buttonGroup.add(angelButton);
            buttonGroup.add(radianButton);
            buttonGroup.add(gradientButton);
    
            angelPanel.add(angelButton);
            angelPanel.add(Box.createHorizontalGlue());
            angelPanel.add(radianButton);
            angelPanel.add(Box.createHorizontalGlue());
            angelPanel.add(gradientButton);
    
            // 添加角度面板
            add(angelPanel, new GBC(0, 0, 5, 1).setFill(GridBagConstraints.BOTH)
                    .setInsets(5).setWeight(100, 100));
    
            // 添加按钮
            String[][] btnStrings = { { "", "Inv", "In", "(", ")" },
                    { "Int", "sinh", "sin", "x^2", "n!" },
                    { "dms", "cosh", "cos", "x^y", "y√x" },
                    { "π", "tanh", "tan", "x^3", "3√x" },
                    { "F-E", "Exp", "Mod", "log", "10^x" } };
    
            for (int i = 0; i < btnStrings.length; i++) {
                for (int j = 0; j < btnStrings[0].length; j++) {
                    JButton button = new JButton(btnStrings[i][j]);
                    add(button,
                            new GBC(j, i + 1, 1, 1)
                                    .setFill(GridBagConstraints.BOTH).setInsets(5)
                                    .setWeight(100, 100));
                    if (i + j == 0)
                        button.setEnabled(false);
                }
            }
    
        }
    
        public static void main(String[] args) {
            // TODO Auto-generated method stub
            
        }
    
    }

    BinaryPanel.java

    import java.awt.FlowLayout;
    import java.awt.GridBagConstraints;
    import java.awt.GridBagLayout;
    import java.util.ArrayList;
    import java.util.List;
    import javax.swing.BorderFactory;
    import javax.swing.JButton;
    import javax.swing.JFrame;
    import javax.swing.JLabel;
    import javax.swing.JPanel;
    
    
    public class BinaryPanel extends JPanel{
    
        List<JPanel> bitPanelList = new ArrayList<JPanel>();
        
        public BinaryPanel(){
            setLayout(new GridBagLayout());
            setBorder(BorderFactory.createEtchedBorder());
            for (int i = 0; i < 4; i++) {
                for (int j = 0; j < 8; j++) {
                    if (i == 0 || i == 2) {
                        // 建立一个面板并设置为左对齐的flowLayout,它容纳4个label
                        JPanel bitPanel = new JPanel();
                        FlowLayout flowLayout = new FlowLayout();
                        flowLayout.setAlignment(FlowLayout.LEFT);
                        flowLayout.setHgap(0);
                        bitPanel.setLayout(flowLayout);
                        bitPanel.setName(String.valueOf(bitPanelList.size()));
                        bitPanelList.add(bitPanel);
                        // 添加4个label
                        for (int k = 0; k < 4; k++) {
                            JLabel label = createBitLabel();
                            String buttonName = String.valueOf(k);
                            label.setName(buttonName);
                            //label.setText(buttonName);
                            bitPanel.add(label);
                            System.out.println("add createBitButton of "
                                    + buttonName);
    
                        }
                        // 将包含4个button的小面板作为一个单元格添加到binaryPanel
                        add(bitPanel,
                                new GBC(j, i).setFill(GridBagConstraints.BOTH)
                                        .setWeight(100, 100).setInsets(5));
                    } else if (i == 1) {
                        String[] texts = { "63", null, null, null, "47", null,
                                null, "     32" };
                        for (int k = 0; k < texts.length; k++) {
                            JLabel indexLabel = new JLabel();
                            if (texts[k] == null)
                                continue;
                            indexLabel.setText(texts[k]);
                            add(indexLabel,    new GBC(k, i).setFill(GridBagConstraints.BOTH)
                                            .setWeight(100, 100).setInsets(5));
                        }
    
                    } else if (i == 3) {
                        String[] texts = { "31", null, null, null, "15", null,
                                null, "       0" };
                        for (int k = 0; k < texts.length; k++) {
                            JLabel indexLabel = new JLabel();
                            if (texts[k] == null)
                                continue;
                            indexLabel.setText(texts[k]);
                            add(indexLabel,
                                    new GBC(k, i).setFill(GridBagConstraints.BOTH)
                                            .setWeight(100, 100).setInsets(5));
                        }
                    }
                }
            }
        }
        
    
        private JButton createBitButton() {
            JButton bitButton = new JButton();
            bitButton.setText("0");
            bitButton.setEnabled(false);
            return bitButton;
        }
    
        private JLabel createBitLabel() {
            JLabel bitLabel = new JLabel();
            bitLabel.setText("0");
    
            // bitLabel.setEnabled(false);
            return bitLabel;
        }
        
        public static void main(String[] args) {
            // TODO Auto-generated method stub
            JFrame frame = new JFrame();
            frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
            frame.add(new BinaryPanel());
            frame.pack();
            frame.setVisible(true);
        }
    
    }

    ProgramFunctionPanel.java

    import java.awt.GridBagConstraints;
    import java.awt.GridBagLayout;
    
    import javax.swing.BorderFactory;
    import javax.swing.BoxLayout;
    import javax.swing.ButtonGroup;
    import javax.swing.JButton;
    import javax.swing.JFrame;
    import javax.swing.JPanel;
    import javax.swing.JRadioButton;
    
    
    public class ProgramFunctionPanel extends JPanel{
    
        public ProgramFunctionPanel(){
            // 设置窗体layout
            setLayout(new GridBagLayout());
            add(createRadixPanel(), new GBC(0,0, 1, 3).setWeight(100, 100).setFill(GridBagConstraints.BOTH));        
            add(createBytePanel(), new GBC(0,3, 1, 3).setWeight(100, 100).setFill(GridBagConstraints.BOTH));
            
            String textString [][] = {
                    {null, "", "Mod","A"}, 
                    {null, "(", ")","B"},
                    {null, "RoL", "RoR","C"},
                    {null, "Or", "Xor","D"},
                    {null, "Lsh", "Rsh","E"},
                    {null, "Not", "And","F"},};
            
            for (int i = 0; i< textString.length; i++) {
                for (int j = 0; j< textString[i].length; j++) {
                    String text = textString[i][j];
                    if(text != null){
                        JButton button = new JButton(text);
                        if(text.equals(""))
                            button.setEnabled(false);
                        add(button, new GBC(j, i).setWeight(100, 100).setFill(GridBagConstraints.BOTH).setInsets(5));
                        //System.out.printf("add btn at (%d,%d)
    ", j,i);
                    }
                }
            }
        }
        
        private JPanel createRadixPanel()
        {
            JPanel radixPanel = new JPanel();
            
            BoxLayout boxLayout=new BoxLayout(radixPanel, BoxLayout.Y_AXIS); 
            radixPanel.setLayout(boxLayout);
            radixPanel.setBorder(BorderFactory.createEtchedBorder());
            String [] radixStrings = {"十六进制", "十进制","八进制","二进制"};    
            ButtonGroup btnGroup = new ButtonGroup();
            for (String radixString : radixStrings) {
                JRadioButton radioButton = new JRadioButton(radixString);
                //注册事件
                btnGroup.add(radioButton);
                radixPanel.add(radioButton);            
            }
            return radixPanel;
        }
        
        private JPanel createBytePanel()
        {
            JPanel bytePanel = new JPanel();
            BoxLayout boxLayout=new BoxLayout(bytePanel, BoxLayout.Y_AXIS); 
            bytePanel.setLayout(boxLayout);
            bytePanel.setBorder(BorderFactory.createEtchedBorder());
            String [] byteStrings = {"四字", "双字","字","字节"};    
            ButtonGroup btnGroup = new ButtonGroup();
            for (String byteString : byteStrings) {
                JRadioButton radioButton = new JRadioButton(byteString);
                //注册事件
                btnGroup.add(radioButton);
                bytePanel.add(radioButton);            
            }
            return bytePanel;
        }
        
        public static void main(String[] args) {
            // TODO Auto-generated method stub
            JFrame frame = new JFrame();
            frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
            frame.add(new ProgramFunctionPanel());
            frame.pack();
            frame.setVisible(true);
        }
    
    }
    GBC.java
    import java.awt.GridBagConstraints;
    import java.awt.GridBagLayout;
    import java.awt.Insets;
    
    /*
     * GBC.java,source code from java核心技术 卷1 基础知识,P381
     */
    
    public class GBC extends GridBagConstraints{
    /*
     * constructs a GBC with a given gridx and gridy position and all other grid
     * bag constraint values set to the default
     * @param gridx the gridx position
     * @param gridy the gridy position
     */
        public GBC(int gridx, int gridy){
            this.gridx = gridx;
            this.gridy = gridy;
        }
        
        public GBC(int gridx, int gridy, int gridWidth, int gridHeight){
            this.gridx = gridx;
            this.gridy = gridy;
            this.gridwidth = gridWidth;
            this.gridheight = gridHeight;
        }
        
        /*
         * sets the anchor
         * @param anchor the anchor style
         * @return this object for further modification
         */
        
        public GBC setAnchor(int anchor){
            this.anchor = anchor;
            return this;
        }
        
        /*
         * sets the fill direction
         * @param fill the fill direction
         * @return this object for further modification
         */
        
        public GBC setFill(int fill){
            this.fill = fill;
            return this;
        }
        
        /*
         * sets the cell weights
         * @param weightx the cell weight in x direction
         * @param weighty the cell weight in y direction
         * @return this object for further modification
         */
        
        public GBC setWeight(int weightx, int weighty){
            this.weightx = weightx;
            this.weighty = weighty;
            return this;
        }
        
        /*
         * sets the insets of this cell
         * @param insets distance ths spacing to use in all directions
         * @return this object for further modification
         */
        
        public GBC setInsets(int distance){
            this.insets = new Insets(distance, distance, distance, distance);
            return this;
        }
        
        /*
         * sets the insets of this cell
         * @param top distance ths spacing to use on top
         * @param bottom distance ths spacing to use on bottom
         * @param left distance ths spacing to use to the left
         * @param right distance ths spacing to use to the  right
         * @return this object for further modification
         */
        
        public GBC setInsets(int top, int left,int bottom,int right){
            this.insets = new Insets(top, left, bottom, right);
            return this;
        }
        
        /*
         * sets the Ipad of this cell
         * @param Ipad distance ths spacing to use in all directions
         * @return this object for further modification
         */
        
        public GBC setIpad(int ipadx, int ipady){
            this.ipadx = ipadx;
            this.ipadx = ipadx;
            return this;
        }
    }
  • 相关阅读:
    Qt生成随机数
    Qt调用系统DLL,判断网络连接状态
    Qt操作sqlite数据库
    Qt 操作注册表
    vs报错:RC1004 unexpected end of file found
    Qt操作ini文件
    Django Admin:自动选择当前用户
    BSTR转QString
    vue-cli4,vue3打包后页面无内容
    Qt 5.12.10 国际化
  • 原文地址:https://www.cnblogs.com/pzy4447/p/4625355.html
Copyright © 2020-2023  润新知