2016-01-16 2 views
0

Я пытаюсь «нормализовать» подкласс DefaultStyledDocument в том смысле, что у нас есть org.w3c.dom.Node.normalize(): т. Е. Слияние смежного текста «листья». В случае DefaultStyledDocument эти листья идентифицируются для слияния, если два соседних имеют одинаковые атрибуты (или none).Jython - как я могу объединить два LeafElements в DefaultStyledDocument?

Ниже приведена простая версия (мы не проверяем фактические атрибуты: это прецедент, где у вас есть простой текст или текст с одним возможным стилем разметки).

def normalise(self): 
    # recursive function: 
    def normalise_structure(el, depth = 0): 
     indent = ' ' * depth 
     start = el.startOffset 
     print('%s# el %s |%s|' % (indent, el, self.getText(start, el.endOffset - start))) 
     prev_attr_set = None 
     for i in range(el.elementCount): 
      subelement = el.getElement(i) 
      normalise_structure(subelement, depth + 1) 
      if subelement.leaf: 
       curr_attr_set = subelement.attributes 
       print('%s # this is a leaf, attribs %s' % (indent, curr_attr_set,)) 
       # this is a simple version: only works if there is only one possible attribute 
       if prev_attr_set and curr_attr_set and prev_attr_set.attributeCount == curr_attr_set.attributeCount: 
        print('%s # %s leaf needs to be merged with previous leaf' % ( 
           indent, 'marked-up' if prev_attr_set.attributeCount == 1 else 'plain')) 
        attr_set = prev_attr_set.getElement(0) if prev_attr_set.attributeCount else None 
        prev_subelement = el.getElement(i - 1) 
        prev_start = prev_subelement.startOffset 
        curr_end = subelement.endOffset 
        merged_element = javax.swing.text.AbstractDocument.LeafElement( 
         javax.swing.text.DefaultStyledDocument(), el, attr_set, prev_start, curr_end ) 
        el.replace(prev_start, curr_end - prev_start, [ merged_element ]) 
       prev_attr_set = curr_attr_set 
      else: 
       print('%s # NOT a leaf...' % (indent,)) 
       prev_attr_set = None 
    for self_el in self.rootElements: 
     normalise_structure(self_el) 

Когда я запускаю это я получаю эту ошибку:

Exception in thread "AWT-EventQueue-0" java.lang.ArrayIndexOutOfBoundsException at java.lang.System.arraycopy(Native Method) at javax.swing.text.AbstractDocument$BranchElement.replace(AbstractDocument.java:2290)

Я спешу добавить, что, прежде чем пытаться javax.swing.text.DefaultStyledDocument(), как пары 1 в конструкторе LeafElement я попытался «self» (т.е. DefaultStyledDocument, призывающий normalise on line один): такой же ошибка.

ответ

0

Да, можно сделать:

AbstractDocument.BranchElement.replace() выглядит следующим образом:

public void replace(int offset, int length, Element[] elems) 
    ... 

Оказывается, что «смещение» и «длина» здесь относятся к подразделам элементов BranchElement (обычно LeafElements) , а не на смещение и длину базового текста в StyledDocument.

Кто-нибудь умнее меня получил бы это раньше. Документация по API (Java 7) может сделать это немного яснее ....