3030
3131package org .scijava .ui .swing .console ;
3232
33- import java .awt .BorderLayout ;
34- import java .awt .Color ;
3533import java .awt .Component ;
36- import java .awt .Dimension ;
37- import java .awt .Font ;
38- import java .awt .FontMetrics ;
3934
4035import javax .swing .JPanel ;
41- import javax .swing .JScrollPane ;
4236import javax .swing .JTextPane ;
43- import javax .swing .text .BadLocationException ;
44- import javax .swing .text .Style ;
45- import javax .swing .text .StyleConstants ;
46- import javax .swing .text .StyledDocument ;
4737
4838import net .miginfocom .swing .MigLayout ;
4939
5040import org .scijava .Context ;
5141import org .scijava .console .OutputEvent ;
52- import org .scijava .console .OutputEvent .Source ;
5342import org .scijava .plugin .Parameter ;
5443import org .scijava .thread .ThreadService ;
5544import org .scijava .ui .console .AbstractConsolePane ;
5645import org .scijava .ui .console .ConsolePane ;
57- import org .scijava .ui .swing .StaticSwingUtils ;
5846
5947/**
6048 * Swing implementation of {@link ConsolePane}.
@@ -66,22 +54,16 @@ public class SwingConsolePane extends AbstractConsolePane<JPanel> {
6654 @ Parameter
6755 private ThreadService threadService ;
6856
69- private JPanel consolePanel ;
70- private JTextPane textPane ;
71- private JScrollPane scrollPane ;
72-
73- private StyledDocument doc ;
74- private Style stdoutLocal ;
75- private Style stderrLocal ;
76- private Style stdoutGlobal ;
77- private Style stderrGlobal ;
57+ private ConsolePanel consolePanel ;
7858
7959 /**
8060 * The console pane's containing window; e.g., a {@link javax.swing.JFrame} or
8161 * {@link javax.swing.JInternalFrame}.
8262 */
8363 private Component window ;
8464
65+ private JPanel component ;
66+
8567 public SwingConsolePane (final Context context ) {
8668 super (context );
8769 }
@@ -93,41 +75,15 @@ public void setWindow(final Component window) {
9375 this .window = window ;
9476 }
9577
96- public JTextPane getTextPane () {
97- if (consolePanel == null ) initConsolePanel ();
98- return textPane ;
99- }
100-
101- public JScrollPane getScrollPane () {
102- if (consolePanel == null ) initConsolePanel ();
103- return scrollPane ;
104- }
105-
10678 public void clear () {
107- if (consolePanel == null ) initConsolePanel ();
108- textPane .setText ("" );
79+ consolePanel ().clear ();
10980 }
11081
11182 // -- ConsolePane methods --
11283
11384 @ Override
11485 public void append (final OutputEvent event ) {
115- if (consolePanel == null ) initConsolePanel ();
116- threadService .queue (new Runnable () {
117-
118- @ Override
119- public void run () {
120- final boolean atBottom =
121- StaticSwingUtils .isScrolledToBottom (scrollPane );
122- try {
123- doc .insertString (doc .getLength (), event .getOutput (), getStyle (event ));
124- }
125- catch (final BadLocationException exc ) {
126- throw new RuntimeException (exc );
127- }
128- if (atBottom ) StaticSwingUtils .scrollToBottom (scrollPane );
129- }
130- });
86+ consolePanel ().outputOccurred (event );
13187 }
13288
13389 @ Override
@@ -146,8 +102,8 @@ public void run() {
146102
147103 @ Override
148104 public JPanel getComponent () {
149- if (consolePanel == null ) initConsolePanel ();
150- return consolePanel ;
105+ if (consolePanel == null ) initLoggingPanel ();
106+ return component ;
151107 }
152108
153109 @ Override
@@ -157,64 +113,21 @@ public Class<JPanel> getComponentType() {
157113
158114 // -- Helper methods - lazy initialization --
159115
160- private synchronized void initConsolePanel () {
161- if (consolePanel != null ) return ;
162-
163- final JPanel panel = new JPanel ();
164- panel .setLayout (new MigLayout ("" , "[grow,fill]" , "[grow,fill,align top]" ));
165-
166- textPane = new JTextPane ();
167- textPane .setFont (new Font (Font .MONOSPACED , Font .PLAIN , 12 ));
168- textPane .setEditable (false );
169-
170- doc = textPane .getStyledDocument ();
171-
172- stdoutLocal = createStyle ("stdoutLocal" , null , Color .black , null , null );
173- stderrLocal = createStyle ("stderrLocal" , null , Color .red , null , null );
174- stdoutGlobal = createStyle ("stdoutGlobal" , stdoutLocal , null , null , true );
175- stderrGlobal = createStyle ("stderrGlobal" , stderrLocal , null , null , true );
176-
177- // NB: We wrap the JTextPane in a JPanel to disable
178- // the text pane's intelligent line wrapping behavior.
179- // I.e.: we want console lines _not_ to wrap, but instead
180- // for the scroll pane to show a horizontal scroll bar.
181- // Thanks to: https://tips4java.wordpress.com/2009/01/25/no-wrap-text-pane/
182- final JPanel textPanel = new JPanel ();
183- textPanel .setLayout (new BorderLayout ());
184- textPanel .add (textPane );
185-
186- scrollPane = new JScrollPane (textPanel );
187- scrollPane .setPreferredSize (new Dimension (600 , 600 ));
188-
189- // Make the scroll bars move at a reasonable pace.
190- final FontMetrics fm = scrollPane .getFontMetrics (scrollPane .getFont ());
191- final int charWidth = fm .charWidth ('a' );
192- final int lineHeight = fm .getHeight ();
193- scrollPane .getHorizontalScrollBar ().setUnitIncrement (charWidth );
194- scrollPane .getVerticalScrollBar ().setUnitIncrement (2 * lineHeight );
195-
196- panel .add (scrollPane );
197-
198- consolePanel = panel ;
116+ private ConsolePanel consolePanel () {
117+ if (consolePanel == null ) initLoggingPanel ();
118+ return consolePanel ;
199119 }
200120
201- // -- Helper methods --
202-
203- private Style createStyle (final String name , final Style parent ,
204- final Color foreground , final Boolean bold , final Boolean italic )
205- {
206- final Style style = textPane .addStyle (name , parent );
207- if (foreground != null ) StyleConstants .setForeground (style , foreground );
208- if (bold != null ) StyleConstants .setBold (style , bold );
209- if (italic != null ) StyleConstants .setItalic (style , italic );
210- return style ;
121+ private synchronized void initLoggingPanel () {
122+ if (consolePanel != null ) return ;
123+ consolePanel = new ConsolePanel (threadService );
124+ component = new JPanel (new MigLayout ("" , "[grow]" , "[grow]" ));
125+ component .add (consolePanel , "grow" );
211126 }
212127
213- private Style getStyle (final OutputEvent event ) {
214- final boolean stderr = event .getSource () == Source .STDERR ;
215- final boolean contextual = event .isContextual ();
216- if (stderr ) return contextual ? stderrLocal : stderrGlobal ;
217- return contextual ? stdoutLocal : stdoutGlobal ;
218- }
128+ // -- Helper methods - testing --
219129
130+ JTextPane getTextPane () {
131+ return consolePanel ().getTextPane ();
132+ }
220133}
0 commit comments