2011-12-17 3 views
2

현재 Log4J 로그를 JTextPane으로 만들려고합니다. 기본 강조 표시 (예 : 오류가 빨간색이고 정보가 녹색)를 원하기 때문에 TextPane을 사용하고 싶습니다.JTextPane의 log4j

두 개의 로거가 설정되어 있고 (루트 로그 작성기) 한 파일에 모든 파일이 기록되고 다른 파일 (guiLogger)은 GUI의 일부 오류 및 정보 만 JTextPane에 기록합니다.

현재 내가 직면하고있는 문제는 TextPane에 추가 기능을 추가 할 수 없다는 것입니다. 그렇지 않습니다합니다 (append() -method가 호출되는

# The root-logger should log everything. 
log4j.rootLogger = DEBUG, file 

# Append the logs to a file. 
log4j.appender.file = org.apache.log4j.RollingFileAppender 
# [...] 

# The logger which logs on the GUI (just some user-information). 
log4j.logger.guiLogger = INFO, gui 

# Append the logs to the GUI 
log4j.appender.gui = mypackage.Log 
# Formatting of the output: 
log4j.appender.gui.layout = org.apache.log4j.PatternLayout 
log4j.appender.gui.layout.ConversionPattern = %m%n 

하고 insertString() -method 깨끗 수행

public class Log extends AppenderSkeleton{ 

    private final JTextPane log; 
    private final StyledDocument doc; 

    public Log(){ 
     super(); 
     log = new JTextPane(); 
     doc = log.getStyledDocument(); 
    } 

    @Override 
    protected void append(LoggingEvent loggingEvent) { 
     try { 
      doc.insertString(doc.getLength(), "Hello World!", null); 
     } catch (BadLocationException e) { 
      e.printStackTrace(); 
     } 
    } 

    public JTextPane getView(){ 
     return log; 
    } 
} 

의 log4j 설정 파일은 다음과 같습니다 : 내가 현재 가지고하는 것은 다음과 같이 보입니다 catch -block을 입력하십시오.)하지만 GUI의 텍스트 패널에 내용이 표시되지 않습니다.

  • JTextPane
  • validate(), revalidate()repaint() 같은 SwingWorker
  • 방법에서 insertString() -method을 실행 SwingUtilities.invokeLater()
  • 사용하여 insertString() -method을 실행 :이 문제를 해결하기 위해 노력했다 무엇

  • 세계 StyledDocument - 개체를 사용하지 않고 직접 0에서 가져옵니다.-instance : log.getStyledDocument().insertString(0, "Hello World!", info_log);
  • setText()- 메서드 (생성자에서만 작동 함).

JTextPane에는 fireContentChanged()- 방법 (또는 이와 유사한)이 없기 때문에 여기에 분실되어 있습니다.


내가 더 조금 주위에 재생 및 다른 것들을 발견은 :

StyledDocument가 업데이트 될 때
  • (getText()를 호출은 텍스트가 삽입 된 것을 보여준다).
  • StyledDocumentJTextPane을 초기화 한 후 컴파일러에서 직접 append() 또는 insertString() -method를 호출하면 모두 정상적으로 작동합니다.

    System.out.println("Thread: "+Thread.currentThread().getName()); 
    

    그것은 단순히 어딘가에 코드에서 두 로그 진술을 할 경우, 다음을 보여줍니다

또한, 나는 append() -method 몸이를 추가하여 메소드를 호출하는 스레드 확인 :

Thread: AWT-EventQueue-0 
Thread: AWT-EventQueue-0 

및 I 호출시 append() 직접 Log - 클래스 (플러스 위에서 두 로깅 문)의 생성자에서, 다음이 도시 -method :

Thread: AWT-EventQueue-0 
Thread: AWT-EventQueue-0 
Thread: AWT-EventQueue-0 

첫 번째 호출은 아마 텍스트를 추가합니다. 그러나 다른 두 사람은 솔기가 작동하지 않습니다.

내 GUI는 을 사용하여 AWT-EventQueue에서 빌드됩니다. 두 개의 로깅 호출은 동일한 컨텍스트에서 이루어 지므로 EventQueue에서도 발생합니다.

+0

는 당신이'org.apache.log4j.lf5.LF5Appender'을 복제하지 않을 확신? –

+0

@이 글은 내 목적에 조금 "과부하가 걸린 것 같아." –

답변

2

텍스트 팬은 appender에게 비공개이며, 사용자는 이에 대한 게터가 없습니다. 따라서 GUI에는 텍스트 창이 있고 로그 작성기에 추가되는 다른 텍스트 창이 있다고 생각합니다.

Log4j가 인스턴스화하는 Log 인스턴스와 다른 Log 인스턴스에서 텍스트 창이 표시됩니다.

또한 appender는 여러 스레드에서 사용할 수 있지만 Swing 구성 요소는 이벤트 발송 스레드에서만 액세스 할 수 있습니다. 텍스트 창에 추가 할 때마다 SwingUtilities.invokeLater() 호출 내에서 수행해야합니다.

+0

'Log'-class에는 private'JTextPane'을 반환하는 getView() 메소드가 있습니다. 코드 스 니프에 추가했습니다. TextPane 자체에 추가하는 것이 아니기 때문에'StyledDocument'에 수정하지 않거나 잘못 되었습니까? –

+0

제 질문에 좀 더 많은 정보를 추가했습니다. 한번보세요. –

+0

정확하게 appender에서 텍스트 창을 어떻게 가져 옵니까? 그렇게하기 위해 사용 된 코드를 보여주십시오. 내 생각 엔 Log4J와 코드가 동일한 Log 인스턴스를 사용하지 않는다는 것입니다. –

1

setText() 또는 setContentType()을 호출하는지 확인하고 Document를 다시 만드는 다른 방법이 될 수 있습니다. 문서에 대한 참조를 저장하는 대신 창에서 가져옵니다. 하지

doc.insertString(doc.getLength(), "Hello World!", null); 

하지만

log.getStyledDocument().insertString(doc.getLength(), "Hello World!", null); 
+0

언급 된 방법 중 하나를 호출하지 않습니다. 직접 참조를 얻는 것도 효과가 없습니다. 제 질문에 좀 더 많은 정보를 추가했습니다. 한번보세요. –

+0

+1'Runnble # Thread' 안에 감싸 진 simlair (삭제 된) 응답을 보냈지 만 Log4J가 Console, File 또는 DB에 출력을 저장할 수 있기 때문에 @Lukas Knuth가' 그는'Log4J'와'Swing JComponents' 사이에'API 브리지'를 놓쳤습니다. – mKorbel