2014-10-30 3 views
0

В настоящее время я пишу программу, которая принимает стилизованный текст в JTextPane, а также отображает тот же текст в не редактируемом JTextPane.. Проблема в том, что я действительно хочу разобрать документы между вводом и отображением. В основном я хочу иметь возможность разделить DefaultStyledDocument на два документа при сохранении форматирования. Как это сделать?Splitting StyledDocument

ВПЧЭ точка, иллюстрирующее:

import java.awt.Color; 
import javax.swing.text.DefaultStyledDocument; 
import javax.swing.text.SimpleAttributeSet; 
import javax.swing.text.StyleConstants; 


public class SSCCE extends javax.swing.JFrame { 


    public SSCCE() { 
     initComponents(); 
     try { 
     DefaultStyledDocument doc = new DefaultStyledDocument(); 
     SimpleAttributeSet attr = new SimpleAttributeSet(); 
     StyleConstants.setBold(attr, true); 
     doc.insertString(0, "This is bold.\n\n", attr); 
     StyleConstants.setItalic(attr, true); 
     doc.insertString(doc.getLength() - 1, "This is bold and italicized.\n", attr); 
     doc.insertString(doc.getLength() - 1, "--\n", null); //This is a delimeter, for splitting the doucment 
     StyleConstants.setBold(attr, false); 
     StyleConstants.setForeground(attr, Color.red); 
     doc.insertString(doc.getLength() - 1, "This is italicized and red.\n", attr); 
     StyleConstants.setBold(attr, true); 
     StyleConstants.setItalic(attr, false); 
     doc.insertString(doc.getLength() -1 , "This is bold and red.\n", attr); 
     txpInput.setDocument(doc); //txpInput is a JTextPane 
     } catch (Exception e) { 
      e.printStackTrace(); 
     } 

    } 

