【问题标题】:how to visualize console java in JFrame/JPanel如何在 JFrame/JPanel 中可视化控制台 java
【发布时间】:2012-04-04 07:26:19
【问题描述】:

我使用 Swing 库制作了一个 Java 程序。 现在我想将我的控制台输出重定向到 JFrame 或 JPanel。

【问题讨论】:

  • 那么你的问题到底是什么?
  • 也许将所有内容附加到另一个 Swing 组件(例如 JTextArea)?

标签: java swing console jtextarea jtextcomponent


【解决方案1】:

我知道我迟到了,但是对于正在寻找更好、更紧凑的答案的人,我让这个女巫结合了两个自定义类。

控制台.java

public class Console {
    final JFrame frame = new JFrame("CONSOLE");
    ColorPane textPane;
    JScrollPane scroll;

    public Console() throws Exception {
        textPane = new ColorPane();
        textPane.setPreferredSize(new Dimension(525, 600));
        textPane.setFont(new Font("Lucida Console", Font.BOLD, 12));
        scroll = new JScrollPane(textPane);
        textPane.setBackground(Color.BLACK);

        scroll.setVerticalScrollBarPolicy ( ScrollPaneConstants.VERTICAL_SCROLLBAR_ALWAYS );

        textPane.getDocument().addDocumentListener(new DocumentListener() {
            @Override
            public void insertUpdate(DocumentEvent e) {
                scrollToBottom(scroll);
            }

            @Override
            public void removeUpdate(DocumentEvent e) {

            }

            @Override
            public void changedUpdate(DocumentEvent e) {

            }
        });

        //Add textPane in to middle panel
        frame.add(scroll);
        frame.setSize(100, 600);
        frame.pack();
        frame.setVisible(false);
        redirectOut();

    }

    public PrintStream redirectOut() {
        OutputStream out = new OutputStream() {
            @Override
            public void write(int b) throws IOException {
                textPane.append(Color.WHITE, String.valueOf((char) b));
            }
        };
        OutputStream errOut = new OutputStream() {
            @Override
            public void write(int b) throws IOException {
                textPane.append(Color.RED, String.valueOf((char) b));
            }
        };
        PrintStream ps = new PrintStream(out);
        PrintStream err = new PrintStream(errOut);

        System.setOut(ps);
        System.setErr(err);
        scrollToBottom(scroll);

        return ps;
    }

    public JFrame getFrame() {
        return frame;
    }

    private void scrollToBottom(JScrollPane scrollPane) {
        JScrollBar verticalBar = scrollPane.getVerticalScrollBar();
        AdjustmentListener downScroller = new AdjustmentListener() {
            @Override
            public void adjustmentValueChanged(AdjustmentEvent e) {
                Adjustable adjustable = e.getAdjustable();
                adjustable.setValue(adjustable.getMaximum());
                verticalBar.removeAdjustmentListener(this);
            }
        };
        verticalBar.addAdjustmentListener(downScroller);
    }
}

和 ColorPane.java

import java.awt.Color;

import javax.swing.JFrame;
import javax.swing.JScrollPane;
import javax.swing.JTextPane;
import javax.swing.text.AttributeSet;
import javax.swing.text.SimpleAttributeSet;
import javax.swing.text.StyleConstants;
import javax.swing.text.StyleContext;

public class ColorPane extends JTextPane {

    public void appendNaive(Color c, String s) { // naive implementation
        // bad: instiantiates a new AttributeSet object on each call
        SimpleAttributeSet aset = new SimpleAttributeSet();
        StyleConstants.setForeground(aset, c);

        int len = getText().length();
        setCaretPosition(len); // place caret at the end (with no selection)
        setCharacterAttributes(aset, false);
        replaceSelection(s); // there is no selection, so inserts at caret
    }

    public void append(Color c, String s) { // better implementation--uses
        // StyleContext
        StyleContext sc = StyleContext.getDefaultStyleContext();
        AttributeSet aset = sc.addAttribute(SimpleAttributeSet.EMPTY,
                StyleConstants.Foreground, c);

        int len = getDocument().getLength(); // same value as
        // getText().length();
        setCaretPosition(len); // place caret at the end (with no selection)
        setCharacterAttributes(aset, false);
        replaceSelection(s); // there is no selection, so inserts at caret
    }

