2012-07-09 14 views
9

मैं एक साधारण चैट प्रोग्राम बना रहा हूं जिसे मैं अंततः HTML लिंक दिखाना चाहता हूं। मेरी समस्या अभी यह है कि मैं उपयोगकर्ता नाम के बगल में पाठ को प्रकट नहीं कर सकता जैसा कि मैं चाहता हूं।JTextPane/JEditorPane और अजीब पाठ समस्या

मैं उपयोगकर्ता का नाम बोल्ड होना चाहता हूं, और पाठ इसके बगल में दिखाई देने वाला है, लेकिन किसी कारण से गैर बोल्ड टेक्स्ट केंद्रित दिखाई देता है।

यदि मैं उपयोगकर्ता नाम बोल्ड नहीं करता हूं, तो यह ठीक काम करता है। शीर्ष दो यह है कि जब मेरे नाम बोल्ड होते हैं तो यह कैसा दिखाई देता है, मध्य तब होता है जब नाम बोल्ड नहीं होता है, नीचे एक हाइपरलिंक दिखाता है, मैं इसे मध्य दो की तरह दिखाना चाहता हूं, लेकिन बोल्ड नामों के साथ।

enter image description here

यहाँ मैं गलत क्या कर रहा हूँ कोड है? ध्यान दें कि मैंने JEextPane को JEditorPane के साथ बदलने की कोशिश की और वही बात होती है।

package com.test; 

import java.awt.BorderLayout; 
import java.awt.Color; 

import javax.swing.JFrame; 
import javax.swing.JPanel; 
import javax.swing.JScrollPane; 
import javax.swing.JTextPane; 
import javax.swing.WindowConstants; 
import javax.swing.event.HyperlinkEvent; 
import javax.swing.event.HyperlinkEvent.EventType; 
import javax.swing.event.HyperlinkListener; 
import javax.swing.text.BadLocationException; 
import javax.swing.text.SimpleAttributeSet; 
import javax.swing.text.StyleConstants; 
import javax.swing.text.html.HTML; 

public class JTextPaneTest extends JPanel { 

    JTextPane pane; 

    public JTextPaneTest() { 
     this.setLayout(new BorderLayout()); 

     pane = new JTextPane(); 
     pane.setEditable(false); 
     pane.setContentType("text/html"); 

     JScrollPane scrollPane = new JScrollPane(pane); 
     this.add(scrollPane, BorderLayout.CENTER); 

     pane.addHyperlinkListener(new HyperlinkListener() { 

      @Override 
      public void hyperlinkUpdate(HyperlinkEvent e) { 
       if (e.getEventType() == EventType.ACTIVATED) { 
        System.out.println(e.getDescription()); 
       } 

      } 
     }); 

    } 

    public void chatWithBold(String user, String text) { 

     SimpleAttributeSet bold = new SimpleAttributeSet(); 
     StyleConstants.setBold(bold, true); 

     SimpleAttributeSet normal = new SimpleAttributeSet(); 

     try { 
      pane.getDocument().insertString(pane.getDocument().getLength(), 
        user + ": ", bold); 
     } catch (BadLocationException e) { 
      // TODO Auto-generated catch block 
      e.printStackTrace(); 
     } 

     try { 
      pane.getDocument().insertString(pane.getDocument().getLength(), 
        text + "\n", normal); 
     } catch (BadLocationException e) { 
      // TODO Auto-generated catch block 
      e.printStackTrace(); 
     } 
    } 

    public void chatNoBold(String user, String text) { 

     SimpleAttributeSet bold = new SimpleAttributeSet(); 
     StyleConstants.setBold(bold, true); 

     SimpleAttributeSet normal = new SimpleAttributeSet(); 

     try { 
      pane.getDocument().insertString(pane.getDocument().getLength(), 
        user + ": ", normal); 
     } catch (BadLocationException e) { 
      // TODO Auto-generated catch block 
      e.printStackTrace(); 
     } 

     try { 
      pane.getDocument().insertString(pane.getDocument().getLength(), 
        text + "\n", normal); 
     } catch (BadLocationException e) { 
      // TODO Auto-generated catch block 
      e.printStackTrace(); 
     } 
    } 

