Java学习者论坛

 找回密码
 立即注册

QQ登录

只需一步,快速开始

手机号码,快捷登录

恭喜Java学习者论坛(https://www.javaxxz.com)已经为数万Java学习者服务超过8年了!积累会员资料超过10000G+
成为本站VIP会员,下载本站10000G+会员资源,购买链接:点击进入购买VIP会员
JAVA高级面试进阶视频教程Java架构师系统进阶VIP课程

分布式高可用全栈开发微服务教程

Go语言视频零基础入门到精通

Java架构师3期(课件+源码)

Java开发全终端实战租房项目视频教程

SpringBoot2.X入门到高级使用教程

大数据培训第六期全套视频教程

深度学习(CNN RNN GAN)算法原理

Java亿级流量电商系统视频教程

互联网架构师视频教程

年薪50万Spark2.0从入门到精通

年薪50万!人工智能学习路线教程

年薪50万!大数据从入门到精通学习路线年薪50万!机器学习入门到精通视频教程
仿小米商城类app和小程序视频教程深度学习数据分析基础到实战最新黑马javaEE2.1就业课程从 0到JVM实战高手教程 MySQL入门到精通教程
查看: 520|回复: 0

[Swing学习]JAVA山寨windows的命令窗口

[复制链接]
  • TA的每日心情
    开心
    2021-3-12 23:18
  • 签到天数: 2 天

    [LV.1]初来乍到

    发表于 2014-11-17 23:57:47 | 显示全部楼层 |阅读模式
    java山寨windows的命令窗口:
    1. import java.awt.BorderLayout;  
    2. import java.awt.Color;  
    3. import java.awt.event.ActionEvent;  
    4. import java.awt.event.ActionListener;  
    5. import java.awt.event.WindowAdapter;  
    6. import java.awt.event.WindowEvent;  
    7. import java.beans.PropertyChangeEvent;  
    8. import java.beans.PropertyChangeListener;  
    9. import java.io.IOException;  
    10. import java.io.InputStream;  
    11. import java.io.PrintWriter;  
    12. import java.util.List;  
    13.   
    14. import javax.swing.JFrame;  
    15. import javax.swing.SwingUtilities;  
    16. import javax.swing.SwingWorker;  
    17.   
    18. public class ConsoleGUI extends JFrame {  
    19.   
    20.     private static final long serialVersionUID = 1L;  
    21.   
    22.     private CMDPane messagePane;  
    23.   
    24.     private Process process;  
    25.     private PrintWriter outStream;  
    26.     private InputStream inputStream;  
    27.     private InputStream errorStream;  
    28.     private InputWorker inputWorker = new InputWorker();  
    29.     private ErrorWorker errorWorker = new ErrorWorker();  
    30.   
    31.     public ConsoleGUI() {  
    32.         setSize(500, 500);  
    33.         setDefaultCloseOperation(DISPOSE_ON_CLOSE);  
    34.         setTitle("命令行GUI");  
    35.   
    36.         messagePane = new CMDPane();  
    37.         messagePane.setForeground(Color.WHITE);  
    38.         messagePane.setBackground(Color.BLACK);  
    39.         add(messagePane, BorderLayout.CENTER);  
    40.   
    41.         // 启动一个CMD   
    42.         try {  
    43.             this.process = Runtime.getRuntime().exec("cmd");  
    44.             inputStream = process.getInputStream();  
    45.             errorStream = process.getErrorStream();  
    46.             errorWorker.execute();  
    47.             inputWorker.execute();  
    48.             this.outStream = new PrintWriter(process.getOutputStream());  
    49.         } catch (IOException e) {  
    50.             e.printStackTrace();  
    51.         }  
    52.   
    53.         // 命令框中按下回车键的事件   
    54.         messagePane.addActionListener(new ActionListener() {  
    55.   
    56.             @Override  
    57.             public void actionPerformed(ActionEvent e) {  
    58.                 String cmd = messagePane.getCmd();  
    59.                 if (cmd == null || "".equals(cmd)) {  
    60.                     return;  
    61.                 } else if ("cls".equals(cmd)) {  
    62.                     messagePane.clearDate();  
    63.                     messagePane.cleanCmd();  
    64.                     return;  
    65.                 } else if ("exit".equals(cmd)) {  
    66.                     dispose();  
    67.                     return;  
    68.                 }  
    69.                 messagePane.addData(messagePane.getCmdTip() + cmd);  
    70.                 outStream.println(cmd);  
    71.                 outStream.flush();  
    72.                 messagePane.cleanCmd();  
    73.             }  
    74.         });  
    75.         addWindowListener(new WindowAdapter() {  
    76.             @Override  
    77.             public void windowClosed(WindowEvent e) {  
    78.                 try {  
    79.                     outStream.close();  
    80.                     inputStream.close();  
    81.                     errorStream.close();  
    82.                     process.destroy();  
    83.                 } catch (IOException e1) {  
    84.                     e1.printStackTrace();  
    85.                 }  
    86.             }  
    87.         });  
    88.         this.setLocationRelativeTo(null);  
    89.         this.setVisible(true);  
    90.         messagePane.cleanCmd();  
    91.     }  
    92.   
    93.     public static void main(String[] args) {  
    94.         System.setProperty("swing.defaultlaf",  
    95.                 "com.sun.java.swing.plaf.nimbus.NimbusLookAndFeel");  
    96.         SwingUtilities.invokeLater(new Runnable() {  
    97.   
    98.             @Override  
    99.             public void run() {  
    100.                 new ConsoleGUI();  
    101.             }  
    102.         });  
    103.     }  
    104.   
    105.     class ErrorWorker extends SwingWorker< String, String> {  
    106.   
    107.         @Override  
    108.         protected void process(List< String> chunks) {  
    109.             for (String string : chunks) {  
    110.                 messagePane.addData(string);  
    111.             }  
    112.         }  
    113.   
    114.         @Override  
    115.         protected String doInBackground() throws Exception {  
    116.             byte[] buf = new byte[1024];  
    117.             int size;  
    118.             while (true) {  
    119.                 if ((size = errorStream.read(buf)) != -1) {  
    120.                     String org = new String(buf, 0, size, "gbk");  
    121.                     String[] lines = org.split("\n");  
    122.                     if (lines != null) {  
    123.                         for (int i = 0; i < lines.length; i++) {  
    124.                             publish(lines[i]);  
    125.                         }  
    126.                     }  
    127.                 }  
    128.             }  
    129.         }  
    130.   
    131.     }  
    132.   
    133.     class InputWorker extends SwingWorker< String, String> {  
    134.   
    135.         public InputWorker() {  
    136.             addPropertyChangeListener(new PropertyChangeListener() {  
    137.   
    138.                 @Override  
    139.                 public void propertyChange(PropertyChangeEvent evt) {  
    140.                     if ("cmd".equals(evt.getPropertyName())) {  
    141.                         messagePane.setCmdTip(evt.getNewValue());  
    142.                     }  
    143.                 }  
    144.             });  
    145.         }  
    146.   
    147.         @Override  
    148.         protected void process(List< String> chunks) {  
    149.             for (String string : chunks) {  
    150.                 messagePane.addData(string);  
    151.             }  
    152.         }  
    153.   
    154.         @Override  
    155.         protected String doInBackground() throws Exception {  
    156.             byte[] buf = new byte[1024];  
    157.             int size;  
    158.             while (true) {  
    159.                 if ((size = inputStream.read(buf)) != -1) {  
    160.                     String org = new String(buf, 0, size, "gbk");  
    161.                     String[] lines = org.split("\n");  
    162.                     if (lines != null && lines.length > 0) {  
    163.                         for (int i = 0; i < lines.length - 1; i++) {  
    164.                             //给予一定的延时,保证正常信息在错误信息之后显示   
    165.                             Thread.sleep(10);  
    166.                             publish(lines[i]);  
    167.                         }  
    168.                         firePropertyChange("cmd", null,  
    169.                                 lines[lines.length - 1]);  
    170.                     }  
    171.                 }  
    172.             }  
    173.         }  
    174.   
    175.     }  
    176. }  
    177. import java.awt.Color;  
    178. import java.awt.Font;  
    179. import java.awt.Graphics;  
    180. import java.awt.GridBagConstraints;  
    181. import java.awt.GridBagLayout;  
    182. import java.awt.Insets;  
    183. import java.awt.Rectangle;  
    184. import java.awt.event.ActionListener;  
    185. import java.awt.event.AdjustmentEvent;  
    186. import java.awt.event.AdjustmentListener;  
    187. import java.awt.event.ComponentAdapter;  
    188. import java.awt.event.ComponentEvent;  
    189. import java.util.LinkedList;  
    190.   
    191. import javax.swing.BorderFactory;  
    192. import javax.swing.JComponent;  
    193. import javax.swing.JScrollBar;  
    194. import javax.swing.JTextField;  
    195. import javax.swing.SwingUtilities;  
    196. import javax.swing.UIManager;  
    197.   
    198. public class CMDPane extends JComponent {  
    199.   
    200.     /**
    201.      * 允许最大数据行数
    202.      */  
    203.     private static final int MAXLINE = 10000;  
    204.     /**
    205.      * 数据队列
    206.      */  
    207.     private LinkedList< String> datas = new LinkedList< String>();  
    208.     /**
    209.      * 每行数据的绘制高度
    210.      */  
    211.     private int lineH = 1;  
    212.     /**
    213.      * 滚动条
    214.      */  
    215.     private JScrollBar bar = new JScrollBar(JScrollBar.VERTICAL);  
    216.     /**
    217.      * 输入栏
    218.      */  
    219.     private JTextField field = new JTextField();  
    220.     /**
    221.      * 命令提示栏
    222.      */  
    223.     private JTextField label = new JTextField(">");  
    224.     /**
    225.      * 滚动条当前值
    226.      */  
    227.     private int barValue = 0;  
    228.     /**
    229.      * 滚动条更新任务
    230.      */  
    231.     private Runnable barRunnable = new Runnable() {  
    232.   
    233.         @Override  
    234.         public void run() {  
    235.             bar.setValues(barValue, getHeight() / lineH, 0, datas.size() + 1);  
    236.         }  
    237.     };  
    238.   
    239.     /**
    240.      * 构造一个新的 MessagePane
    241.      */  
    242.     public CMDPane() {  
    243.         initialize();  
    244.     }  
    245.   
    246.     /**
    247.      * 初始化
    248.      */  
    249.     private void initialize() {  
    250.         setOpaque(true);  
    251.         setLayout(new GridBagLayout());  
    252.         label.setOpaque(true);  
    253.         field.setOpaque(true);  
    254.         GridBagConstraints c = new GridBagConstraints();  
    255.         c.gridx = 2;  
    256.         c.gridy = 0;  
    257.         c.gridheight = 2;  
    258.         c.weighty = 1;  
    259.         c.fill = GridBagConstraints.VERTICAL;  
    260.         add(bar, c);  
    261.         c.gridx = 0;  
    262.         c.gridy = 1;  
    263.         c.gridheight = 1;  
    264.         c.weighty = 0;  
    265.         c.fill = GridBagConstraints.HORIZONTAL;  
    266.         c.anchor = GridBagConstraints.SOUTH;  
    267.         add(label, c);  
    268.         c.weightx = 1;  
    269.         c.gridx = 1;  
    270.         c.gridy = 1;  
    271.         c.insets = new Insets(0, 0, 0, 0);  
    272.         add(field, c);  
    273.         field.setBorder(BorderFactory.createEmptyBorder(1, 1, 1, 1));  
    274.         label.setBorder(BorderFactory.createEmptyBorder(1, 1, 1, 0));  
    275.         label.setEditable(false);  
    276.         bar.addAdjustmentListener(new AdjustmentListener() {  
    277.   
    278.             @Override  
    279.             public void adjustmentValueChanged(AdjustmentEvent e) {  
    280.                 int newValue = bar.getValue();  
    281.                 if (newValue != barValue) {  
    282.                     barValue = newValue;  
    283.                     repaint();  
    284.                 }  
    285.             }  
    286.         });  
    287.         addComponentListener(new ComponentAdapter() {  
    288.   
    289.             @Override  
    290.             public void componentResized(ComponentEvent e) {  
    291.                 //控件大小变化时,更新滚动条   
    292.                 updateBar();  
    293.             }  
    294.         });  
    295.         setFont(UIManager.getFont("Panel.font"));  
    296.         lineH = getFontMetrics(getFont()).getHeight() + 2;  
    297.         updateBar();  
    298.     }  
    299.   
    300.     @Override  
    301.     public void setBackground(Color bg) {  
    302.         label.setBackground(bg);  
    303.         field.setBackground(bg);  
    304.         super.setBackground(bg);  
    305.     }  
    306.   
    307.     @Override  
    308.     public void setForeground(Color fg) {  
    309.         label.setForeground(fg);  
    310.         field.setForeground(fg);  
    311.         super.setForeground(fg);  
    312.     }  
    313.   
    314.     @Override  
    315.     public void setFont(Font font) {  
    316.         label.setFont(font);  
    317.         field.setFont(font);  
    318.         super.setFont(font);  
    319.         if (font != null) {  
    320.             lineH = getFontMetrics(font).getHeight() + 2;  
    321.         }  
    322.     }  
    323.   
    324.     /**
    325.      * 根据当前数据量,更新滚动条属性
    326.      */  
    327.     private void updateBar() {  
    328.         if (SwingUtilities.isEventDispatchThread()) {  
    329.             barRunnable.run();  
    330.         } else {  
    331.             SwingUtilities.invokeLater(barRunnable);  
    332.         }  
    333.     }  
    334.   
    335.     /**
    336.      * 标准的添加数据接口,在事件指派线程中调用该方法,可以获得最大的性能优化
    337.      *  
    338.      * @param data - 数据
    339.      */  
    340.     public synchronized void addData(String data) {  
    341.         datas.addLast(data);  
    342.         if (datas.size() > MAXLINE) {  
    343.             //数据超出限定范围时,移除最旧的一条数据   
    344.             datas.pollFirst();  
    345.         } else {  
    346.             //数据长度变化时,更新滚动条   
    347.             updateBar();  
    348.         }  
    349.         bar.setValue(datas.size());  
    350.         repaint();  
    351.     }  
    352.   
    353.     /**
    354.      * 标准的清除数据接口
    355.      */  
    356.     public synchronized void clearDate() {  
    357.         datas.clear();  
    358.         //清除数据后,滚动条值归零   
    359.         barValue = 0;  
    360.         repaint();  
    361.         //清除数据后,更新滚动条   
    362.         updateBar();  
    363.     }  
    364.       
    365.     /**
    366.      * 设置命题输入栏的提示
    367.      * @param text
    368.      */  
    369.     public void setCmdTip(Object text) {  
    370.         label.setText(text.toString());  
    371.         revalidate();  
    372.     }  
    373.       
    374.     /**
    375.      * 返回命题输入栏的提示
    376.      */  
    377.     public String getCmdTip() {  
    378.         return label.getText();  
    379.     }  
    380.       
    381.     /**
    382.      * 获得命令
    383.      * @return
    384.      */  
    385.     public String getCmd() {  
    386.         return field.getText();  
    387.     }  
    388.       
    389.     /**
    390.      * 清除命令
    391.      */  
    392.     public void cleanCmd() {  
    393.         field.setText("");  
    394.         field.requestFocusInWindow();  
    395.     }  
    396.       
    397.     /**
    398.      * 设置命令相应事件
    399.      * @param listener
    400.      */  
    401.     public void addActionListener(ActionListener listener) {  
    402.         field.addActionListener(listener);  
    403.     }  
    404.   
    405.     /**
    406.      * 获得真实的绘制宽度(减去滚动条宽度)
    407.      *  
    408.      * @return
    409.      */  
    410.     private int getPaintWidth() {  
    411.         return getWidth() - bar.getWidth();  
    412.     }  
    413.       
    414.     /**
    415.      * 获得真实的绘制高度(减去输入框高度)
    416.      *  
    417.      * @return
    418.      */  
    419.     private int getPaintHeight() {  
    420.         return getHeight() - field.getHeight();  
    421.     }  
    422.   
    423.     @Override  
    424.     protected void paintComponent(Graphics g) {  
    425.         int w = getPaintWidth();  
    426.         int h = getPaintHeight();  
    427.         Rectangle clip = g.getClipBounds();  
    428.         int clipX = clip.x;  
    429.         int clipY = clip.y;  
    430.         int clipH = clip.height;  
    431.         int y = 0;  
    432.         g.setColor(getBackground());  
    433.         g.fillRect(clipX, clipY, w, clipH);  
    434.         g.setColor(getForeground());  
    435.         for (int i = barValue; i < datas.size(); i++) {  
    436.             y += lineH;  
    437.             if (y > clipY + h) {  
    438.                 //由于是从上往下绘制,因此大于绘制区域下沿时,终止绘制   
    439.                 break;  
    440.             }  
    441.             g.drawString(datas.get(i).toString(), 0, y);  
    442.         }  
    443.     }  
    444.   
    445. }  
    复制代码

       
         
         
          
          

            
          

            
          
         
       

      


    源码下载:http://file.javaxxz.com/2014/11/17/235746859.zip
    回复

    使用道具 举报

    您需要登录后才可以回帖 登录 | 立即注册

    本版积分规则

    QQ|手机版|Java学习者论坛 ( 声明:本站资料整理自互联网,用于Java学习者交流学习使用,对资料版权不负任何法律责任,若有侵权请及时联系客服屏蔽删除 )

    GMT+8, 2025-2-25 07:38 , Processed in 0.305898 second(s), 34 queries .

    Powered by Discuz! X3.4

    © 2001-2017 Comsenz Inc.

    快速回复 返回顶部 返回列表