    @SuppressWarnings("unchecked")      
    private void initComponents() { 

     jScrollPane1 = new javax.swing.JScrollPane(); 
     jPanel1 = new javax.swing.JPanel(); 
     jScrollPane2 = new javax.swing.JScrollPane(); 
     txpInput = new javax.swing.JTextPane(); 
     jScrollPane3 = new javax.swing.JScrollPane(); 
     txpOutput1 = new javax.swing.JTextPane(); 
     jLabel1 = new javax.swing.JLabel(); 
     btnOutput = new javax.swing.JButton(); 
     jScrollPane4 = new javax.swing.JScrollPane(); 
     txpOutput2 = new javax.swing.JTextPane(); 

     setDefaultCloseOperation(javax.swing.WindowConstants.EXIT_ON_CLOSE); 

     jScrollPane2.setViewportView(txpInput); 

     txpOutput1.setEditable(false); 
     jScrollPane3.setViewportView(txpOutput1); 

     jLabel1.setText("Output:"); 

     btnOutput.setText("Output"); 
     btnOutput.addActionListener(new java.awt.event.ActionListener() { 
      public void actionPerformed(java.awt.event.ActionEvent evt) { 
       btnOutputActionPerformed(evt); 
      } 
     }); 

     txpOutput2.setEditable(false); 
     jScrollPane4.setViewportView(txpOutput2); 

     javax.swing.GroupLayout jPanel1Layout = new javax.swing.GroupLayout(jPanel1); 
     jPanel1.setLayout(jPanel1Layout); 
     jPanel1Layout.setHorizontalGroup(
      jPanel1Layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING) 
      .addGroup(jPanel1Layout.createSequentialGroup() 
       .addContainerGap() 
       .addGroup(jPanel1Layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING) 
        .addComponent(jScrollPane3, javax.swing.GroupLayout.Alignment.TRAILING) 
        .addComponent(jLabel1, javax.swing.GroupLayout.Alignment.TRAILING, javax.swing.GroupLayout.DEFAULT_SIZE, javax.swing.GroupLayout.DEFAULT_SIZE, Short.MAX_VALUE) 
        .addComponent(jScrollPane2) 
        .addGroup(jPanel1Layout.createSequentialGroup() 
         .addComponent(btnOutput, javax.swing.GroupLayout.PREFERRED_SIZE, 174, javax.swing.GroupLayout.PREFERRED_SIZE) 
         .addGap(0, 462, Short.MAX_VALUE)) 
        .addComponent(jScrollPane4)) 
       .addContainerGap()) 
     ); 
     jPanel1Layout.setVerticalGroup(
      jPanel1Layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING) 
      .addGroup(jPanel1Layout.createSequentialGroup() 
       .addContainerGap() 
       .addComponent(jScrollPane2, javax.swing.GroupLayout.PREFERRED_SIZE, 105, javax.swing.GroupLayout.PREFERRED_SIZE) 
       .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) 
       .addComponent(jLabel1) 
       .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) 
       .addComponent(btnOutput) 
       .addGap(9, 9, 9) 
       .addComponent(jScrollPane3, javax.swing.GroupLayout.PREFERRED_SIZE, 135, javax.swing.GroupLayout.PREFERRED_SIZE) 
       .addPreferredGap(javax.swing.LayoutStyle.ComponentPlacement.RELATED) 
       .addComponent(jScrollPane4, javax.swing.GroupLayout.PREFERRED_SIZE, 135, javax.swing.GroupLayout.PREFERRED_SIZE) 
       .addContainerGap(79, Short.MAX_VALUE)) 
     ); 

     jScrollPane1.setViewportView(jPanel1); 

     javax.swing.GroupLayout layout = new javax.swing.GroupLayout(getContentPane()); 
     getContentPane().setLayout(layout); 
     layout.setHorizontalGroup(
      layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING) 
      .addComponent(jScrollPane1) 
     ); 
     layout.setVerticalGroup(
      layout.createParallelGroup(javax.swing.GroupLayout.Alignment.LEADING) 
      .addComponent(jScrollPane1) 
     ); 

     pack(); 
    }       

    private void btnOutputActionPerformed(java.awt.event.ActionEvent evt) {           
     //Comment out the body of this method to get code to run 
     //This needs to parse the text and output it to the two output JTextPanes 
     DefaultStyledDocument inputDoc = (DefaultStyledDocument) txpInput.getDocument(); 
     DefaultStyledDocument[] output = inputDoc.split("--"); //Invalid, is there an equivalent 
     txpOutput1.setDocument(ouput[0]); 
     txpOutput2.setDocument(ouput[1]); 
     this.validate(); 
     this.repaint(); 
    }           

    public static void main(String args[]) { 
     /* Set the Nimbus look and feel */ 
     try { 
      for (javax.swing.UIManager.LookAndFeelInfo info : javax.swing.UIManager.getInstalledLookAndFeels()) { 
       if ("Nimbus".equals(info.getName())) { 
        javax.swing.UIManager.setLookAndFeel(info.getClassName()); 
        break; 
       } 
      } 
     } catch (ClassNotFoundException ex) { 
      java.util.logging.Logger.getLogger(SSCCE.class.getName()).log(java.util.logging.Level.SEVERE, null, ex); 
     } catch (InstantiationException ex) { 
      java.util.logging.Logger.getLogger(SSCCE.class.getName()).log(java.util.logging.Level.SEVERE, null, ex); 
     } catch (IllegalAccessException ex) { 
      java.util.logging.Logger.getLogger(SSCCE.class.getName()).log(java.util.logging.Level.SEVERE, null, ex); 
     } catch (javax.swing.UnsupportedLookAndFeelException ex) { 
      java.util.logging.Logger.getLogger(SSCCE.class.getName()).log(java.util.logging.Level.SEVERE, null, ex); 
     }  
     /* Create and display the form */ 
     java.awt.EventQueue.invokeLater(new Runnable() { 
      public void run() { 
       new SSCCE().setVisible(true); 
      } 
     }); 
    } 

    // Variables declaration - do not modify      
    private javax.swing.JButton btnOutput; 
    private javax.swing.JLabel jLabel1; 
    private javax.swing.JPanel jPanel1; 
    private javax.swing.JScrollPane jScrollPane1; 
    private javax.swing.JScrollPane jScrollPane2; 
    private javax.swing.JScrollPane jScrollPane3; 
    private javax.swing.JScrollPane jScrollPane4; 
    private javax.swing.JTextPane txpInput; 
    private javax.swing.JTextPane txpOutput1; 
    private javax.swing.JTextPane txpOutput2; 
    // End of variables declaration     
} 

Примечание: Я использую Netbeans строитель GUI, следовательно, длинный сгенерированный код.

В принципе, в примере я ввожу некоторый отформатированный текст на вход JTextPane. Затем я хочу разбить этот форматированный текст на две панели вывода, не теряя форматирования. В SCCE, когда пользователь нажимает кнопку «Выход», данные должны копироваться, разделяясь линией --. В примере я использовал несуществующий метод split(), но я думаю, что он имеет смысл.

Это ожидаемый вход (для данного примера): enter image description here

И это ожидаемый результат: enter image description here

Первоначально я думал this вопрос был возможный ответ. Но я попробовал и нашел, что это не работает. Итак, наконец, как я могу разделить стилизованный документ, сохраняя стиль.

ответ

0

Создайте 2 копии StyledDocument из того же источника контента.

Найти разделитель документов.

В первом документе удалите все содержимое перед разделителем.

Во втором документе удалите весь контент после разделителя.

UPDATE: вы можете использовать the code для слияния документов, но иметь 2 документа назначения и перенаправить вставки исходного документа в нужный экземпляр в соответствии с вашими правилами фильтрации.

+0

Как получить два документа? Я получаю документ с JTextPane. Это только передаст мне ссылку на _one_ документ. – DonyorM

+0

Вы можете просто создать его - новый EditorKitDependentDocument или textPane.getEditorKit(). CreateDefaultDocument() – StanislavL