    private void submitALinkWithBold(String user, String link) { 
     SimpleAttributeSet bold = new SimpleAttributeSet(); 
     StyleConstants.setBold(bold, true); 

     try { 
      pane.getDocument().insertString(pane.getDocument().getLength(), 
        user + ": ", bold); 
     } catch (BadLocationException e) { 
      // TODO Auto-generated catch block 
      e.printStackTrace(); 
     } 

     SimpleAttributeSet attrs = new SimpleAttributeSet(); 
     attrs.addAttribute(HTML.Attribute.HREF, link); 

     SimpleAttributeSet htmlLink = new SimpleAttributeSet(); 
     htmlLink.addAttribute(HTML.Tag.A, attrs); 
     StyleConstants.setUnderline(htmlLink, true); 
     StyleConstants.setForeground(htmlLink, Color.BLUE); 
     try { 
      pane.getDocument().insertString(pane.getDocument().getLength(), 
        link + "\n", htmlLink); 
     } catch (BadLocationException e) { 
      // TODO Auto-generated catch block 
      e.printStackTrace(); 
     } 

    } 

    public static void main(String[] args) { 
     JFrame frame = new JFrame(); 

     JTextPaneTest chat = new JTextPaneTest(); 
     frame.add(chat); 

     frame.setDefaultCloseOperation(WindowConstants.DISPOSE_ON_CLOSE); 

     chat.chatWithBold("User1", "Hi everyone"); 
     chat.chatWithBold("User2", "Hey.. Hows it going"); 

     chat.chatNoBold("User1", "Hi everyone"); 
     chat.chatNoBold("User2", "Hey.. Hows it going"); 

     chat.submitALinkWithBold("User1", "http://www.stackoverflow.com"); 

     frame.setSize(400, 400); 

     frame.setVisible(true); 

    } 

} 
+2

1+ एक अच्छी तरह से कामकाजी और लघु डेमो प्रोग्राम पोस्ट करने के लिए, जो समस्या को अच्छी तरह से दिखाता है। –

+1

मैं कोई JTextPane विशेषज्ञ नहीं हूं, लेकिन मुझे लगता है कि अगर आप 'pane.setContentType ("text/html");' line 'पर टिप्पणी करते हैं तो समस्या दूर हो जाती है। –

+0

हाँ, मुझे पता है कि समस्या के साथ समस्या दूर हो गई है। मैं टेक्स्ट/एचटीएमएल का उपयोग कर रहा हूं क्योंकि मुझे इसे हाइपरलिंक प्रदर्शित करने में सक्षम होने की आवश्यकता है, और वे केवल टेक्स्ट/एचटीएमएल सेट के साथ काम करने लगते हैं। – systemoutprintln

उत्तर

3

मैं सिर्फ खेला और थोड़ा के आसपास खोज की है और निम्नलिखित समाधान नहीं मिला:

प्रारंभ अपने JTextPaneकुछ इस तरह के साथ सामग्री प्रकार सेट करने के बाद:

final String emptyHtml = "<html><body id='bodyElement'></body></html>"; 
pane.getEditorKit().read(new StringReader(emptyHtml), pane.getDocument(), 0); 

को आरम्भ करने के बाद निम्नलिखित दो नए फ़ील्ड (केवल सुविधा के लिए, विधियों में उपयोग किए जाएंगे):

this.doc = (HTMLDocument) pane.getDocument(); 
this.bodyElement = this.doc.getElement("bodyElement"); 

अब तुम इस तरह अपने विधि submitALinkWithBold बदल सकते हैं:

final String html = "<p><b>" + user + ": </b>" 
    + "<a href='" + link + "'>" + link + "</a></p>"; 
doc.insertBeforeEnd(bodyElement, html); 

तुम भी अन्य दो तरीकों (chatWithBold और chatNoBold) करने के लिए इस योजना को अपनाने के लिए सक्षम होना चाहिए।

ध्यान दें कि जब तक आप अपने सभी तरीकों को बदल नहीं लेते हैं, तो परिणाम अच्छा नहीं दिखता है (या बिल्कुल काम नहीं करता)। यह भी ध्यान रखें कि सभी विधियों को बदलने के बाद भी, यह आपके मूल उदाहरण (बड़ी लाइन दूरी, अन्य फ़ॉन्ट ...) जैसा नहीं दिखता है। मुझे लगता है कि इसे pane.getEditorKit() को HTMLEditorKit पर कास्टिंग करके और setStyleSheet(…) विधि का उपयोग करके तय किया जा सकता है लेकिन मैंने यह कोशिश नहीं की।

संबंधित मुद्दे