    public static boolean isPrime(int n) {
        if (n < 2)
            return false;
        double max = Math.sqrt(n);
        for (int j = 2; j <= max; j += 1)
            if (n % j == 0)
                return false; // j is a factor
        return true;
    }

    public static boolean isPerfectSquare(int n) {
        int j = 1;
        while (j * j < n && j * j > 0)
            j += 1;
        return (j * j == n);
    }

}

这是我一直在使用的解决方案,它甚至有彩色输出。 PS:顺便说一句,对不起英语不好(我只有 11 岁)

【讨论】:

    【解决方案2】:

    您需要创建一个将输出重定向到文本区域并实现 OutputStream 接口的所有必要方法的 OutputStream,然后在您的主程序中,将您的标准输出重定向到此流。我在我的一个程序中使用了类似的东西:

    import java.io.IOException;
    import java.io.OutputStream;
    
    import javax.swing.JTextArea;
    import javax.swing.SwingUtilities;
    
    public class TextAreaOutputStream extends OutputStream {
    
       private final JTextArea textArea;
       private final StringBuilder sb = new StringBuilder();
       private String title;
    
       public TextAreaOutputStream(final JTextArea textArea, String title) {
          this.textArea = textArea;
          this.title = title;
          sb.append(title + "> ");
       }
    
       @Override
       public void flush() {
       }
    
       @Override
       public void close() {
       }
    
       @Override
       public void write(int b) throws IOException {
    
          if (b == '\r')
             return;
    
          if (b == '\n') {
             final String text = sb.toString() + "\n";
             SwingUtilities.invokeLater(new Runnable() {
                public void run() {
                   textArea.append(text);
                }
             });
             sb.setLength(0);
             sb.append(title + "> ");
             return;
          }
    
          sb.append((char) b);
       }
    }
    

    你可以用这个来演示它:

    import java.awt.BorderLayout;
    import java.awt.event.ActionEvent;
    import java.awt.event.ActionListener;
    import java.io.PrintStream;
    import javax.swing.*;
    
    @SuppressWarnings("serial")
    public class TextAreaOutputStreamTest extends JPanel {
    
       private JTextArea textArea = new JTextArea(15, 30);
       private TextAreaOutputStream taOutputStream = new TextAreaOutputStream(
             textArea, "Test");
    
       public TextAreaOutputStreamTest() {
          setLayout(new BorderLayout());
          add(new JScrollPane(textArea, JScrollPane.VERTICAL_SCROLLBAR_ALWAYS, 
                JScrollPane.HORIZONTAL_SCROLLBAR_NEVER));
          System.setOut(new PrintStream(taOutputStream));
    
          int timerDelay = 1000;
          new Timer(timerDelay , new ActionListener() {
             int count = 0;
             @Override
             public void actionPerformed(ActionEvent arg0) {
    
                // though this outputs via System.out.println, it actually displays
                // in the JTextArea:
                System.out.println("Count is now: " + count + " seconds");
                count++;
             }
          }).start();
       }
    
       private static void createAndShowGui() {
          JFrame frame = new JFrame("Test");
          frame.setDefaultCloseOperation(JFrame.EXIT_ON_CLOSE);
          frame.getContentPane().add(new TextAreaOutputStreamTest());
          frame.pack();
          frame.setLocationRelativeTo(null);
          frame.setVisible(true);
       }
    
       public static void main(String[] args) {
          SwingUtilities.invokeLater(new Runnable() {
             public void run() {
                createAndShowGui();
             }
          });
       }
    }
    

    【讨论】:

      【解决方案3】:

      获得JFrameJPanel 后,向其中添加一个文本字段。

      JTextArea 是一个不错的选择,因为它是多行。 添加后,您可以.append('text'); 给它,而不是写System.out.print();

      JFrame jFrame = new JFrame();
      
      JTextArea jTextArea = new JTextArea();
      jTextArea.append( "Hello World." );
      
      jFrame.add( jTextArea );
      

      【讨论】:

      • 好的,我读到了。我认为还有其他事情可以做到这一点。因为已经有 println 我不想添加新的 textarea 并附加它们
      猜你喜欢
      • 1970-01-01
      • 2010-11-01
      • 1970-01-01
      • 1970-01-01
      • 2020-09-02
      • 2011-07-18
      • 1970-01-01
      • 1970-01-01
      • 2012-10-24
      相关资源
      最近更新 更多