1 # -*- coding: utf-8 -*-
4 This file is part of the LibreOffice project.
6 This Source Code Form is subject to the terms of the Mozilla Public
7 License, v. 2.0. If a copy of the MPL was not distributed with this
8 file, You can obtain one at http://mozilla.org/MPL/2.0/.
10 This file incorporates work covered by the following license notice:
12 Licensed to the Apache Software Foundation (ASF) under one or more
13 contributor license agreements. See the NOTICE file distributed
14 with this work for additional information regarding copyright
15 ownership. The ASF licenses this file to you under the Apache
16 License, Version 2.0 (the "License"); you may not use this file
17 except in compliance with the License. You may obtain a copy of
18 the License at http://www.apache.org/licenses/LICENSE-2.0 .
23 from org
.libreoffice
.unotest
import UnoInProcess
, mkPropertyValue
24 from tempfile
import TemporaryDirectory
25 from com
.sun
.star
.uno
import RuntimeException
26 from com
.sun
.star
.lang
import IllegalArgumentException
, NoSupportException
27 from com
.sun
.star
.beans
import PropertyValue
, StringPair
28 from com
.sun
.star
.rdf
.URIs
import ODF_PREFIX
, ODF_SUFFIX
29 from com
.sun
.star
.i18n
.NumberFormatIndex
import NUMBER_INT
30 from com
.sun
.star
.text
.ControlCharacter
import PARAGRAPH_BREAK
, HARD_HYPHEN
31 from com
.sun
.star
.text
.TextContentAnchorType
import (
32 AT_CHARACTER
, AS_CHARACTER
, AT_PARAGRAPH
, AT_PAGE
, AT_FRAME
)
36 '''base class for tree nodes. only instance: root of tree.'''
38 def __init__(self
, content
=None):
39 self
.content
= content
41 self
.nodetype
= "__ROOT__"
42 self
.isnesting
= False
45 return "<{}>".format(self
.nodetype
)
47 def __eq__(self
, other
):
48 return type(self
) == type(other
)
50 def __ne__(self
, other
):
51 return not self
== other
53 def _dup(self
, nodetype
, *args
):
55 return nodetype(*args
)
56 except Exception as e
:
57 raise RuntimeError("TreeNode.dup") from e
59 def createenumeration(self
):
60 return iter(self
._children
)
62 def appendchild(self
, child
):
63 self
._children
.append(child
)
67 class ContentNode(TreeNode
):
69 def __init__(self
, content
):
70 super().__init
__(content
)
73 return "{}\tcontent: {}".format(super().__str
__(), self
.content
)
75 def __eq__(self
, other
):
77 return other
.content
== self
.content
and super().__eq
__(other
)
78 except AttributeError:
81 def appendchild(self
, child
):
83 self
._children
.append(child
)
85 except Exception as e
:
86 raise RuntimeError("ContentNode.appendchild") from e
89 class TextNode(ContentNode
):
91 def __init__(self
, content
):
92 super().__init
__(content
)
93 self
.nodetype
= "Text"
96 return self
._dup
(TextNode
, self
.content
)
99 class TextFieldNode(ContentNode
):
101 def __init__(self
, content
):
102 super().__init
__(content
)
103 self
.nodetype
= "TextField"
106 return self
._dup
(TextFieldNode
, self
.content
)
109 class ControlCharacterNode(TreeNode
):
110 def __init__(self
, char
):
113 self
.nodetype
= "ControlCharacter"
116 return "{}\tcontent: {}".format(super().__str
__(), self
.char
)
118 def __eq__(self
, other
):
120 return other
.char
== self
.char
and super().__eq
__(other
)
121 except AttributeError:
125 return self
._dup
(ControlCharacterNode
, self
.char
)
128 class FootnoteNode(TreeNode
):
130 def __init__(self
, label
):
133 self
.nodetype
= "Footnote"
136 return "{}\tlabel: {}".format(super().__str
__(), self
.label
)
138 def __eq__(self
, other
):
140 return other
.label
== self
.label
and super().__eq
__(other
)
141 except AttributeError:
145 return self
._dup
(FootnoteNode
, self
.label
)
148 class FrameNode(TreeNode
):
149 def __init__(self
, name
, anchor
):
153 self
.nodetype
= "Frame"
156 return "{}\tname: {}\tanchor: {}".format(
157 super().__str
__(),self
.name
, self
.str_anchor(self
.anchor
))
159 def __eq__(self
, other
):
161 return (other
.name
== self
.name
and
162 other
.anchor
== self
.anchor
and
163 super().__eq
__(other
))
164 except AttributeError:
168 return self
._dup
(FrameNode
, self
.name
, self
.anchor
)
170 def str_anchor(self
, anchor
):
171 anchors
= {str(AS_CHARACTER
): "AS_CHARACTER",
172 str(AT_CHARACTER
): "AT_CHARACTER",
173 str(AT_PARAGRAPH
): "AT_PARAGRAPH",
174 str(AT_PAGE
): "AT_PAGE",
175 str(AT_FRAME
): "AT_FRAME"}
177 return anchors
[str(anchor
)]
179 raise RuntimeError("unknown anchor")
182 class MetaNode(TreeNode
):
183 def __init__(self
, xmlid
):
186 self
.nodetype
= "InContentMetadata"
187 self
.isnesting
= True
190 return "{}\txmlid: {}#{}".format(
191 super().__str
__(), self
.xmlid
.First
, self
.xmlid
.Second
)
193 def __eq__(self
, other
):
195 return (type(other
) == type(self
) and
196 MetaNode
.eq(other
.xmlid
, self
.xmlid
))
197 except AttributeError:
201 def eq(cls
, left
, right
):
202 return left
.First
== right
.First
and left
.Second
== right
.Second
205 return self
._dup
(MetaNode
, self
.xmlid
)
208 class MarkNode(TreeNode
):
209 def __init__(self
, name
, ispoint
=True):
212 self
.ispoint
= ispoint
216 return "{}\tisPoint: {}\tisStart: {}".format(
217 super().__str
__(), self
.ispoint
, self
.isstart
)
219 def __eq__(self
, other
):
221 return (other
.name
== self
.name
and
222 other
.ispoint
== self
.ispoint
and
223 other
.isstart
== self
.isstart
)
224 except AttributeError:
228 class BookmarkNode(MarkNode
):
229 def __init__(self
, name
, xmlid
=StringPair()):
230 super().__init
__(name
)
232 self
.nodetype
= "Bookmark"
235 return "{}\txmlid: {}#{}".format(
236 super().__str
__(), self
.xmlid
.First
, self
.xmlid
.Second
)
238 def __eq__(self
, other
):
240 return (type(other
) == type(self
) and
241 super().__eq
__(other
) and
242 MetaNode
.eq(other
.xmlid
, self
.xmlid
))
243 except AttributeError:
247 return self
._dup
(BookmarkNode
, self
.name
, self
.xmlid
)
250 class BookmarkStartNode(BookmarkNode
):
252 def __init__(self
, name
, xmlid
=StringPair()):
253 super().__init
__(name
, xmlid
)
258 return self
._dup
(BookmarkStartNode
, self
.name
)
261 class BookmarkEndNode(BookmarkNode
):
263 def __init__(self
, name
, xmlid
=StringPair()):
264 super().__init
__(name
, xmlid
)
269 return self
._dup
(BookmarkEndNode
, self
.name
)
272 class ReferenceMarkNode(MarkNode
):
273 def __init__(self
, name
):
274 super().__init
__(name
)
275 self
.nodetype
= "ReferenceMark"
277 def __eq__(self
, other
):
278 return (type(other
) == type(self
) and super().__eq
__(other
))
281 return self
._dup
(ReferenceMarkNode
, self
.name
)
284 class ReferenceMarkStartNode(ReferenceMarkNode
):
285 def __init__(self
, name
):
286 super().__init
__(name
)
291 return self
._dup
(ReferenceMarkStartNode
, self
.name
)
294 class ReferenceMarkEndNode(ReferenceMarkNode
):
295 def __init__(self
, name
):
296 super().__init
__(name
)
301 return self
._dup
(ReferenceMarkEndNode
, self
.name
)
304 class DocumentIndexMarkNode(MarkNode
):
305 def __init__(self
, name
):
306 super().__init
__(name
)
307 self
.nodetype
= "DocumentIndexMark"
309 def __eq__(self
, other
):
310 return (type(other
) == type(self
) and super().__eq
__(other
))
313 return self
._dup
(DocumentIndexMarkNode
, self
.name
)
316 class DocumentIndexMarkStartNode(DocumentIndexMarkNode
):
317 def __init__(self
, name
):
318 super().__init
__(name
)
323 return self
._dup
(DocumentIndexMarkStartNode
, self
.name
)
326 class DocumentIndexMarkEndNode(DocumentIndexMarkNode
):
327 def __init__(self
, name
):
328 super().__init
__(name
)
333 return self
._dup
(DocumentIndexMarkEndNode
, self
.name
)
336 class HyperlinkNode(TreeNode
):
337 def __init__(self
, url
):
339 self
.nodetype
= "Hyperlink"
340 self
.isnesting
= True
344 raise RuntimeError("HyperlinkNode")
347 return "{}\turl: {}".format(super().__str
__(), self
.url
)
349 def __eq__(self
, other
):
351 return other
.url
== self
.url
and super().__eq
__(other
)
352 except AttributeError:
356 return self
._dup
(HyperlinkNode
, self
.url
)
359 class RubyNode(TreeNode
):
360 def __init__(self
, ruby
):
362 self
.nodetype
= "Ruby"
363 self
.isnesting
= True
367 raise RuntimeError("RubyNode")
370 return "{}\trubytext: {}".format(super().__str
__(), self
.ruby
)
372 def __eq__(self
, other
):
374 return other
.ruby
== self
.ruby
and super().__eq
__(other
)
375 except AttributeError:
379 return self
._dup
(RubyNode
, self
.ruby
)
382 class MetaFieldNode(MetaNode
):
383 def __init__(self
, xmlid
):
384 super().__init
__(xmlid
)
385 self
.nodetype
= "MetadataField"
388 return self
._dup
(MetaFieldNode
, self
.xmlid
)
392 def __init__(self
, start
, end
, node
):
396 self
.extent
= end
- start
401 def __init__(self
, xDoc
):
403 self
.xText
= xDoc
.getText()
404 self
.xCursor
= self
.xText
.createTextCursor()
406 def initparagraph(self
):
407 ## we split the first (empty) paragraph, and then insert into the
408 ## second (empty) paragraph; this ensures first is always empty!
409 self
.xCursor
.gotoStartOfParagraph(False)
410 self
.xText
.insertControlCharacter(self
.xCursor
, PARAGRAPH_BREAK
, False)
412 def inserttext(self
, xCursor
, text
):
413 xCursor
.setString(text
)
415 def inserttextfield(self
, xCursor
, content
):
416 xContent
= self
.maketextfield(content
)
417 xContent
.attach(xCursor
)
419 def maketextfield(self
, content
):
420 xField
= self
.xDoc
.createInstance("com.sun.star.text.textfield.Author")
421 xField
.IsFixed
= True
422 xField
.FullName
= False
423 xField
.Content
= content
426 def insertcontrolcharacter(self
, xCursor
, cchar
):
427 self
.xText
.insertControlCharacter(xCursor
, cchar
, False)
429 def insertframe(self
, xCursor
, name
, anchor
):
430 xContent
= self
.makeframe(name
, anchor
)
431 xContent
.attach(xCursor
)
433 def makeframe(self
, name
, anchor
):
434 xFrame
= self
.xDoc
.createInstance("com.sun.star.text.TextFrame")
435 xFrame
.AnchorType
= anchor
439 def insertfootnote(self
, xCursor
, label
):
440 xContent
= self
.makefootnote(label
)
441 xContent
.attach(xCursor
)
443 def makefootnote(self
, label
):
444 xFootNote
= self
.xDoc
.createInstance("com.sun.star.text.Footnote")
445 xFootNote
.setLabel(label
)
448 def insertbookmark(self
, xCursor
, name
, xmlid
):
449 xContent
= self
.makebookmark(name
)
450 xContent
.attach(xCursor
)
451 if xmlid
.First
!= "":
452 xContent
.MetadataReference
= xmlid
454 def makebookmark(self
, name
):
455 xBookmark
= self
.xDoc
.createInstance("com.sun.star.text.Bookmark")
456 xBookmark
.setName(name
)
459 def insertreferencemark(self
, xCursor
, name
):
460 xContent
= self
.makereferencemark(name
)
461 xContent
.attach(xCursor
)
463 def makereferencemark(self
, name
):
464 xMark
= self
.xDoc
.createInstance("com.sun.star.text.ReferenceMark")
468 def insertdocumentindexmark(self
, xCursor
, key
):
469 xContent
= self
.makedocumentindexmark(key
)
470 xContent
.attach(xCursor
)
472 def makedocumentindexmark(self
, key
):
473 xMark
= self
.xDoc
.createInstance("com.sun.star.text.DocumentIndexMark")
474 xMark
.PrimaryKey
= key
477 def inserthyperlink(self
, xCursor
, url
):
478 xCursor
.HyperLinkURL
= url
480 def insertruby(self
, xCursor
, rubytext
):
481 xCursor
.RubyText
= rubytext
483 def insertmeta(self
, xCursor
, xmlid
):
484 xContent
= self
.makemeta()
485 xContent
.attach(xCursor
)
486 xContent
.MetadataReference
= xmlid
490 xMeta
= self
.xDoc
.createInstance("com.sun.star.text.InContentMetadata")
493 def insertmetafield(self
, xCursor
, xmlid
):
494 xContent
= self
.makemetafield()
495 xContent
.attach(xCursor
)
496 xContent
.MetadataReference
= xmlid
499 def makemetafield(self
):
500 xMeta
= self
.xDoc
.createInstance(
501 "com.sun.star.text.textfield.MetadataField")
505 class TreeInserter(Inserter
):
507 def __init__(self
, xDoc
):
508 super().__init
__(xDoc
)
509 self
._bookmarkstarts
= {}
510 self
._referencemarkstarts
= {}
511 self
._documentindexmarkstarts
= {}
512 self
._framehints
= []
514 def inserttree(self
, tree
):
515 if tree
.nodetype
!= "__ROOT__":
516 raise RuntimeError("insertTree: test error: no root")
518 self
.insertchildren(tree
.createenumeration())
519 for p
in self
._framehints
:
520 self
.insertframe(p
[0], p
[1].name
, p
[1].anchor
)
522 def insertchildren(self
, children
):
523 xCursor
= self
.xCursor
524 for node
in children
:
525 xCursor
.gotoEndOfParagraph(False)
526 type_
= node
.nodetype
528 self
.inserttext(xCursor
, node
.content
)
529 elif type_
== "TextField":
530 self
.inserttextfield(xCursor
, node
.content
)
531 elif type_
== "ControlCharacter":
532 self
.insertcontrolcharacter(xCursor
, node
.char
)
533 elif type_
== "Footnote":
534 self
.insertfootnote(xCursor
, node
.label
)
535 elif type_
== "Frame":
536 if node
.anchor
== AT_CHARACTER
:
537 self
._framehints
.append((xCursor
.getStart(), node
))
539 self
.insertframe(xCursor
, node
.name
, node
.anchor
)
540 elif type_
== "Bookmark":
544 self
.insertbookmark(xCursor
, name
, id_
)
546 self
._bookmarkstarts
[name
] = xCursor
.getStart()
548 xRange
= self
._bookmarkstarts
[name
]
549 xParaCursor
= self
.mkcursor(xRange
)
550 self
.insertbookmark(xParaCursor
, name
, id_
)
551 elif type_
== "ReferenceMark":
554 self
.insertreferencemark(xCursor
, name
)
556 self
._referencemarkstarts
[name
] = xCursor
.getStart()
558 xRange
= self
._referencemarkstarts
[name
]
559 xParaCursor
= self
.mkcursor(xRange
)
560 self
.insertreferencemark(xParaCursor
, name
)
561 elif type_
== "DocumentIndexMark":
564 self
.insertdocumentindexmark(xCursor
, name
)
566 self
._documentindexmarkstarts
[name
] = xCursor
.getStart()
568 xRange
= self
._documentindexmarkstarts
[name
]
569 xParaCursor
= self
.mkcursor(xRange
)
570 self
.insertdocumentindexmark(xParaCursor
, name
)
571 elif type_
== "Hyperlink":
572 xRange
= xCursor
.getStart()
573 self
.insertchildren(node
.createenumeration())
574 xParaCursor
= self
.mkcursor(xRange
)
575 self
.inserthyperlink(xParaCursor
, node
.url
)
576 elif type_
== "Ruby":
577 xRange
= xCursor
.getStart()
578 self
.insertchildren(node
.createenumeration())
579 xParaCursor
= self
.mkcursor(xRange
)
580 self
.insertruby(xParaCursor
, node
.ruby
)
581 elif type_
== "InContentMetadata":
582 xRange
= xCursor
.getStart()
583 self
.insertchildren(node
.createenumeration())
584 xParaCursor
= self
.mkcursor(xRange
)
585 self
.insertmeta(xParaCursor
, node
.xmlid
)
586 elif type_
== "MetadataField":
587 xRange
= xCursor
.getStart()
588 self
.insertchildren(node
.createenumeration())
589 xParaCursor
= self
.mkcursor(xRange
)
590 self
.insertmetafield(xParaCursor
, node
.xmlid
)
591 elif type_
== "SoftPageBreak":
592 raise RuntimeError("sorry, cannot test SoftPageBreak")
594 raise RuntimeError("unexpected type: {}".format(type_
))
596 def mkcursor(self
, xRange
):
597 xCursor
= self
.xText
.createTextCursorByRange(xRange
)
598 xCursor
.gotoEndOfParagraph(True)
602 # FIXME: this does not account for inserted dummy characters!
603 class RangeInserter(Inserter
):
604 def __init__(self
, xDoc
):
605 super().__init
__(xDoc
)
608 # def inserttext(self, pos, text):
609 # self.xCursor.gotoStartOfParagraph(False)
610 # self.xCursor.goRight(pos, False)
611 # self.inserttext(self.xCursor, text)
613 def insertrange(self
, range):
614 self
.xCursor
.gotoStartOfParagraph(False)
615 self
.xCursor
.goRight(range.start
, False)
616 self
.xCursor
.goRight(range.extent
, True)
617 return self
.insertnode(self
.xCursor
, range.node
)
619 def insertnode(self
, xParaCursor
, node
):
620 nodetype
= node
.nodetype
621 if nodetype
== "Text":
623 self
.inserttext(xParaCursor
, text
.content
)
624 elif nodetype
== "Hyperlink":
626 self
.inserthyperlink(xParaCursor
, href
.url
)
627 elif nodetype
== "Ruby":
629 self
.insertruby(xParaCursor
, ruby
.ruby
)
630 elif nodetype
== "InContentMetadata":
632 return self
.insertmeta(xParaCursor
, meta
.xmlid
)
633 elif nodetype
== "MetadataField":
635 return self
.insertmetafield(xParaCursor
, meta
.xmlid
)
636 elif nodetype
== "Bookmark":
639 raise RuntimeError("range only")
640 self
.insertbookmark(xParaCursor
, bkmk
.name
, bkmk
.xmlid
)
641 elif nodetype
== "ReferenceMark":
644 raise RuntimeError("range only")
645 self
.insertreferencemark(xParaCursor
, mark
.name
)
646 elif nodetype
== "DocumentIndexMark":
649 raise RuntimeError("range only")
650 self
.insertdocumentindexmark(xParaCursor
, mark
.name
)
651 elif nodetype
== "TextField":
653 self
.inserttextfield(self
.xCursor
, field
.content
)
654 elif nodetype
== "Footnote":
656 self
.insertfootnote(self
.xCursor
, note
.label
)
657 elif nodetype
== "Frame":
659 self
.insertframe(xParaCursor
, frame
.name
, frame
.anchor
)
660 elif nodetype
== "ControlCharacter":
662 self
.insertcontrolcharacter(self
.xCursor
, cchar
.char
)
663 elif nodetype
== "SoftPageBreak":
664 raise RuntimeError("sorry, cannot test SoftPageBreak")
666 raise RuntimeError("unexpected nodetype: {}".format(nodetype
))
670 class EnumConverter():
675 def convert(self
, xEnum
):
677 self
._stack
.append(root
)
678 ret
= self
.convertchildren(xEnum
)
679 assert (len(self
._stack
)==0), "EnumConverter.convert: stack is not empty"
682 def convertchildren(self
, xEnum
):
683 for xPortion
in xEnum
:
684 type_
= xPortion
.TextPortionType
686 text
= xPortion
.getString()
687 node
= TextNode(text
)
688 url
= xPortion
.HyperLinkURL
691 node
= HyperlinkNode(url
)
692 node
.appendchild(temp
)
693 elif type_
== "TextField":
694 xField
= xPortion
.TextField
695 if xField
.supportsService("com.sun.star.text.textfield.MetadataField"):
696 xmlid
= xField
.MetadataReference
697 node
= MetaFieldNode(xmlid
)
698 self
._stack
.append(node
)
699 xEnumChildren
= xField
.createEnumeration()
700 node2
= self
.convertchildren(xEnumChildren
)
703 assert (node2
is node
), "stack error: meta-field"
705 content
= xField
.Content
706 isFixed
= xField
.IsFixed
707 assert isFixed
, "field not fixed?"
708 node
= TextFieldNode(content
)
709 elif type_
== "ControlCharacter":
710 c
= xPortion
.ControlCharacter
711 node
= ControlCharacterNode(c
)
712 elif type_
== "Footnote":
713 xFootnote
= xPortion
.Footnote
714 label
= xFootnote
.getLabel()
715 node
= FootnoteNode(label
)
716 elif type_
== "Frame":
717 xCEA
= xPortion
.createContentEnumeration('')
718 while xCEA
.hasMoreElements():
719 xFrame
= xCEA
.nextElement()
720 anchor
= xFrame
.AnchorType
721 name
= xFrame
.getName()
722 node
= FrameNode(name
, anchor
)
723 self
._stack
[-1].appendchild(node
)
725 elif type_
== "Bookmark":
726 xMark
= xPortion
.Bookmark
727 name
= xMark
.getName()
728 xmlid
= xMark
.MetadataReference
729 isCollapsed
= xPortion
.IsCollapsed
731 node
= BookmarkNode(name
, xmlid
)
733 isStart
= xPortion
.IsStart
735 node
= BookmarkStartNode(name
, xmlid
)
737 node
= BookmarkEndNode(name
, xmlid
)
738 elif type_
== "ReferenceMark":
739 xMark
= xPortion
.ReferenceMark
740 name
= xMark
.getName()
741 isCollapsed
= xPortion
.IsCollapsed
743 node
= ReferenceMarkNode(name
)
745 isStart
= xPortion
.IsStart
747 node
= ReferenceMarkStartNode(name
)
749 node
= ReferenceMarkEndNode(name
)
750 elif type_
== "DocumentIndexMark":
751 xMark
= xPortion
.DocumentIndexMark
752 name
= xMark
.PrimaryKey
753 isCollapsed
= xPortion
.IsCollapsed
755 node
= DocumentIndexMarkNode(name
)
757 isStart
= xPortion
.IsStart
759 node
= DocumentIndexMarkStartNode(name
)
761 node
= DocumentIndexMarkEndNode(name
)
762 elif type_
== "Ruby":
763 isStart
= xPortion
.IsStart
765 # ARRGH!!! stupid api...
766 # the text is ONLY at the start!
767 ruby
= xPortion
.RubyText
768 node
= RubyNode(ruby
)
769 self
._stack
.append(node
)
772 node
= self
._stack
.pop()
773 assert (isinstance(node
, RubyNode
)), "stack error: Ruby expected; is: {}".format(str(node
))
774 elif type_
== "InContentMetadata":
775 xMeta
= xPortion
.InContentMetadata
776 xmlid
= xMeta
.MetadataReference
777 node
= MetaNode(xmlid
)
778 self
._stack
.append(node
)
779 xEnumChildren
= xMeta
.createEnumeration()
780 node2
= self
.convertchildren(xEnumChildren
)
781 assert (node2
is node
), "stack error: meta"
782 elif type_
== "SoftPageBreak":
783 node
= SoftPageBreakNode()
785 raise RuntimeError("unexpected type: {}".format(type_
))
786 self
._stack
[-1].appendchild(node
)
787 ret
= self
._stack
.pop()
792 '''this is where we nail the pudding to the wall'''
797 self
.diffspuriousemptytext
= 0
798 self
.diffsequence
= 0 # ignored?
799 self
.stackexpected
= []
800 self
.stackactual
= []
801 self
.bufferexpected
= []
802 self
.bufferactual
= []
804 def dotest(self
, expected
, actual
):
805 '''idea: traverse both trees, enumerate nodes, stopping at content nodes.
806 then compare buffers.'''
807 assert "__ROOT__" == expected
.nodetype
808 assert "__ROOT__" == actual
.nodetype
809 self
.stackexpected
.append((expected
, expected
.createenumeration()))
810 self
.stackactual
.append((actual
, actual
.createenumeration()))
811 while self
.stackexpected
or self
.stackactual
:
812 self
.traverse(self
.stackexpected
, self
.bufferexpected
)
813 self
.traverse(self
.stackactual
, self
.bufferactual
)
815 if self
.diffsequence
:
816 print("warning: {} differences in sequence".format(
818 if self
.diffspuriousemptytext
:
819 print("warning: {} spurious empty text nodes".format(
820 self
.diffspuriousemptytext
))
822 print("WARNING: {} differences in nesting".format(
824 assert self
.diffcontent
== 0
825 assert self
.diffmissing
== 0
827 def traverse(self
, stack
, buffer):
829 topenum
= stack
[-1][1]
834 node_enum
= node
.createenumeration()
835 stack
.append((node
, node_enum
))
837 if not (isinstance(node
, TextNode
) and # spurious empty text?
838 len(node
.content
) == 0):
840 except StopIteration:
841 buffer.append(stack
[-1][0])
844 def testterminatingnode(self
):
845 lenexpected
= len(self
.bufferexpected
)
846 lenactual
= len(self
.bufferactual
)
847 if lenexpected
== 0 or lenactual
== 0:
849 expected
= self
.bufferexpected
[-1]
850 actual
= self
.bufferactual
[-1]
851 eroot
= expected
.nodetype
== "__ROOT__"
852 aroot
= actual
.nodetype
== "__ROOT__"
854 if not (eroot
and aroot
):
856 self
.printmissing(expected
)
858 self
.printunexpected(actual
)
859 self
.diffmissing
+= 1
861 self
.testcontentnode(expected
, actual
)
862 self
.bufferexpected
[-1] = None
863 self
.bufferactual
[-1] = None
865 def testcontentnode(self
, expected
, actual
):
866 contentexpected
= expected
.content
867 contentactual
= actual
.content
868 if expected
!= actual
:
869 self
.printdiff("text content differs", contentexpected
, contentactual
)
870 self
.diffcontent
+= 1
872 def testbuffer(self
):
873 lenactual
= len(self
.bufferactual
)
874 tmp_bufferactual
= self
.bufferactual
[:]
875 for i
, node
in enumerate(self
.bufferexpected
):
877 j
= tmp_bufferactual
.index(node
)
879 # FIXME how bad is this?
880 self
.printdiff("position differs", i
, j
)
883 max_
= max(min(lenactual
-1, i
),j
)
884 for k
in range(min_
, max_
):
885 tmp
= tmp_bufferactual
[k
]
886 if tmp
and tmp
.isnesting
:
887 self
.printnesting(node
, tmp
)
888 self
.diffnesting
+= 1
889 self
.diffsequence
+= 1
890 tmp_bufferactual
[j
] = None
893 self
.printmissing(node
)
894 self
.diffmissing
+= 1
895 for j
, node
in enumerate(tmp_bufferactual
):
897 self
.printunexpected(node
)
898 if isinstance(node
, TextNode
) and len(node
.content
) == 0:
899 self
.diffspuriousemptytext
+= 1
902 self
.diffmissing
+= 1
903 self
.testterminatingnode()
904 self
.bufferexpected
[:] = []
905 self
.bufferactual
[:] = []
907 def printdiff(self
, prefix
, expected
, actual
):
908 print("{}:\texpected: {}\tactual: {}".format(prefix
, expected
, actual
))
910 def printnesting(self
, node
, nesting
):
911 print("node: {} possibly moved across nesting {}".format(
912 str(node
), str(nesting
)))
914 def printmissing(self
, node
):
915 print(" missing node: {}".format(str(node
)))
917 def printunexpected(self
, node
):
918 print("unexpected node: {}".format(str(node
)))
921 class TextPortionEnumerationTest(unittest
.TestCase
):
929 cls
._uno
= UnoInProcess()
931 cls
.xDoc
= cls
._uno
.openEmptyWriterDoc()
935 def tearDownClass(cls
):
940 text
= TextNode("abc")
941 root
.appendchild(text
)
944 def test_text_field(self
):
947 txtf
= TextFieldNode("abc")
948 root
.appendchild(txtf
)
951 @unittest.skip("FIXME this is converted to a text portion: ControlCharacter is obsolete")
952 def test_control_char(self
):
954 cchr
= ControlCharacterNode(HARD_HYPHEN
)
955 root
.appendchild(cchr
)
958 @unittest.skip("FIXME: insert a soft page break: not done")
959 def test_soft_page_break(self
):
961 spbk
=SoftPageBreakNode()
962 text
= TextNode("abc")
963 root
.appendchild(spbk
)
964 root
.appendchild(text
)
967 def test_footnote(self
):
968 name
= self
.mkname("ftn")
970 ftnd
= FootnoteNode(name
)
971 root
.appendchild(ftnd
)
974 def test_frame_as(self
):
975 name
= self
.mkname("frame")
977 fram
= FrameNode(name
, AS_CHARACTER
)
978 root
.appendchild(fram
)
981 def test_frame_at(self
):
982 name
= self
.mkname("frame")
984 fram
= FrameNode(name
, AT_CHARACTER
)
985 root
.appendchild(fram
)
988 def test_bookmark_point(self
):
989 name
= self
.mkname("mark")
991 bkmk
= BookmarkNode(name
)
992 text
= TextNode("abc")
993 root
.appendchild(bkmk
)
994 root
.appendchild(text
)
997 def test_bookmark(self
):
998 name
= self
.mkname("mark")
1000 bkm1
= BookmarkStartNode(name
)
1001 text
= TextNode("abc")
1002 bkm2
= BookmarkEndNode(name
)
1003 root
.appendchild(bkm1
)
1004 root
.appendchild(text
)
1005 root
.appendchild(bkm2
)
1008 def test_bookmark_point_xmlid(self
):
1009 name
= self
.mkname("mark")
1010 id = self
.mkid("id")
1012 bkmk
= BookmarkNode(name
, id)
1013 text
= TextNode("abc")
1014 root
.appendchild(bkmk
)
1015 root
.appendchild(text
)
1018 def test_bookmark_xmlid(self
):
1019 name
= self
.mkname("mark")
1020 id = self
.mkid("id")
1022 bkm1
= BookmarkStartNode(name
, id)
1023 text
= TextNode("abc")
1024 bkm2
= BookmarkEndNode(name
, id)
1025 root
.appendchild(bkm1
)
1026 root
.appendchild(text
)
1027 root
.appendchild(bkm2
)
1030 def test_refmark_point(self
):
1031 name
= self
.mkname("refmark")
1033 rfmk
= ReferenceMarkNode(name
)
1034 text
= TextNode("abc")
1035 root
.appendchild(rfmk
)
1036 root
.appendchild(text
)
1039 def test_refmark(self
):
1040 name
= self
.mkname("refmark")
1042 rfm1
= ReferenceMarkStartNode(name
)
1043 text
= TextNode("abc")
1044 rfm2
= ReferenceMarkEndNode(name
)
1045 root
.appendchild(rfm1
)
1046 root
.appendchild(text
)
1047 root
.appendchild(rfm2
)
1050 def test_toxmark_point(self
):
1051 name
= self
.mkname("toxmark")
1053 txmk
= DocumentIndexMarkNode(name
)
1054 text
= TextNode("abc")
1055 root
.appendchild(txmk
)
1056 root
.appendchild(text
)
1059 def test_toxmark(self
):
1060 name
= self
.mkname("toxmark")
1062 txm1
= DocumentIndexMarkStartNode(name
)
1063 text
= TextNode("abc")
1064 txm2
= DocumentIndexMarkEndNode(name
)
1065 root
.appendchild(txm1
)
1066 root
.appendchild(text
)
1067 root
.appendchild(txm2
)
1070 def test_hyperlink(self
):
1071 name
= self
.mkname("url")
1073 href
= HyperlinkNode(name
)
1074 text
= TextNode("abc")
1075 href
.appendchild(text
)
1076 root
.appendchild(href
)
1079 def test_hyperlink_empty(self
):
1080 name
= self
.mkname("url")
1082 href
= HyperlinkNode(name
)
1084 href
.appendchild(text
)
1085 root
.appendchild(href
)
1088 def test_ruby(self
):
1089 name
= self
.mkname("ruby")
1091 ruby
= RubyNode(name
)
1092 text
= TextNode("abc")
1093 ruby
.appendchild(text
)
1094 root
.appendchild(ruby
)
1097 def test_ruby_empty(self
):
1099 name
= self
.mkname("ruby")
1101 ruby
= RubyNode(name
)
1102 root
.appendchild(ruby
)
1105 def test_meta(self
):
1106 id = StringPair("content.xml", self
.mkname("id"))
1109 text
= TextNode("abc")
1110 root
.appendchild(TextNode("123"))
1111 meta
.appendchild(text
)
1112 root
.appendchild(meta
)
1115 def test_meta_empty(self
):
1116 id = StringPair("content.xml", self
.mkname("id"))
1119 root
.appendchild(meta
)
1122 def test_meta_field(self
):
1123 id = StringPair("content.xml", self
.mkname("id"))
1125 meta
= MetaFieldNode(id)
1126 text
= TextNode("abc")
1127 root
.appendchild(TextNode("123"))
1128 meta
.appendchild(text
)
1129 root
.appendchild(meta
)
1132 def test_meta_field_empty(self
):
1133 id = StringPair("content.xml", self
.mkname("id"))
1135 meta
= MetaFieldNode(id)
1136 root
.appendchild(meta
)
1139 def test_bookmark1(self
):
1140 name1
= self
.mkname("mark")
1141 name2
= self
.mkname("mark")
1142 name3
= self
.mkname("mark")
1144 root
.appendchild(BookmarkStartNode(name1
))
1145 root
.appendchild(BookmarkNode(name2
))
1146 root
.appendchild(BookmarkStartNode(name3
))
1147 root
.appendchild(TextNode("abc"))
1148 root
.appendchild(BookmarkEndNode(name1
))
1149 root
.appendchild(TextNode("de"))
1150 root
.appendchild(BookmarkEndNode(name3
))
1153 def test_bookmark2(self
):
1154 name1
= self
.mkname("mark")
1155 name2
= self
.mkname("mark")
1156 name3
= self
.mkname("mark")
1158 root
.appendchild(BookmarkStartNode(name1
))
1159 root
.appendchild(TextNode("abc"))
1160 root
.appendchild(BookmarkNode(name2
))
1161 root
.appendchild(BookmarkStartNode(name3
))
1162 root
.appendchild(BookmarkEndNode(name1
))
1163 root
.appendchild(TextNode("de"))
1164 root
.appendchild(BookmarkEndNode(name3
))
1167 def test_refmark2(self
):
1168 name1
= self
.mkname("refmark")
1170 root
.appendchild(ReferenceMarkStartNode(name1
))
1171 root
.appendchild(TextNode("abc"))
1172 # BUG: #i102541# (this is actually not unoportenum's fault)
1173 root
.appendchild(ReferenceMarkEndNode(name1
))
1174 root
.appendchild(TextNode("de"))
1177 def test_refmark3(self
):
1178 # BUG: #i107672# (non-deterministic; depends on pointer ordering)
1179 name1
= self
.mkname("refmark")
1180 name2
= self
.mkname("refmark")
1181 name3
= self
.mkname("refmark")
1182 name4
= self
.mkname("refmark")
1183 name5
= self
.mkname("refmark")
1184 name6
= self
.mkname("refmark")
1185 name7
= self
.mkname("refmark")
1187 root
.appendchild(ReferenceMarkStartNode(name1
))
1188 root
.appendchild(ReferenceMarkStartNode(name2
))
1189 root
.appendchild(ReferenceMarkStartNode(name3
))
1190 root
.appendchild(ReferenceMarkStartNode(name4
))
1191 root
.appendchild(ReferenceMarkStartNode(name5
))
1192 root
.appendchild(ReferenceMarkStartNode(name6
))
1193 root
.appendchild(ReferenceMarkStartNode(name7
))
1194 root
.appendchild(TextNode("abc"))
1195 root
.appendchild(ReferenceMarkEndNode(name7
))
1196 root
.appendchild(ReferenceMarkEndNode(name6
))
1197 root
.appendchild(ReferenceMarkEndNode(name5
))
1198 root
.appendchild(ReferenceMarkEndNode(name4
))
1199 root
.appendchild(ReferenceMarkEndNode(name3
))
1200 root
.appendchild(ReferenceMarkEndNode(name2
))
1201 root
.appendchild(ReferenceMarkEndNode(name1
))
1202 root
.appendchild(TextNode("de"))
1205 def test_toxmark2(self
):
1206 name1
= self
.mkname("toxmark")
1208 root
.appendchild(DocumentIndexMarkStartNode(name1
))
1209 root
.appendchild(TextNode("abc"))
1210 root
.appendchild(DocumentIndexMarkEndNode(name1
))
1211 root
.appendchild(TextNode("de"))
1214 def test_toxmark3(self
):
1215 # BUG: #i107672# (non-deterministic; depends on pointer ordering)
1216 name1
= self
.mkname("toxmark")
1217 name2
= self
.mkname("toxmark")
1218 name3
= self
.mkname("toxmark")
1219 name4
= self
.mkname("toxmark")
1220 name5
= self
.mkname("toxmark")
1221 name6
= self
.mkname("toxmark")
1222 name7
= self
.mkname("toxmark")
1224 root
.appendchild(DocumentIndexMarkStartNode(name1
))
1225 root
.appendchild(DocumentIndexMarkStartNode(name2
))
1226 root
.appendchild(DocumentIndexMarkStartNode(name3
))
1227 root
.appendchild(DocumentIndexMarkStartNode(name4
))
1228 root
.appendchild(DocumentIndexMarkStartNode(name5
))
1229 root
.appendchild(DocumentIndexMarkStartNode(name6
))
1230 root
.appendchild(DocumentIndexMarkStartNode(name7
))
1231 root
.appendchild(TextNode("abc"))
1232 root
.appendchild(DocumentIndexMarkEndNode(name7
))
1233 root
.appendchild(DocumentIndexMarkEndNode(name6
))
1234 root
.appendchild(DocumentIndexMarkEndNode(name5
))
1235 root
.appendchild(DocumentIndexMarkEndNode(name4
))
1236 root
.appendchild(DocumentIndexMarkEndNode(name3
))
1237 root
.appendchild(DocumentIndexMarkEndNode(name2
))
1238 root
.appendchild(DocumentIndexMarkEndNode(name1
))
1239 root
.appendchild(TextNode("de"))
1242 def test_marks1(self
):
1243 name1
= self
.mkname("bookmark")
1244 name2
= self
.mkname("toxmark")
1245 name3
= self
.mkname("refmark")
1246 name4
= self
.mkname("toxmark")
1248 root
.appendchild(BookmarkStartNode(name1
))
1249 root
.appendchild(DocumentIndexMarkNode(name2
))
1250 root
.appendchild(ReferenceMarkStartNode(name3
))
1251 root
.appendchild(TextNode("abc"))
1252 root
.appendchild(BookmarkEndNode(name1
))
1253 root
.appendchild(DocumentIndexMarkStartNode(name4
))
1254 root
.appendchild(TextNode("de"))
1255 root
.appendchild(DocumentIndexMarkEndNode(name4
))
1256 root
.appendchild(ReferenceMarkEndNode(name3
))
1259 def test_marks2(self
):
1260 name1
= self
.mkname("bookmark")
1261 name2
= self
.mkname("refmark")
1262 name3
= self
.mkname("refmark")
1263 name4
= self
.mkname("toxmark")
1264 name5
= self
.mkname("refmark")
1266 root
.appendchild(BookmarkStartNode(name1
))
1267 root
.appendchild(ReferenceMarkNode(name2
))
1268 root
.appendchild(ReferenceMarkStartNode(name3
))
1269 root
.appendchild(TextNode("abc"))
1270 root
.appendchild(DocumentIndexMarkStartNode(name4
))
1271 root
.appendchild(ReferenceMarkStartNode(name5
))
1272 # BUG: #i102541# (this is actually not unoportenum's fault)
1273 root
.appendchild(ReferenceMarkEndNode(name3
))
1274 root
.appendchild(TextNode("de"))
1275 root
.appendchild(DocumentIndexMarkEndNode(name4
))
1276 root
.appendchild(BookmarkEndNode(name1
))
1277 root
.appendchild(ReferenceMarkEndNode(name5
))
1280 def test_marks3(self
):
1281 name1
= self
.mkname("bookmark")
1282 name2
= self
.mkname("refmark")
1283 name3
= self
.mkname("refmark")
1284 name4
= self
.mkname("toxmark")
1285 name5
= self
.mkname("refmark")
1287 root
.appendchild(BookmarkStartNode(name1
))
1288 root
.appendchild(DocumentIndexMarkNode(name2
))
1289 root
.appendchild(DocumentIndexMarkStartNode(name3
))
1290 root
.appendchild(TextNode("abc"))
1291 root
.appendchild(ReferenceMarkStartNode(name4
))
1292 root
.appendchild(DocumentIndexMarkStartNode(name5
))
1293 root
.appendchild(DocumentIndexMarkEndNode(name3
))
1294 root
.appendchild(TextNode("de"))
1295 root
.appendchild(ReferenceMarkEndNode(name4
))
1296 root
.appendchild(BookmarkEndNode(name1
))
1297 root
.appendchild(DocumentIndexMarkEndNode(name5
))
1300 def test_frame_mark1(self
):
1301 name1
= self
.mkname("bookmark")
1302 name2
= self
.mkname("frame")
1304 root
.appendchild(TextNode("abc"))
1305 root
.appendchild(BookmarkNode(name1
))
1306 root
.appendchild(TextNode("de"))
1307 root
.appendchild(FrameNode(name2
, AS_CHARACTER
))
1310 def test_frame_mark2(self
):
1312 name1
= self
.mkname("bookmark")
1313 name2
= self
.mkname("frame")
1315 root
.appendchild(TextNode("abc"))
1316 root
.appendchild(BookmarkNode(name1
))
1317 root
.appendchild(TextNode("de"))
1318 root
.appendchild(FrameNode(name2
, AT_CHARACTER
))
1321 def test_frame_mark3(self
):
1322 name1
= self
.mkname("frame")
1323 name2
= self
.mkname("bookmark")
1325 root
.appendchild(TextNode("abc"))
1326 root
.appendchild(FrameNode(name1
, AS_CHARACTER
))
1327 root
.appendchild(TextNode("de"))
1328 root
.appendchild(BookmarkNode(name2
))
1331 def test_frame_mark4(self
):
1332 name1
= self
.mkname("frame")
1333 name2
= self
.mkname("bookmark")
1335 root
.appendchild(TextNode("abc"))
1336 root
.appendchild(FrameNode(name1
, AT_CHARACTER
))
1337 root
.appendchild(TextNode("de"))
1338 root
.appendchild(BookmarkNode(name2
))
1341 def test_frames1(self
):
1342 name1
= self
.mkname("frame")
1343 name2
= self
.mkname("frame")
1344 name3
= self
.mkname("frame")
1346 root
.appendchild(FrameNode(name1
, AT_CHARACTER
))
1347 root
.appendchild(FrameNode(name2
, AT_CHARACTER
))
1348 root
.appendchild(FrameNode(name3
, AT_CHARACTER
))
1351 def test_frames2(self
):
1352 name1
= self
.mkname("frame")
1353 name2
= self
.mkname("frame")
1354 name3
= self
.mkname("frame")
1356 root
.appendchild(FrameNode(name1
, AS_CHARACTER
))
1357 root
.appendchild(FrameNode(name2
, AS_CHARACTER
))
1358 root
.appendchild(FrameNode(name3
, AS_CHARACTER
))
1361 def test_frames3(self
):
1362 name1
= self
.mkname("frame")
1363 name2
= self
.mkname("frame")
1364 name3
= self
.mkname("frame")
1366 root
.appendchild(FrameNode(name1
, AT_CHARACTER
))
1367 root
.appendchild(FrameNode(name2
, AS_CHARACTER
))
1368 root
.appendchild(FrameNode(name3
, AT_CHARACTER
))
1371 def test_frames4(self
):
1372 name1
= self
.mkname("frame")
1373 name2
= self
.mkname("frame")
1374 name3
= self
.mkname("frame")
1376 root
.appendchild(FrameNode(name1
, AT_CHARACTER
))
1377 root
.appendchild(FrameNode(name2
, AT_CHARACTER
))
1378 root
.appendchild(FrameNode(name3
, AS_CHARACTER
))
1381 def test_frames5(self
):
1382 name1
= self
.mkname("frame")
1383 name2
= self
.mkname("frame")
1384 name3
= self
.mkname("frame")
1386 root
.appendchild(FrameNode(name1
, AS_CHARACTER
))
1387 root
.appendchild(FrameNode(name2
, AT_CHARACTER
))
1388 root
.appendchild(FrameNode(name3
, AT_CHARACTER
))
1391 def test_ruby_hyperlink1(self
):
1392 name1
= self
.mkname("ruby")
1393 name2
= self
.mkname("url")
1395 ruby
= RubyNode(name1
)
1396 href
= HyperlinkNode(name2
)
1397 href
.appendchild(TextNode("abc"))
1398 ruby
.appendchild(href
)
1399 root
.appendchild(ruby
)
1402 def test_ruby_hyperlink2(self
):
1403 name1
= self
.mkname("url")
1404 name2
= self
.mkname("ruby")
1406 href
= HyperlinkNode(name1
)
1407 ruby
= RubyNode(name2
)
1408 ruby
.appendchild(TextNode("abc"))
1409 href
.appendchild(ruby
)
1410 root
.appendchild(href
)
1413 def test_end1(self
):
1414 name1
= self
.mkname("bookmark")
1415 name2
= self
.mkname("toxmark")
1416 name3
= self
.mkname("refmark")
1418 root
.appendchild(TextNode("abc"))
1419 root
.appendchild(BookmarkNode(name1
))
1420 root
.appendchild(DocumentIndexMarkNode(name2
))
1421 root
.appendchild(ReferenceMarkNode(name3
))
1424 def test_end2(self
):
1425 name1
= self
.mkname("bookmark")
1426 name2
= self
.mkname("frame")
1427 name3
= self
.mkname("refmark")
1428 name4
= self
.mkname("frame")
1429 name5
= self
.mkname("frame")
1431 root
.appendchild(TextNode("abc"))
1432 root
.appendchild(BookmarkStartNode(name1
))
1433 root
.appendchild(FrameNode(name2
, AT_CHARACTER
))
1434 root
.appendchild(BookmarkEndNode(name1
))
1435 root
.appendchild(ReferenceMarkNode(name3
))
1436 root
.appendchild(FrameNode(name4
, AT_CHARACTER
))
1437 root
.appendchild(FrameNode(name5
, AT_CHARACTER
))
1440 def test_end3(self
):
1441 name1
= self
.mkname("ftn")
1442 name2
= self
.mkname("toxmark")
1444 root
.appendchild(TextNode("abc"))
1445 root
.appendchild(FootnoteNode(name1
))
1446 root
.appendchild(DocumentIndexMarkNode(name2
))
1449 def test_end4(self
):
1450 name1
= self
.mkname("bookmark")
1451 name2
= self
.mkname("frame")
1453 root
.appendchild(BookmarkStartNode(name1
))
1454 root
.appendchild(TextNode("abc"))
1455 root
.appendchild(FrameNode(name2
, AS_CHARACTER
))
1456 root
.appendchild(BookmarkEndNode(name1
))
1459 def test_end5(self
):
1460 name1
= self
.mkname("refmark")
1461 name2
= self
.mkname("ruby")
1463 root
.appendchild(ReferenceMarkStartNode(name1
))
1464 root
.appendchild(TextNode("abc"))
1465 ruby
= RubyNode(name2
)
1466 ruby
.appendchild(TextFieldNode("de"))
1467 root
.appendchild(ruby
)
1468 root
.appendchild(ReferenceMarkEndNode(name1
))
1471 def test_empty1(self
):
1472 name1
= self
.mkname("refmark")
1473 name2
= self
.mkname("toxmark")
1474 name3
= self
.mkname("bookmark")
1475 name4
= self
.mkname("frame")
1476 name7
= self
.mkname("refmark")
1477 name8
= self
.mkname("toxmark")
1478 name9
= self
.mkname("bookmark")
1479 nameA
= self
.mkname("frame")
1481 root
.appendchild(ReferenceMarkNode(name1
))
1482 root
.appendchild(DocumentIndexMarkNode(name2
))
1483 root
.appendchild(BookmarkStartNode(name3
))
1484 root
.appendchild(FrameNode(name4
, AT_CHARACTER
))
1485 root
.appendchild(BookmarkEndNode(name3
))
1486 root
.appendchild(ReferenceMarkNode(name7
))
1487 root
.appendchild(DocumentIndexMarkNode(name8
))
1488 root
.appendchild(BookmarkStartNode(name9
))
1489 root
.appendchild(FrameNode(nameA
, AT_CHARACTER
))
1490 root
.appendchild(BookmarkEndNode(name9
))
1493 def test_empty2(self
):
1494 name3
= self
.mkname("bookmark")
1495 name4
= self
.mkname("frame")
1496 name9
= self
.mkname("bookmark")
1497 nameA
= self
.mkname("frame")
1499 root
.appendchild(BookmarkStartNode(name3
))
1500 root
.appendchild(FrameNode(name4
, AT_CHARACTER
))
1501 root
.appendchild(BookmarkEndNode(name3
))
1502 root
.appendchild(BookmarkStartNode(name9
))
1503 root
.appendchild(FrameNode(nameA
, AT_CHARACTER
))
1504 root
.appendchild(BookmarkEndNode(name9
))
1507 def test_empty3(self
):
1508 name1
= self
.mkname("refmark")
1509 name2
= self
.mkname("toxmark")
1510 name3
= self
.mkname("bookmark")
1511 name4
= self
.mkname("frame")
1512 name5
= self
.mkname("url")
1513 name6
= self
.mkname("ruby")
1514 name7
= self
.mkname("refmark")
1515 name8
= self
.mkname("toxmark")
1516 name9
= self
.mkname("bookmark")
1517 nameA
= self
.mkname("frame")
1519 root
.appendchild(ReferenceMarkNode(name1
))
1520 root
.appendchild(DocumentIndexMarkNode(name2
))
1521 root
.appendchild(BookmarkStartNode(name3
))
1522 root
.appendchild(FrameNode(name4
, AT_CHARACTER
))
1523 root
.appendchild(BookmarkEndNode(name3
))
1524 ## currently empty hyperlinks may get eaten...
1525 # href = HyperlinkNode(name5)
1526 # href.appendchild(TextNode(""))
1527 # root.appendchild(href)
1528 ruby
= RubyNode(name6
)
1529 root
.appendchild(ruby
)
1530 root
.appendchild(ReferenceMarkNode(name7
))
1531 root
.appendchild(DocumentIndexMarkNode(name8
))
1532 root
.appendchild(BookmarkStartNode(name9
))
1533 root
.appendchild(FrameNode(nameA
, AT_CHARACTER
))
1534 root
.appendchild(BookmarkEndNode(name9
))
1538 name1
= self
.mkname("frame")
1539 name2
= self
.mkname("bookmark")
1540 name3
= self
.mkname("ruby")
1541 name4
= self
.mkname("ftn")
1542 name5
= self
.mkname("frame")
1544 root
.appendchild(FrameNode(name1
, AT_CHARACTER
))
1545 root
.appendchild(BookmarkStartNode(name2
))
1546 root
.appendchild(TextNode("abc"))
1547 ruby
= RubyNode(name3
)
1548 ruby
.appendchild(TextNode("de"))
1549 ruby
.appendchild(FootnoteNode(name4
))
1550 ruby
.appendchild(BookmarkEndNode(name2
))
1551 root
.appendchild(ruby
)
1552 root
.appendchild(TextNode("fg"))
1553 root
.appendchild(FrameNode(name5
, AT_CHARACTER
))
1554 root
.appendchild(TextFieldNode("h"))
1557 # some range tests for the insertion: these are for the current
1558 # API which treats hyperlinks and rubys not as entities, but as formatting
1559 # attributes; if these ever become entities, they should not be split!'''
1561 def test_range1(self
):
1562 name1
= self
.mkname("url")
1563 inserter
= RangeInserter(self
.__class
__.xDoc
)
1564 text
= TextNode("12345")
1565 inserter
.insertrange(Range(0, 0, text
))
1566 url1
= HyperlinkNode(name1
)
1567 range1
= Range(0, 5, url1
)
1568 inserter
.insertrange(range1
)
1570 root
.appendchild(url1
)
1571 url1
.appendchild(text
)
1572 self
.dotest(root
, False)
1574 def test_range_hyperlink_hyperlink(self
):
1575 inserter
= RangeInserter(self
.__class
__.xDoc
)
1576 text
= TextNode("123456789")
1577 inserter
.insertrange(Range(0, 0, text
))
1578 url1
= HyperlinkNode(self
.mkname("url"))
1579 inserter
.insertrange(Range(1, 4, url1
))
1581 url2
= HyperlinkNode(self
.mkname("url"))
1582 inserter
.insertrange(Range(0, 2, url2
))
1584 root
.appendchild(url2
.dup().appendchild(TextNode("12")))
1585 root
.appendchild(url1
.dup().appendchild(TextNode("34")))
1586 root
.appendchild(TextNode("56789"))
1587 self
.dotest(root
, False)
1589 url3
= HyperlinkNode(self
.mkname("url"))
1590 inserter
.insertrange(Range(3, 7, url3
))
1592 root
.appendchild(url2
.dup().appendchild(TextNode("12")))
1593 root
.appendchild(url1
.dup().appendchild(TextNode("3")))
1594 root
.appendchild(url3
.dup().appendchild(TextNode("4567")))
1595 root
.appendchild(TextNode("89"))
1596 self
.dotest(root
, False)
1598 url4
= HyperlinkNode(self
.mkname("url"))
1599 inserter
.insertrange(Range(3, 7, url4
))
1601 root
.appendchild(url2
.dup().appendchild(TextNode("12")))
1602 root
.appendchild(url1
.dup().appendchild(TextNode("3")))
1603 root
.appendchild(url4
.dup().appendchild(TextNode("4567")))
1604 root
.appendchild(TextNode("89"))
1605 self
.dotest(root
, False)
1607 url5
= HyperlinkNode(self
.mkname("url"))
1608 inserter
.insertrange(Range(4, 6, url5
))
1610 root
.appendchild(url2
.dup().appendchild(TextNode("12")))
1611 root
.appendchild(url1
.dup().appendchild(TextNode("3")))
1612 root
.appendchild(url4
.dup().appendchild(TextNode("4")))
1613 root
.appendchild(url5
.dup().appendchild(TextNode("56")))
1614 root
.appendchild(url4
.dup().appendchild(TextNode("7")))
1615 root
.appendchild(TextNode("89"))
1616 self
.dotest(root
, False)
1618 url6
= HyperlinkNode(self
.mkname("url"))
1619 inserter
.insertrange(Range(7, 7, url6
))
1621 root
.appendchild(url2
.dup().appendchild(TextNode("12")))
1622 root
.appendchild(url1
.dup().appendchild(TextNode("3")))
1623 root
.appendchild(url4
.dup().appendchild(TextNode("4")))
1624 root
.appendchild(url5
.dup().appendchild(TextNode("56")))
1625 root
.appendchild(url4
.dup().appendchild(TextNode("7")))
1626 ## this one gets eaten, but we still need to test inserting it (#i106930#)
1627 # root.appendchild(url6.dup().appendchild(TextNode("")))
1628 root
.appendchild(TextNode("89"))
1629 ## inside (left-edge)
1630 url7
= HyperlinkNode(self
.mkname("url"))
1631 inserter
.insertrange(Range(0, 1, url7
))
1633 root
.appendchild(url7
.dup().appendchild(TextNode("1")))
1634 root
.appendchild(url2
.dup().appendchild(TextNode("2")))
1635 root
.appendchild(url1
.dup().appendchild(TextNode("3")))
1636 root
.appendchild(url4
.dup().appendchild(TextNode("4")))
1637 root
.appendchild(url5
.dup().appendchild(TextNode("56")))
1638 root
.appendchild(url4
.dup().appendchild(TextNode("7")))
1639 root
.appendchild(TextNode("89"))
1640 ## inside (right-edge)
1641 url8
= HyperlinkNode(self
.mkname("url"))
1642 inserter
.insertrange(Range(5, 6, url8
))
1644 root
.appendchild(url7
.dup().appendchild(TextNode("1")))
1645 root
.appendchild(url2
.dup().appendchild(TextNode("2")))
1646 root
.appendchild(url1
.dup().appendchild(TextNode("3")))
1647 root
.appendchild(url4
.dup().appendchild(TextNode("4")))
1648 root
.appendchild(url5
.dup().appendchild(TextNode("5")))
1649 root
.appendchild(url8
.dup().appendchild(TextNode("6")))
1650 root
.appendchild(url4
.dup().appendchild(TextNode("7")))
1651 root
.appendchild(TextNode("89"))
1652 self
.dotest(root
, False)
1654 def test_range_hyperlink_ruby(self
):
1655 inserter
= RangeInserter(self
.__class
__.xDoc
)
1656 text
= TextNode("123456789")
1657 inserter
.insertrange(Range(0, 0, text
))
1658 url1
= HyperlinkNode(self
.mkname("url"))
1659 inserter
.insertrange(Range(1, 4, url1
))
1661 rby2
= RubyNode(self
.mkname("ruby"))
1662 inserter
.insertrange(Range(0, 2, rby2
))
1664 root
.appendchild(rby2
.dup()
1665 .appendchild(TextNode("1"))
1666 .appendchild(url1
.dup().appendchild(TextNode("2"))))
1667 root
.appendchild(url1
.dup().appendchild(TextNode("34")))
1668 root
.appendchild(TextNode("56789"))
1669 self
.dotest(root
, False)
1671 rby3
= RubyNode(self
.mkname("ruby"))
1672 inserter
.insertrange(Range(3, 5, rby3
))
1674 root
.appendchild(rby2
.dup()
1675 .appendchild(TextNode("1"))
1676 .appendchild(url1
.dup().appendchild(TextNode("2"))))
1677 root
.appendchild(url1
.dup().appendchild(TextNode("3")))
1678 root
.appendchild(rby3
.dup()
1679 .appendchild(url1
.dup().appendchild(TextNode("4")))
1680 .appendchild(TextNode("5")))
1681 root
.appendchild(TextNode("6789"))
1682 self
.dotest(root
, False)
1684 rby4
= RubyNode(self
.mkname("ruby"))
1685 inserter
.insertrange(Range(2, 3, rby4
))
1687 root
.appendchild(rby2
.dup()
1688 .appendchild(TextNode("1"))
1689 .appendchild(url1
.dup().appendchild(TextNode("2"))))
1690 root
.appendchild(rby4
.dup()
1691 .appendchild(url1
.dup().appendchild(TextNode("3"))))
1692 root
.appendchild(rby3
.dup()
1693 .appendchild(url1
.dup().appendchild(TextNode("4")))
1694 .appendchild(TextNode("5")))
1695 root
.appendchild(TextNode("6789"))
1696 self
.dotest(root
, False)
1698 url5
= HyperlinkNode(self
.mkname("url"))
1699 inserter
.insertrange(Range(6, 9, url5
))
1700 rby6
= RubyNode(self
.mkname("ruby"))
1701 inserter
.insertrange(Range(7, 8, rby6
))
1703 root
.appendchild(rby2
.dup()
1704 .appendchild(TextNode("1"))
1705 .appendchild(url1
.dup().appendchild(TextNode("2"))))
1706 root
.appendchild(rby4
.dup()
1707 .appendchild(url1
.dup().appendchild(TextNode("3"))))
1708 root
.appendchild(rby3
.dup()
1709 .appendchild(url1
.dup().appendchild(TextNode("4")))
1710 .appendchild(TextNode("5")))
1711 root
.appendchild(TextNode("6"))
1712 root
.appendchild(url5
.dup().appendchild(TextNode("7")))
1713 root
.appendchild(rby6
.dup()
1714 .appendchild(url5
.dup().appendchild(TextNode("8"))))
1715 root
.appendchild(url5
.dup().appendchild(TextNode("9")))
1716 self
.dotest(root
, False)
1718 def test_range_ruby_hyperlink(self
):
1719 inserter
= RangeInserter(self
.__class
__.xDoc
)
1720 text
= TextNode("123456789")
1721 inserter
.insertrange(Range(0, 0, text
))
1722 rby1
= RubyNode(self
.mkname("ruby"))
1723 inserter
.insertrange(Range(1, 6, rby1
))
1725 url2
= HyperlinkNode(self
.mkname("url"))
1726 inserter
.insertrange(Range(0, 3, url2
))
1728 root
.appendchild(url2
.dup().appendchild(TextNode("1")))
1729 root
.appendchild(rby1
.dup()
1730 .appendchild(url2
.dup().appendchild(TextNode("23")))
1731 .appendchild(TextNode("456")))
1732 root
.appendchild(TextNode("789"))
1733 self
.dotest(root
, False)
1735 url3
= HyperlinkNode(self
.mkname("url"))
1736 inserter
.insertrange(Range(5, 7, url3
))
1738 root
.appendchild(url2
.dup().appendchild(TextNode("1")))
1739 root
.appendchild(rby1
.dup()
1740 .appendchild(url2
.dup().appendchild(TextNode("23")))
1741 .appendchild(TextNode("45"))
1742 .appendchild(url3
.dup().appendchild(TextNode("6"))))
1743 root
.appendchild(url3
.dup().appendchild(TextNode("7")))
1744 root
.appendchild(TextNode("89"))
1745 self
.dotest(root
, False)
1746 ## around (not quite, due to API)
1747 url4
= HyperlinkNode(self
.mkname("url"))
1748 inserter
.insertrange(Range(1, 8, url4
))
1750 root
.appendchild(url2
.dup().appendchild(TextNode("1")))
1751 root
.appendchild(rby1
.dup()
1752 .appendchild(url4
.dup()
1753 .appendchild(TextNode("23456"))))
1754 root
.appendchild(url4
.dup().appendchild(TextNode("78")))
1755 root
.appendchild(TextNode("9"))
1756 self
.dotest(root
, False)
1758 url5
= HyperlinkNode(self
.mkname("url"))
1759 inserter
.insertrange(Range(3, 5, url5
))
1761 root
.appendchild(url2
.dup().appendchild(TextNode("1")))
1762 root
.appendchild(rby1
.dup()
1763 .appendchild(url4
.dup()
1764 .appendchild(TextNode("23")))
1765 .appendchild(url5
.dup()
1766 .appendchild(TextNode("45")))
1767 .appendchild(url4
.dup()
1768 .appendchild(TextNode("6"))))
1769 root
.appendchild(url4
.dup().appendchild(TextNode("78")))
1770 root
.appendchild(TextNode("9"))
1771 self
.dotest(root
, False)
1773 def test_range_ruby_ruby(self
):
1774 inserter
= RangeInserter(self
.__class
__.xDoc
)
1775 text
= TextNode("123456789")
1776 inserter
.insertrange(Range(0, 0, text
))
1777 rby1
= RubyNode(self
.mkname("ruby"))
1778 inserter
.insertrange(Range(1, 4, rby1
))
1780 rby2
= RubyNode(self
.mkname("ruby"))
1781 inserter
.insertrange(Range(0, 2, rby2
))
1783 root
.appendchild(rby2
.dup().appendchild(TextNode("12")))
1784 root
.appendchild(rby1
.dup().appendchild(TextNode("34")))
1785 root
.appendchild(TextNode("56789"))
1786 self
.dotest(root
, False)
1788 rby3
= RubyNode(self
.mkname("ruby"))
1789 inserter
.insertrange(Range(3, 7, rby3
))
1791 root
.appendchild(rby2
.dup().appendchild(TextNode("12")))
1792 root
.appendchild(rby1
.dup().appendchild(TextNode("3")))
1793 root
.appendchild(rby3
.dup().appendchild(TextNode("4567")))
1794 root
.appendchild(TextNode("89"))
1795 self
.dotest(root
, False)
1797 rby4
= RubyNode(self
.mkname("ruby"))
1798 inserter
.insertrange(Range(3, 7, rby4
))
1800 root
.appendchild(rby2
.dup().appendchild(TextNode("12")))
1801 root
.appendchild(rby1
.dup().appendchild(TextNode("3")))
1802 root
.appendchild(rby4
.dup().appendchild(TextNode("4567")))
1803 root
.appendchild(TextNode("89"))
1804 self
.dotest(root
, False)
1806 rby5
= RubyNode(self
.mkname("ruby"))
1807 inserter
.insertrange(Range(4, 6, rby5
))
1809 root
.appendchild(rby2
.dup().appendchild(TextNode("12")))
1810 root
.appendchild(rby1
.dup().appendchild(TextNode("3")))
1811 root
.appendchild(rby4
.dup().appendchild(TextNode("4")))
1812 root
.appendchild(rby5
.dup().appendchild(TextNode("56")))
1813 root
.appendchild(rby4
.dup().appendchild(TextNode("7")))
1814 root
.appendchild(TextNode("89"))
1815 self
.dotest(root
, False)
1817 def test_range_hyperlink_meta(self
):
1818 inserter
= RangeInserter(self
.__class
__.xDoc
)
1819 text
= TextNode("123456789")
1820 inserter
.insertrange(Range(0, 0, text
))
1821 url1
= HyperlinkNode(self
.mkname("url"))
1822 inserter
.insertrange(Range(1, 4, url1
))
1824 met2
= MetaNode(self
.mkid("id"))
1825 inserter
.insertrange(Range(0, 2, met2
))
1827 root
.appendchild(met2
.dup()
1828 .appendchild(TextNode("1"))
1829 .appendchild(url1
.dup().appendchild(TextNode("2"))))
1830 root
.appendchild(url1
.dup().appendchild(TextNode("34")))
1831 root
.appendchild(TextNode("56789"))
1832 self
.dotest(root
, False)
1834 met3
= MetaNode(self
.mkid("id"))
1835 # inserter.insertrange(Range(4-1, 6-1, met3))
1836 inserter
.insertrange(Range(4, 6, met3
))
1838 root
.appendchild(met2
.dup()
1839 .appendchild(TextNode("1"))
1840 .appendchild(url1
.dup().appendchild(TextNode("2"))))
1841 root
.appendchild(url1
.dup().appendchild(TextNode("3")))
1842 root
.appendchild(met3
.dup()
1843 .appendchild(url1
.dup().appendchild(TextNode("4")))
1844 .appendchild(TextNode("5")))
1845 root
.appendchild(TextNode("6789"))
1846 self
.dotest(root
, False)
1848 met4
= MetaNode(self
.mkid("id"))
1849 # inserter.insertrange(Range(3-1, 4-1, met4))
1850 inserter
.insertrange(Range(3, 4, met4
))
1852 root
.appendchild(met2
.dup()
1853 .appendchild(TextNode("1"))
1854 .appendchild(url1
.dup().appendchild(TextNode("2"))))
1855 root
.appendchild(met4
.dup()
1856 .appendchild(url1
.dup().appendchild(TextNode("3"))))
1857 root
.appendchild(met3
.dup()
1858 .appendchild(url1
.dup().appendchild(TextNode("4")))
1859 .appendchild(TextNode("5")))
1860 root
.appendchild(TextNode("6789"))
1861 self
.dotest(root
, False)
1863 url5
= HyperlinkNode(self
.mkname("url"))
1864 # inserter.insertrange(Range(9-3, 12-3, url5))
1865 inserter
.insertrange(Range(9, 12, url5
))
1866 met6
= MetaNode(self
.mkid("id"))
1867 # inserter.insertrange(Range(10-3, 11-3, met6))
1868 inserter
.insertrange(Range(10, 11, met6
))
1870 root
.appendchild(met2
.dup()
1871 .appendchild(TextNode("1"))
1872 .appendchild(url1
.dup().appendchild(TextNode("2"))))
1873 root
.appendchild(met4
.dup()
1874 .appendchild(url1
.dup().appendchild(TextNode("3"))))
1875 root
.appendchild(met3
.dup()
1876 .appendchild(url1
.dup().appendchild(TextNode("4")))
1877 .appendchild(TextNode("5")))
1878 root
.appendchild(TextNode("6"))
1879 root
.appendchild(url5
.dup().appendchild(TextNode("7")))
1880 root
.appendchild(met6
.dup()
1881 .appendchild(url5
.dup().appendchild(TextNode("8"))))
1882 root
.appendchild(url5
.dup().appendchild(TextNode("9")))
1883 self
.dotest(root
, False)
1885 def test_range_ruby_meta(self
):
1886 inserter
= RangeInserter(self
.__class
__.xDoc
)
1887 text
= TextNode("123456789")
1888 inserter
.insertrange(Range(0, 0, text
))
1889 rby1
= RubyNode(self
.mkname("ruby"))
1890 inserter
.insertrange(Range(1, 4, rby1
))
1892 met2
= MetaNode(self
.mkid("id"))
1893 inserter
.insertrange(Range(0, 2, met2
))
1895 root
.appendchild(met2
.dup()
1896 .appendchild(TextNode("1"))
1897 .appendchild(rby1
.dup().appendchild(TextNode("2"))))
1898 root
.appendchild(rby1
.dup().appendchild(TextNode("34")))
1899 root
.appendchild(TextNode("56789"))
1900 self
.dotest(root
, False)
1902 met3
= MetaNode(self
.mkid("id"))
1903 # inserter.insertrange(Range(4-1, 6-1, met3))
1904 inserter
.insertrange(Range(4, 6, met3
))
1906 root
.appendchild(met2
.dup()
1907 .appendchild(TextNode("1"))
1908 .appendchild(rby1
.dup().appendchild(TextNode("2"))))
1909 root
.appendchild(rby1
.dup().appendchild(TextNode("3")))
1910 root
.appendchild(met3
.dup()
1911 .appendchild(rby1
.dup().appendchild(TextNode("4")))
1912 .appendchild(TextNode("5")))
1913 root
.appendchild(TextNode("6789"))
1914 self
.dotest(root
, False)
1916 met4
= MetaNode(self
.mkid("id"))
1917 # inserter.insertrange(Range(3-1, 4-1, met4))
1918 inserter
.insertrange(Range(3, 4, met4
))
1920 root
.appendchild(met2
.dup()
1921 .appendchild(TextNode("1"))
1922 .appendchild(rby1
.dup().appendchild(TextNode("2"))))
1923 root
.appendchild(met4
.dup()
1924 .appendchild(rby1
.dup().appendchild(TextNode("3"))))
1925 root
.appendchild(met3
.dup()
1926 .appendchild(rby1
.dup().appendchild(TextNode("4")))
1927 .appendchild(TextNode("5")))
1928 root
.appendchild(TextNode("6789"))
1929 self
.dotest(root
, False)
1931 rby5
= RubyNode(self
.mkname("ruby"))
1932 # inserter.insertrange(Range(9-3, 12-3, rby5))
1933 inserter
.insertrange(Range(9, 12, rby5
))
1934 met6
= MetaNode(self
.mkid("id"))
1935 # inserter.insertrange(Range(10-3, 11-3, met6))
1936 inserter
.insertrange(Range(10, 11, met6
))
1938 root
.appendchild(met2
.dup()
1939 .appendchild(TextNode("1"))
1940 .appendchild(rby1
.dup().appendchild(TextNode("2"))))
1941 root
.appendchild(met4
.dup()
1942 .appendchild(rby1
.dup().appendchild(TextNode("3"))))
1943 root
.appendchild(met3
.dup()
1944 .appendchild(rby1
.dup().appendchild(TextNode("4")))
1945 .appendchild(TextNode("5")))
1946 root
.appendchild(TextNode("6"))
1947 root
.appendchild(rby5
.dup()
1948 .appendchild(TextNode("7"))
1949 .appendchild(met6
.dup()
1950 .appendchild(TextNode("8")))
1951 .appendchild(TextNode("9")))
1952 self
.dotest(root
, False)
1954 def test_range_meta_hyperlink(self
):
1955 inserter
= RangeInserter(self
.__class
__.xDoc
)
1956 text
= TextNode("123456789")
1957 inserter
.insertrange(Range(0, 0, text
))
1958 met1
= MetaNode(self
.mkid("id"))
1959 inserter
.insertrange(Range(1, 6, met1
))
1961 url2
= HyperlinkNode(self
.mkname("url"))
1962 # inserter.insertrange(Range(0, 4-1, url2))
1963 inserter
.insertrange(Range(0, 4, url2
))
1965 root
.appendchild(url2
.dup().appendchild(TextNode("1")))
1966 root
.appendchild(met1
.dup()
1967 .appendchild(url2
.dup().appendchild(TextNode("23")))
1968 .appendchild(TextNode("456")))
1969 root
.appendchild(TextNode("789"))
1970 self
.dotest(root
, False)
1972 url3
= HyperlinkNode(self
.mkname("url"))
1973 # inserter.insertrange(Range(6-1, 8-1, url3))
1974 inserter
.insertrange(Range(6, 8, url3
))
1976 root
.appendchild(url2
.dup().appendchild(TextNode("1")))
1977 root
.appendchild(met1
.dup()
1978 .appendchild(url2
.dup().appendchild(TextNode("23")))
1979 .appendchild(TextNode("45"))
1980 .appendchild(url3
.dup().appendchild(TextNode("6"))))
1981 root
.appendchild(url3
.dup().appendchild(TextNode("7")))
1982 root
.appendchild(TextNode("89"))
1983 self
.dotest(root
, False)
1984 ## around (not quite, due to API)
1985 url4
= HyperlinkNode(self
.mkname("url"))
1986 # inserter.insertrange(Range(1, 9-1, url4))
1987 inserter
.insertrange(Range(1, 9, url4
))
1989 root
.appendchild(url2
.dup().appendchild(TextNode("1")))
1990 root
.appendchild(met1
.dup()
1991 .appendchild(url4
.dup()
1992 .appendchild(TextNode("23456"))))
1993 root
.appendchild(url4
.dup().appendchild(TextNode("78")))
1994 root
.appendchild(TextNode("9"))
1995 self
.dotest(root
, False)
1997 url5
= HyperlinkNode(self
.mkname("url"))
1998 # inserter.insertrange(Range(4-1, 6-1, url5))
1999 inserter
.insertrange(Range(4, 6, url5
))
2001 root
.appendchild(url2
.dup().appendchild(TextNode("1")))
2002 root
.appendchild(met1
.dup()
2003 .appendchild(url4
.dup()
2004 .appendchild(TextNode("23")))
2005 .appendchild(url5
.dup()
2006 .appendchild(TextNode("45")))
2007 .appendchild(url4
.dup()
2008 .appendchild(TextNode("6"))))
2009 root
.appendchild(url4
.dup().appendchild(TextNode("78")))
2010 root
.appendchild(TextNode("9"))
2011 self
.dotest(root
, False)
2013 def test_range_meta_ruby(self
):
2014 inserter
= RangeInserter(self
.__class
__.xDoc
)
2015 text
= TextNode("123456789")
2016 inserter
.insertrange(Range(0, 0, text
))
2017 met1
= MetaNode(self
.mkid("id"))
2018 inserter
.insertrange(Range(1, 5, met1
))
2020 rby2
= RubyNode(self
.mkname("ruby"))
2021 # inserter.insertrange(Range(0, 3-1, rby2))
2022 inserter
.insertrange(Range(0, 3, rby2
))
2024 root
.appendchild(rby2
.dup().appendchild(TextNode("1")))
2025 root
.appendchild(met1
.dup()
2026 .appendchild(rby2
.dup().appendchild(TextNode("2")))
2027 .appendchild(TextNode("345")))
2028 root
.appendchild(TextNode("6789"))
2029 self
.dotest(root
, False)
2031 rby3
= RubyNode(self
.mkname("ruby"))
2032 # inserter.insertrange(Range(5-1, 7-1, rby3))
2033 inserter
.insertrange(Range(5, 7, rby3
))
2035 root
.appendchild(rby2
.dup().appendchild(TextNode("1")))
2036 root
.appendchild(met1
.dup()
2037 .appendchild(rby2
.dup().appendchild(TextNode("2")))
2038 .appendchild(TextNode("34"))
2039 .appendchild(rby3
.dup().appendchild(TextNode("5"))))
2040 root
.appendchild(rby3
.dup().appendchild(TextNode("6")))
2041 root
.appendchild(TextNode("789"))
2042 self
.dotest(root
, False)
2044 rby4
= RubyNode(self
.mkname("ruby"))
2045 # inserter.insertrange(Range(1, 7-1, rby4))
2046 inserter
.insertrange(Range(1, 7, rby4
))
2048 root
.appendchild(rby2
.dup().appendchild(TextNode("1")))
2049 root
.appendchild(rby4
.dup()
2050 .appendchild(met1
.dup()
2051 .appendchild(TextNode("2345")))
2052 .appendchild(TextNode("6")))
2053 root
.appendchild(TextNode("789"))
2054 self
.dotest(root
, False)
2056 met5
= MetaNode(self
.mkid("id"))
2057 # inserter.insertrange(Range(7-1, 9-1, met5))
2058 inserter
.insertrange(Range(7, 9, met5
))
2059 rby6
= RubyNode(self
.mkname("ruby"))
2060 # inserter.insertrange(Range(9-2, 10/-2, rby6))
2061 inserter
.insertrange(Range(9, 10, rby6
))
2063 root
.appendchild(rby2
.dup().appendchild(TextNode("1")))
2064 root
.appendchild(rby4
.dup()
2065 .appendchild(met1
.dup()
2066 .appendchild(TextNode("2345")))
2067 .appendchild(TextNode("6")))
2068 root
.appendchild(met5
.dup()
2069 .appendchild(TextNode("7"))
2070 .appendchild(rby6
.dup()
2071 .appendchild(TextNode("8"))))
2072 root
.appendchild(TextNode("9"))
2073 self
.dotest(root
, False)
2074 ## inside, with invalid range that includes the dummy char
2075 rby7
= RubyNode(self
.mkname("ruby"))
2076 # inserter.insertrange(Range(7-1, 9-2, rby7))
2077 inserter
.insertrange(Range(7, 9, rby7
))
2079 root
.appendchild(rby2
.dup().appendchild(TextNode("1")))
2080 root
.appendchild(rby4
.dup()
2081 .appendchild(met1
.dup()
2082 .appendchild(TextNode("2345")))
2083 .appendchild(TextNode("6")))
2084 root
.appendchild(met5
.dup()
2085 .appendchild(rby7
.dup()
2086 .appendchild(TextNode("7")))
2087 .appendchild(rby6
.dup()
2088 .appendchild(TextNode("8"))))
2089 root
.appendchild(TextNode("9"))
2090 self
.dotest(root
, False)
2091 ## around, at same position as meta
2092 rby8
= RubyNode(self
.mkname("ruby"))
2093 # inserter.insertrange(Range(7-1, 10-2, rby8))
2094 inserter
.insertrange(Range(7, 10, rby8
))
2096 root
.appendchild(rby2
.dup().appendchild(TextNode("1")))
2097 root
.appendchild(rby4
.dup()
2098 .appendchild(met1
.dup()
2099 .appendchild(TextNode("2345")))
2100 .appendchild(TextNode("6")))
2101 root
.appendchild(rby8
.dup()
2102 .appendchild(met5
.dup()
2103 .appendchild(TextNode("78"))))
2104 root
.appendchild(TextNode("9"))
2105 self
.dotest(root
, False)
2107 def test_range_meta_meta(self
):
2108 inserter
= RangeInserter(self
.__class
__.xDoc
)
2109 text
= TextNode("123456789")
2110 inserter
.insertrange(Range(0, 0, text
))
2111 met1
= MetaNode(self
.mkid("id"))
2112 inserter
.insertrange(Range(3, 6, met1
))
2114 met2
= MetaNode(self
.mkid("id"))
2116 inserter
.insertrange(Range(0, 4, met2
))
2117 fail("testRangeMetaMeta: overlap left allowed")
2118 except IllegalArgumentException
:
2121 root
.appendchild(TextNode("123"))
2122 root
.appendchild(met1
.dup().appendchild(TextNode("456")))
2123 root
.appendchild(TextNode("789"))
2124 self
.dotest(root
, False)
2126 met3
= MetaNode(self
.mkid("id"))
2129 # inserter.insertrange(Range(5-1, 8-1, met3))
2130 inserter
.insertrange(Range(5, 8, met3
))
2131 self
.fail("testRangeMetaMeta: overlap right allowed")
2132 except IllegalArgumentException
:
2136 root
.appendchild(TextNode("123"))
2137 root
.appendchild(met1
.dup().appendchild(TextNode("456")))
2138 root
.appendchild(TextNode("789"))
2139 self
.dotest(root
, False)
2141 met4
= MetaNode(self
.mkid("id"))
2142 # inserter.insertrange(Range(3, 7-1, met4))
2143 inserter
.insertrange(Range(3, 7, met4
))
2145 root
.appendchild(TextNode("123"))
2146 root
.appendchild(met4
.dup()
2147 .appendchild(met1
.dup().appendchild(TextNode("456"))))
2148 root
.appendchild(TextNode("789"))
2149 self
.dotest(root
, False)
2151 met5
= MetaNode(self
.mkid("id"))
2152 # inserter.insertrange(Range(6-2, 8-2, met5))
2153 inserter
.insertrange(Range(6, 8, met5
))
2155 root
.appendchild(TextNode("123"))
2156 root
.appendchild(met4
.dup()
2157 .appendchild(met1
.dup()
2158 .appendchild(TextNode("4"))
2159 .appendchild(met5
.dup()
2160 .appendchild(TextNode("56")))))
2161 root
.appendchild(TextNode("789"))
2162 self
.dotest(root
, False)
2164 def test_range2(self
):
2165 inserter
= RangeInserter(self
.__class
__.xDoc
)
2166 text
= TextNode("123456789")
2167 inserter
.insertrange(Range(0, 0, text
))
2168 met1
= MetaNode(self
.mkid("id"))
2169 inserter
.insertrange(Range(1, 8, met1
))
2170 met2
= MetaNode(self
.mkid("id"))
2171 # inserter.insertrange(Range(3-1, 8-1, met2))
2172 inserter
.insertrange(Range(3, 8, met2
))
2173 met3
= MetaNode(self
.mkid("id"))
2174 # inserter.insertrange(Range(5-2, 8-2, met3))
2175 inserter
.insertrange(Range(5, 8, met3
))
2177 root
.appendchild(TextNode("1"))
2178 root
.appendchild(met1
.dup()
2179 .appendchild(TextNode("2"))
2180 .appendchild(met2
.dup()
2181 .appendchild(TextNode("3"))
2182 .appendchild(met3
.dup()
2183 .appendchild(TextNode("456")))
2184 .appendchild(TextNode("7")))
2185 .appendchild(TextNode("8")))
2186 root
.appendchild(TextNode("9"))
2187 self
.dotest(root
, False)
2188 ## split ruby at every meta start!
2189 rby4
= RubyNode(self
.mkname("ruby"))
2190 # inserter.insertrange(Range(0, 7-3, rby4))
2191 inserter
.insertrange(Range(0, 7, rby4
))
2193 root
.appendchild(rby4
.dup()
2194 .appendchild(TextNode("1")))
2195 root
.appendchild(met1
.dup()
2196 .appendchild(rby4
.dup()
2197 .appendchild(TextNode("2")))
2198 .appendchild(met2
.dup()
2199 .appendchild(rby4
.dup()
2200 .appendchild(TextNode("3")))
2201 .appendchild(met3
.dup()
2202 .appendchild(rby4
.dup()
2203 .appendchild(TextNode("4")))
2204 .appendchild(TextNode("56")))
2205 .appendchild(TextNode("7")))
2206 .appendchild(TextNode("8")))
2207 root
.appendchild(TextNode("9"))
2208 self
.dotest(root
, False)
2209 ## split ruby at every meta end!
2210 rby5
= RubyNode(self
.mkname("ruby"))
2211 # inserter.insertrange(Range(8-3, 12-3, rby5))
2212 inserter
.insertrange(Range(8, 12, rby5
))
2214 root
.appendchild(rby4
.dup()
2215 .appendchild(TextNode("1")))
2216 root
.appendchild(met1
.dup()
2217 .appendchild(rby4
.dup()
2218 .appendchild(TextNode("2")))
2219 .appendchild(met2
.dup()
2220 .appendchild(rby4
.dup()
2221 .appendchild(TextNode("3")))
2222 .appendchild(met3
.dup()
2223 .appendchild(rby4
.dup()
2224 .appendchild(TextNode("4")))
2225 .appendchild(TextNode("5"))
2226 .appendchild(rby5
.dup()
2227 .appendchild(TextNode("6"))))
2228 .appendchild(rby5
.dup()
2229 .appendchild(TextNode("7"))))
2230 .appendchild(rby5
.dup()
2231 .appendchild(TextNode("8"))))
2232 root
.appendchild(rby5
.dup()
2233 .appendchild(TextNode("9")))
2234 self
.dotest(root
, False)
2236 def test_range3(self
):
2237 inserter
= RangeInserter(self
.__class
__.xDoc
)
2238 text
= TextNode("123456789")
2239 inserter
.insertrange(Range(0, 0, text
))
2240 rby1
= RubyNode(self
.mkname("ruby"))
2241 inserter
.insertrange(Range(0, 9, rby1
))
2242 met2
= MetaNode(self
.mkid("id"))
2243 inserter
.insertrange(Range(2, 7, met2
))
2245 root
.appendchild(rby1
.dup()
2246 .appendchild(TextNode("12"))
2247 .appendchild(met2
.dup()
2248 .appendchild(TextNode("34567")))
2249 .appendchild(TextNode("89")))
2250 self
.dotest(root
, False)
2251 ## overwrite outer ruby, split remains at inner meta!
2252 rby3
= RubyNode(self
.mkname("ruby"))
2253 # inserter.insertrange(Range(5-1, 6-1, rby3))
2254 inserter
.insertrange(Range(5, 6, rby3
))
2256 root
.appendchild(rby1
.dup()
2257 .appendchild(TextNode("12")))
2258 root
.appendchild(met2
.dup()
2259 .appendchild(rby1
.dup()
2260 .appendchild(TextNode("34")))
2261 .appendchild(rby3
.dup()
2262 .appendchild(TextNode("5")))
2263 .appendchild(rby1
.dup()
2264 .appendchild(TextNode("67"))))
2265 root
.appendchild(rby1
.dup()
2266 .appendchild(TextNode("89")))
2267 self
.dotest(root
, False)
2269 def test_range4(self
):
2270 inserter
= RangeInserter(self
.__class
__.xDoc
)
2271 text
= TextNode("123456789")
2272 inserter
.insertrange(Range(0, 0, text
))
2273 rby1
= RubyNode(self
.mkname("ruby"))
2274 inserter
.insertrange(Range(0, 9, rby1
))
2275 met2
= MetaNode(self
.mkid("id"))
2276 inserter
.insertrange(Range(1, 8, met2
))
2277 met3
= MetaNode(self
.mkid("id"))
2278 # inserter.insertrange(Range(3-1, 8-1, met3))
2279 inserter
.insertrange(Range(3, 8, met3
))
2280 met4
= MetaNode(self
.mkid("id"))
2281 # inserter.insertrange(Range(5-2, 8-2, met4))
2282 inserter
.insertrange(Range(5, 8, met4
))
2284 root
.appendchild(rby1
.dup()
2285 .appendchild(TextNode("1"))
2286 .appendchild(met2
.dup()
2287 .appendchild(TextNode("2"))
2288 .appendchild(met3
.dup()
2289 .appendchild(TextNode("3"))
2290 .appendchild(met4
.dup()
2291 .appendchild(TextNode("456")))
2292 .appendchild(TextNode("7")))
2293 .appendchild(TextNode("8")))
2294 .appendchild(TextNode("9")))
2295 self
.dotest(root
, False)
2296 ## overwrite outer ruby, split remains at every inner meta!
2297 rby5
= RubyNode(self
.mkname("ruby"))
2298 # inserter.insertrange(Range(7-3, 8-3, rby5))
2299 inserter
.insertrange(Range(7, 8, rby5
))
2301 root
.appendchild(rby1
.dup()
2302 .appendchild(TextNode("1")))
2303 root
.appendchild(met2
.dup()
2304 .appendchild(rby1
.dup()
2305 .appendchild(TextNode("2")))
2306 .appendchild(met3
.dup()
2307 .appendchild(rby1
.dup()
2308 .appendchild(TextNode("3")))
2309 .appendchild(met4
.dup()
2310 .appendchild(rby1
.dup()
2311 .appendchild(TextNode("4")))
2312 .appendchild(rby5
.dup()
2313 .appendchild(TextNode("5")))
2314 .appendchild(rby1
.dup()
2315 .appendchild(TextNode("6"))))
2316 .appendchild(rby1
.dup()
2317 .appendchild(TextNode("7"))))
2318 .appendchild(rby1
.dup()
2319 .appendchild(TextNode("8"))))
2320 root
.appendchild(rby1
.dup()
2321 .appendchild(TextNode("9")))
2322 self
.dotest(root
, False)
2324 def test_range5(self
):
2325 inserter
= RangeInserter(self
.__class
__.xDoc
)
2326 text
= TextNode("123456789")
2327 inserter
.insertrange(Range(0, 0, text
))
2328 rby1
= RubyNode(self
.mkname("ruby"))
2329 inserter
.insertrange(Range(0, 9, rby1
))
2330 met2
= MetaNode(self
.mkid("id"))
2331 inserter
.insertrange(Range(1, 3, met2
))
2332 met3
= MetaNode(self
.mkid("id"))
2333 # inserter.insertrange(Range(5-1, 6-1, met3))
2334 inserter
.insertrange(Range(5, 6, met3
))
2335 met4
= MetaNode(self
.mkid("id"))
2336 # inserter.insertrange(Range(8-2, 10-2, met4))
2337 inserter
.insertrange(Range(8, 10, met4
))
2339 root
.appendchild(rby1
.dup()
2340 .appendchild(TextNode("1"))
2341 .appendchild(met2
.dup().appendchild(TextNode("23")))
2342 .appendchild(TextNode("4"))
2343 .appendchild(met3
.dup().appendchild(TextNode("5")))
2344 .appendchild(TextNode("6"))
2345 .appendchild(met4
.dup().appendchild(TextNode("78")))
2346 .appendchild(TextNode("9")))
2347 self
.dotest(root
, False)
2348 ## overwrite outer ruby, but split at inner metas!
2349 rby5
= RubyNode(self
.mkname("ruby"))
2350 # inserter.insertrange(Range(3-1, 10-3, rby5))
2351 inserter
.insertrange(Range(3, 10, rby5
))
2353 root
.appendchild(rby1
.dup()
2354 .appendchild(TextNode("1")))
2355 root
.appendchild(met2
.dup()
2356 .appendchild(rby1
.dup()
2357 .appendchild(TextNode("2")))
2358 .appendchild(rby5
.dup()
2359 .appendchild(TextNode("3"))))
2360 root
.appendchild(rby5
.dup()
2361 .appendchild(TextNode("4"))
2362 .appendchild(met3
.dup()
2363 .appendchild(TextNode("5")))
2364 .appendchild(TextNode("6")))
2365 root
.appendchild(met4
.dup()
2366 .appendchild(rby5
.dup()
2367 .appendchild(TextNode("7")))
2368 .appendchild(rby1
.dup()
2369 .appendchild(TextNode("8"))))
2370 root
.appendchild(rby1
.dup()
2371 .appendchild(TextNode("9")))
2372 self
.dotest(root
, False)
2374 def test_range6(self
):
2375 inserter
= RangeInserter(self
.__class
__.xDoc
)
2376 text
= TextNode("123456789")
2377 inserter
.insertrange(Range(0, 0, text
))
2378 met1
= MetaNode(self
.mkid("id"))
2379 inserter
.insertrange(Range(1, 5, met1
))
2380 met2
= MetaNode(self
.mkid("id"))
2381 # inserter.insertrange(Range(3-1, 6-1, met2))
2382 inserter
.insertrange(Range(3, 6, met2
))
2383 met3
= MetaNode(self
.mkid("id"))
2384 # inserter.insertrange(Range(5-2, 7-2, met3))
2385 inserter
.insertrange(Range(5, 7, met3
))
2387 root
.appendchild(TextNode("1"))
2388 root
.appendchild(met1
.dup()
2389 .appendchild(TextNode("2"))
2390 .appendchild(met2
.dup()
2391 .appendchild(TextNode("3"))
2392 .appendchild(met3
.dup()
2393 .appendchild(TextNode("45")))))
2394 root
.appendchild(TextNode("6789"))
2395 self
.dotest(root
, False)
2396 ## split at 3 metas, all at same position
2397 rby4
= RubyNode(self
.mkname("ruby"))
2398 # inserter.insertrange(Range(7-3, 10-3, rby4))
2399 inserter
.insertrange(Range(7, 10, rby4
))
2401 root
.appendchild(TextNode("1"))
2402 root
.appendchild(met1
.dup()
2403 .appendchild(TextNode("2"))
2404 .appendchild(met2
.dup()
2405 .appendchild(TextNode("3"))
2406 .appendchild(met3
.dup()
2407 .appendchild(TextNode("4"))
2408 .appendchild(rby4
.dup()
2409 .appendchild(TextNode("5"))))))
2410 root
.appendchild(rby4
.dup()
2411 .appendchild(TextNode("67")))
2412 root
.appendchild(TextNode("89"))
2413 self
.dotest(root
, False)
2415 def test_range7(self
):
2416 inserter
= RangeInserter(self
.__class
__.xDoc
)
2417 text
= TextNode("123456789")
2418 inserter
.insertrange(Range(0, 0, text
))
2419 url1
= HyperlinkNode(self
.mkname("url"))
2420 inserter
.insertrange(Range(1, 5, url1
))
2421 met2
= MetaNode(self
.mkid("id"))
2422 inserter
.insertrange(Range(3, 5, met2
))
2424 root
.appendchild(TextNode("1"))
2425 root
.appendchild(url1
.dup()
2426 .appendchild(TextNode("23")))
2427 root
.appendchild(met2
.dup()
2428 .appendchild(url1
.dup()
2429 .appendchild(TextNode("45"))))
2430 root
.appendchild(TextNode("6789"))
2431 self
.dotest(root
, False)
2432 ## this should result in not splitting the hyperlink, but due to API
2434 rby3
= RubyNode(self
.mkname("ruby"))
2435 # inserter.insertrange(Range(5-1, 8-1, rby3))
2436 inserter
.insertrange(Range(5, 8, rby3
))
2438 root
.appendchild(TextNode("1"))
2439 root
.appendchild(url1
.dup()
2440 .appendchild(TextNode("23")))
2441 root
.appendchild(met2
.dup()
2442 .appendchild(url1
.dup()
2443 .appendchild(TextNode("4")))
2444 .appendchild(rby3
.dup()
2445 .appendchild(url1
.dup()
2446 .appendchild(TextNode("5")))))
2447 root
.appendchild(rby3
.dup()
2448 .appendchild(TextNode("67")))
2449 root
.appendchild(TextNode("89"))
2450 self
.dotest(root
, False)
2452 # TODO: test partial selection, test UNDO/REDO
2454 ##i109601# NestedTextContent and XChild
2455 def test_meta_xchild(self
):
2456 xDoc
= self
.__class
__.xDoc
2457 id1
= StringPair("content.xml", self
.mkname("id"))
2458 id2
= StringPair("content.xml", self
.mkname("id"))
2459 id3
= StringPair("content.xml", self
.mkname("id"))
2460 id4
= StringPair("content.xml", self
.mkname("id"))
2461 id5
= StringPair("content.xml", self
.mkname("id"))
2462 id6
= StringPair("content.xml", self
.mkname("id"))
2463 meta1
= MetaNode(id1
)
2464 meta2
= MetaNode(id2
)
2465 meta3
= MetaFieldNode(id3
)
2466 meta4
= MetaNode(id4
)
2467 meta5
= MetaNode(id5
)
2468 meta6
= MetaFieldNode(id6
)
2470 root
.appendchild(meta1
.dup()
2471 .appendchild(TextNode("1")))
2472 root
.appendchild(TextNode("2"))
2473 root
.appendchild(meta2
.dup()
2474 .appendchild(meta3
.dup()
2475 .appendchild(TextNode("34"))
2476 .appendchild(meta4
.dup()
2477 .appendchild(TextNode("56")))
2478 .appendchild(meta5
.dup())
2479 .appendchild(TextNode("7"))))
2480 root
.appendchild(TextNode("8"))
2481 root
.appendchild(meta6
.dup()
2482 .appendchild(TextNode("9")))
2484 inserter
= RangeInserter(xDoc
)
2485 text
= TextNode("123456789")
2486 inserter
.insertrange(Range(0, 0, text
))
2487 xMeta1
= inserter
.insertrange(Range(0, 1, meta1
))
2488 xMeta2
= inserter
.insertrange(Range(3, 8, meta2
))
2489 xMeta3
= inserter
.insertrange(Range(4, 9, meta3
))
2490 xMeta4
= inserter
.insertrange(Range(7, 9, meta4
))
2491 xMeta5
= inserter
.insertrange(Range(10, 10, meta5
))
2492 xMeta6
= inserter
.insertrange(Range(13, 14, meta6
))
2494 self
.dotest(root
, False)
2496 xDocText
= xDoc
.getText()
2497 xDocTextCursor
= xDocText
.createTextCursor()
2498 xDocTextCursor
.gotoNextParagraph(False) # second paragraph
2503 nestedTextContent
= (
2520 for i
, ntc
in enumerate(nestedTextContent
):
2521 oNTC
= xDocTextCursor
.NestedTextContent
2523 self
.assertIsNone(oNTC
,
2524 "unexpected NestedTextContent at: {}".format(i
))
2526 xmlid
= oNTC
.MetadataReference
2527 self
.assertTrue(MetaNode
.eq(ntc
, xmlid
),
2528 "wrong NestedTextContent at: {}".format(i
))
2529 xDocTextCursor
.goRight(1, False)
2532 xMeta1
.setParent(xMeta4
)
2533 fail("setParent(): allowed?")
2534 except NoSupportException
:
2536 self
.assertIsNone(xMeta1
.getParent(), "getParent(): not None")
2537 self
.assertIsNone(xMeta2
.getParent(), "getParent(): not None")
2538 self
.assertIsNone(xMeta6
.getParent(), "getParent(): not None")
2540 xParent3
= xMeta3
.getParent()
2541 self
.assertIsNotNone(xParent3
, "getParent(): None")
2542 xmlid
= xParent3
.MetadataReference
2543 self
.assertTrue(MetaNode
.eq(xmlid
, id2
), "getParent(): wrong")
2545 xParent4
= xMeta4
.getParent()
2546 self
.assertIsNotNone(xParent4
, "getParent(): None")
2547 xmlid
= xParent4
.MetadataReference
2548 self
. assertTrue(MetaNode
.eq(xmlid
, id3
), "getParent(): wrong")
2550 xParent5
= xMeta5
.getParent()
2551 self
.assertIsNotNone(xParent5
, "getParent(): None")
2552 xmlid
= xParent5
.MetadataReference
2553 self
.assertTrue(MetaNode
.eq(xmlid
, id3
), "getParent(): wrong")
2555 # test SwXMeta XText interface
2556 def test_meta_xtext(self
):
2557 xDoc
= self
.__class
__.xDoc
2558 inserter
= RangeInserter(xDoc
)
2559 text
= TextNode("12AB6789")
2560 inserter
.insertrange(Range(0, 0, text
))
2561 meta
= MetaNode(self
.mkid("id"))
2562 xMeta
= inserter
.makemeta()
2564 xDocText
= xDoc
.getText()
2565 xDocTextCursor
= xDocText
.createTextCursor()
2566 xDocTextCursor
.goRight(3, False)
2567 xDocTextCursor
.goRight(2, True)
2568 xDocText
.insertTextContent(xDocTextCursor
, xMeta
, True)
2570 xMeta
.MetadataReference
= meta
.xmlid
2571 xParentText
= xMeta
.getText()
2572 self
.assertIsNotNone(xParentText
, "getText(): no parent")
2574 xStart
= xMeta
.getStart()
2575 self
.assertIsNotNone(xStart
, "getStart(): no start")
2577 xEnd
= xMeta
.getEnd()
2578 self
.assertIsNotNone(xEnd
, "getEnd(): no end")
2580 xMeta
.setString("45")
2582 string
= xMeta
.getString()
2583 self
.assertEqual("45", string
, "getString(): invalid string returned")
2585 xTextCursor
= xMeta
.createTextCursor()
2586 self
.assertIsNotNone(xTextCursor
, "createTextCursor(): failed")
2589 xMeta
.createTextCursorByRange(None)
2590 fail("createTextCursorByRange(): None allowed?")
2591 except RuntimeException
:
2594 xTextCursorStart
= xMeta
.createTextCursorByRange(xStart
)
2595 self
.assertIsNotNone(xTextCursorStart
,
2596 "createTextCursorByRange(): failed for start")
2598 xTextCursorEnd
= xMeta
.createTextCursorByRange(xEnd
)
2599 self
.assertIsNotNone(xTextCursorEnd
,
2600 "createTextCursorByRange(): failed for end")
2602 ## move outside meta
2603 xDocTextCursor
.gotoStart(False)
2606 xMeta
.insertString(None, "foo", False)
2607 fail("insertString(): None allowed?")
2608 except RuntimeException
:
2612 xMeta
.insertString(xDocTextCursor
, "foo", False)
2613 fail("insertString(): cursor outside allowed?")
2614 except RuntimeException
:
2617 xStart
= xMeta
.getStart()
2618 xMeta
.insertString(xStart
, "A", False)
2619 string
= xMeta
.getString()
2620 self
.assertEqual("A45", string
, "getString(): invalid string returned")
2622 xMeta
.insertString(xEnd
, "B", False)
2623 string
= xMeta
.getString()
2624 self
.assertEqual("A45B", string
, "getString(): invalid string returned")
2627 xMeta
.insertControlCharacter(None, HARD_HYPHEN
, False)
2628 fail("insertControlCharacter(): None allowed?")
2629 except IllegalArgumentException
:
2632 xStart
= xMeta
.getStart()
2634 xMeta
.insertControlCharacter(xDocTextCursor
, HARD_HYPHEN
, False)
2635 fail("insertControlCharacter(): cursor outside allowed?")
2636 except IllegalArgumentException
:
2639 xMeta
.insertControlCharacter(xStart
, HARD_HYPHEN
, False)
2640 string
= xMeta
.getString()
2641 self
.assertEqual('\u2011' + 'A45B', string
,
2642 "getString(): invalid string returned")
2644 xMeta
.insertControlCharacter(xEnd
, HARD_HYPHEN
, False)
2645 string
= xMeta
.getString()
2646 self
.assertEqual('\u2011' + 'A45B' + '\u2011', string
,
2647 "getString(): invalid string returned")
2649 xMeta
.setString("45")
2651 xMeta
.insertTextContent(None, xMeta
, False)
2652 fail("insertTextContent(): None range allowed?")
2653 except IllegalArgumentException
:
2657 xMeta
.insertTextContent(xStart
, None, False)
2658 fail("insertTextContent(): None content allowed?")
2659 except IllegalArgumentException
:
2663 xMeta
.insertTextContent(xDocTextCursor
, xMeta
, False)
2664 fail("insertTextContent(): cursor outside allowed?")
2665 except IllegalArgumentException
:
2668 field1
= TextFieldNode("f1")
2669 field2
= TextFieldNode("f2")
2670 xField1
= inserter
.maketextfield(field1
.content
)
2671 xField2
= inserter
.maketextfield(field2
.content
)
2673 xStart
= xMeta
.getStart()
2674 xMeta
.insertTextContent(xStart
, xField1
, False)
2677 root
.appendchild(TextNode("12"))
2678 root
.appendchild(meta
.dup()
2679 .appendchild(field1
.dup())
2680 .appendchild(TextNode("45")))
2681 root
.appendchild(TextNode("6789"))
2682 self
.dotest(root
, False)
2684 xMeta
.insertTextContent(xEnd
, xField2
, False)
2687 root
.appendchild(TextNode("12"))
2688 root
.appendchild(meta
.dup()
2689 .appendchild(field1
.dup())
2690 .appendchild(TextNode("45"))
2691 .appendchild(field2
.dup()))
2692 root
.appendchild(TextNode("6789"))
2693 self
.dotest(root
, False)
2696 xMeta
.removeTextContent(None)
2697 fail("removeTextContent(): None content allowed?")
2698 except RuntimeException
:
2701 xMeta
.removeTextContent(xField1
)
2703 xAnchor
= xMeta
.getAnchor()
2704 self
.assertIsNotNone(xAnchor
, "getAnchor(): None")
2706 ## evil test case: insert ruby around meta
2707 ruby
= RubyNode(self
.mkname("ruby"))
2708 inserter
.insertrange(Range(2, 6, ruby
))
2710 ## prevent caching...
2712 # root.appendchild(TextNode("12"))
2713 # root.appendchild(ruby.dup()
2714 # .appendchild(meta.dup()
2715 # .appendchild(TextNode("45"))
2716 # .appendchild(field2.dup())))
2717 # root.appendchild(TextNode("6789"))
2718 # self.dotest(root, False)
2720 xEnum
= xMeta
.createEnumeration()
2721 self
.assertIsNotNone("createEnumeration(): returns None", xEnum
)
2723 self
.assertTrue(xEnum
.hasMoreElements(),"hasNext(): first missing")
2724 xPortion
= xEnum
.nextElement()
2725 type_
= xPortion
.TextPortionType
2726 self
.assertEqual("Text", type_
, "first: not text")
2727 txt
= xPortion
.getString()
2728 self
.assertEqual("45", txt
, "first: text differs")
2730 self
.assertTrue(xEnum
.hasMoreElements(),"hasNext(): second missing")
2731 xPortion
= xEnum
.nextElement()
2732 type_
= xPortion
.TextPortionType
2733 self
.assertEqual("TextField", type_
, "second: not text")
2735 ## no ruby end here!!!
2736 self
.assertFalse(xEnum
.hasMoreElements(), "hasNext(): more elements?")
2741 xCursor
= xMeta
.createTextCursor()
2742 self
.assertIsNone(xCursor
,
2743 "createTextCursor(): succeeds on disposed object?")
2744 except RuntimeException
:
2747 # check that cursor move methods move to positions in the meta,
2748 # but do not move to positions outside the meta.
2749 def test_meta_xtextcursor(self
):
2750 xDoc
= self
.__class
__.xDoc
2751 inserter
= RangeInserter(xDoc
)
2752 text
= TextNode("Text. 12 More text here.")
2753 inserter
.insertrange(Range(0, 0, text
))
2754 met1
= MetaNode(self
.mkid("id"))
2755 xMeta
= inserter
.makemeta()
2757 xDocText
= xDoc
.getText()
2758 xDocTextCursor
= xDocText
.createTextCursor()
2759 xDocTextCursor
.goRight(7, False)
2760 xDocTextCursor
.goRight(2, True)
2761 xDocText
.insertTextContent(xDocTextCursor
, xMeta
, True)
2762 xDocTextCursor
.gotoStart(True)
2764 xMeta
.MetadataReference
= met1
.xmlid
2765 xStart
= xMeta
.getStart()
2766 self
.assertIsNotNone(xStart
, "getStart(): no start")
2767 xEnd
= xMeta
.getEnd()
2768 self
.assertIsNotNone(xEnd
, "getEnd(): no end")
2771 xMetaCursor
= xMeta
.createTextCursor()
2772 self
.assertIsNotNone(xMetaCursor
, "createTextCursor(): no cursor")
2774 xMetaCursor
.gotoStart(False)
2775 xMetaCursor
.gotoEnd(False)
2776 bSuccess
= xMetaCursor
.goLeft(1, False)
2777 self
.assertTrue(bSuccess
, "goLeft(): failed")
2778 bSuccess
= xMetaCursor
.goLeft(1000, False)
2779 self
.assertFalse(bSuccess
, "goLeft(): succeeded")
2780 bSuccess
= xMetaCursor
.goRight(1, False)
2781 self
.assertTrue(bSuccess
, "goRight(): failed")
2782 bSuccess
= xMetaCursor
.goRight(1000, False)
2783 self
.assertFalse(bSuccess
, "goRight(): succeeded")
2784 xMetaCursor
.gotoRange(xStart
, False)
2785 xMetaCursor
.gotoRange(xEnd
, False)
2787 xMetaCursor
.gotoRange(xDocTextCursor
, False)
2788 fail("gotoRange(): succeeded")
2789 except RuntimeException
:
2793 xMeta
.setString("Two words")
2794 xMetaCursor
.gotoStart(False)
2796 bSuccess
= xMetaCursor
.gotoNextWord(True) # at start of "words"
2797 self
.assertTrue(bSuccess
, "gotoNextWord(): failed")
2799 string
= xMetaCursor
.getString()
2800 self
.assertEqual("Two ", string
, "gotoNextWord(): wrong string")
2802 bSuccess
= xMetaCursor
.gotoNextWord(False) # at end of "words", cannot leave metafield
2803 self
.assertFalse(bSuccess
,"gotoNextWord(): succeeded")
2804 xMetaCursor
.collapseToEnd()
2805 bSuccess
= xMetaCursor
.gotoPreviousWord(True) # at start of "words"
2806 self
.assertTrue(bSuccess
, "gotoPreviousWord(): failed")
2808 string
= xMetaCursor
.getString()
2809 self
.assertEqual("words", string
, "gotoPreviousWord(): wrong string")
2811 bSuccess
= xMetaCursor
.gotoPreviousWord(False) # at start of "Two"
2812 self
.assertTrue(bSuccess
, "gotoPreviousWord(): failed")
2814 bSuccess
= xMetaCursor
.gotoPreviousWord(False) # cannot leave metafield
2815 self
.assertFalse(bSuccess
, "gotoPreviousWord(): succeeded")
2817 bSuccess
= xMetaCursor
.gotoEndOfWord(True) # at end of "Two"
2818 self
.assertTrue(bSuccess
, "gotoEndOfWord(): failed")
2820 string
= xMetaCursor
.getString()
2821 self
.assertEqual("Two", string
, "gotoEndOfWord(): wrong string")
2823 xMetaCursor
.gotoEnd(False)
2824 bSuccess
= xMetaCursor
.gotoStartOfWord(True)
2825 self
.assertTrue(bSuccess
, "gotoStartOfWord(): failed")
2827 string
= xMetaCursor
.getString()
2828 self
.assertEqual("words", string
, "gotoStartOfWord(): wrong string")
2831 bSuccess
= xMetaCursor
.gotoEndOfWord(False)
2832 self
.assertFalse(bSuccess
, "gotoEndOfWord(): succeeded")
2833 bSuccess
= xMetaCursor
.gotoStartOfWord(False)
2834 self
.assertFalse(bSuccess
, "gotoStartOfWord(): succeeded")
2837 xMeta
.setString("This is a sentence. Another sentence.")
2838 xMetaCursor
.gotoStart(False)
2840 bSuccess
= xMetaCursor
.gotoNextSentence(True)
2841 self
.assertTrue(bSuccess
,"gotoNextSentence(): failed")
2843 string
= xMetaCursor
.getString()
2844 self
.assertEqual("This is a sentence. ", string
,
2845 "gotoNextSentence(): wrong string")
2847 bSuccess
= xMetaCursor
.gotoNextSentence(False)
2848 self
.assertFalse(bSuccess
, "gotoNextSentence(): succeeded")
2850 ## the sentence cursor seems to work differently than the word cursor
2851 xMeta
.setString("This is a sentence. Another sentence. Sentence 3.")
2852 xMetaCursor
.gotoEnd(False)
2853 bSuccess
= xMetaCursor
.gotoPreviousSentence(True)
2854 self
.assertTrue(bSuccess
, "gotoPreviousSentence(): failed")
2856 string
= xMetaCursor
.getString()
2857 self
.assertEqual("Another sentence. Sentence 3.", string
,
2858 "gotoPreviousSentence(): wrong string")
2860 bSuccess
= xMetaCursor
.gotoPreviousSentence(False)
2861 self
.assertFalse(bSuccess
, "gotoPreviousSentence(): succeeded")
2862 bSuccess
= xMetaCursor
.gotoEndOfSentence(True)
2863 self
.assertTrue(bSuccess
, "gotoEndOfSentence(): failed")
2865 string
= xMetaCursor
.getString()
2866 self
.assertEqual("This is a sentence.", string
,
2867 "gotoEndOfSentence(): wrong string")
2869 xMetaCursor
.gotoEnd(False)
2870 bSuccess
= xMetaCursor
.gotoStartOfSentence(True)
2871 self
.assertTrue(bSuccess
,"gotoStartOfSentence(): failed")
2873 string
= xMetaCursor
.getString()
2874 self
.assertEqual("Sentence 3.", string
,
2875 "gotoStartOfSentence(): wrong string")
2878 bSuccess
= xMetaCursor
.gotoEndOfSentence(False)
2879 self
.assertFalse(bSuccess
, "gotoEndOfSentence(): succeeded")
2880 bSuccess
= xMetaCursor
.gotoStartOfSentence(False)
2881 self
.assertFalse(bSuccess
, "gotoStartOfSentence(): succeeded")
2883 ## XParagraphCursor (does not make sense)
2884 bSuccess
= xMetaCursor
.gotoNextParagraph(False)
2885 self
.assertFalse(bSuccess
, "gotoNextParagraph(): succeeded")
2886 bSuccess
= xMetaCursor
.gotoPreviousParagraph(False)
2887 self
.assertFalse(bSuccess
, "gotoPreviousParagraph(): succeeded")
2888 bSuccess
= xMetaCursor
.gotoStartOfParagraph(False)
2889 self
.assertFalse(bSuccess
, "gotoStartOfParagraph(): succeeded")
2890 bSuccess
= xMetaCursor
.gotoEndOfParagraph(False)
2891 self
.assertFalse(bSuccess
, "gotoEndOfParagraph(): succeeded")
2893 # See https://bugs.libreoffice.org/show_bug.cgi?id=49629
2894 # ensure that gotoEndOfWord does not fail when footnote is at word end
2895 def test_xtextcursor(self
):
2896 xDoc
= self
.__class
__.xDoc
2897 inserter
= RangeInserter(xDoc
)
2898 xDocText
= xDoc
.getText()
2899 xDocTextCursor
= xDocText
.createTextCursor()
2900 xDocTextCursor
.gotoNextParagraph(False)
2901 inserter
.inserttext(xDocTextCursor
, "Text")
2902 xDocTextCursor
.gotoEndOfWord(False)
2903 inserter
.insertfootnote(xDocTextCursor
, "footnote")
2904 xDocTextCursor
.gotoStartOfParagraph(False)
2905 bSuccess
= xDocTextCursor
.gotoEndOfWord(True)
2906 self
.assertTrue(bSuccess
, "gotoEndOfWord(): failed")
2907 string
= xDocTextCursor
.getString()
2908 self
.assertEqual("Text", string
, "gotoEndOfWord(): wrong string")
2909 self
.assertNotEqual("a","b")
2911 class AttachHelper():
2912 def isattribute(self
): pass
2913 def mktreenode(self
): pass
2914 def mktextcontent(self
, inserter
, node
): pass
2915 def postinserted(self
, node
, xContent
): pass
2917 def test_meta_xtextattach_toxmark(self
):
2918 class Helper(self
.AttachHelper
):
2922 return DocumentIndexMarkNode(self
.mkname("toxmark"))
2923 def mktextcontent(_
, inserter
, node
):
2924 return inserter
.makedocumentindexmark(node
.name
)
2925 self
.do_meta_xtextattach(Helper())
2927 def test_meta_xtextattach_refmark(self
):
2928 class Helper(self
.AttachHelper
):
2932 return ReferenceMarkNode(self
.mkname("refmark"))
2933 def mktextcontent(_
, inserter
, node
):
2934 return inserter
.makereferencemark(node
.name
)
2935 self
.do_meta_xtextattach(Helper())
2937 def test_meta_xtextattach_textfield(self
):
2938 class Helper(self
.AttachHelper
):
2942 return TextFieldNode(self
.mkname("field"))
2943 def mktextcontent(_
, inserter
, node
):
2944 return inserter
.maketextfield(node
.content
)
2945 self
.do_meta_xtextattach(Helper())
2947 def test_meta_xtextattach_footnote(self
):
2948 class Helper(self
.AttachHelper
):
2952 return FootnoteNode(self
.mkname("ftn"))
2953 def mktextcontent(_
, inserter
, node
):
2954 return inserter
.makefootnote(node
.label
)
2955 self
.do_meta_xtextattach(Helper())
2957 def test_meta_xtextattach_meta(self
):
2958 class Helper(self
.AttachHelper
):
2962 return MetaNode(self
.mkid("id"))
2963 def mktextcontent(_
, inserter
, node
):
2964 return inserter
.makemeta()
2965 def postinserted(_
, node
, xContent
):
2966 xContent
.MetadataReference
= node
.xmlid
2967 self
.do_meta_xtextattach(Helper())
2969 def do_meta_xtextattach(self
, helper
):
2970 xDoc
= self
.__class
__.xDoc
2971 inserter
= RangeInserter(xDoc
)
2972 text
= TextNode("12AB6789")
2973 inserter
.insertrange(Range(0, 0, text
))
2974 met1
= MetaNode(self
.mkid("id"))
2975 xMeta
= inserter
.makemeta()
2977 xDocText
= xDoc
.getText()
2978 xDocTextCursor
= xDocText
.createTextCursor()
2979 xDocTextCursor
.goRight(3, False)
2980 xDocTextCursor
.goRight(2, True)
2981 xDocText
.insertTextContent(xDocTextCursor
, xMeta
, True)
2983 xMeta
.MetadataReference
= met1
.xmlid
2987 xStart
= xMeta
.getStart()
2988 xEnd
= xMeta
.getEnd()
2990 nod1
= helper
.mktreenode()
2991 nod2
= helper
.mktreenode()
2992 xContent1
= helper
.mktextcontent(inserter
, nod1
)
2993 xContent2
= helper
.mktextcontent(inserter
, nod2
)
2995 ## insertTextContent with meta getStart()/getEnd()
2996 xMeta
.insertTextContent(xStart
, xContent1
, False)
2997 xMeta
.insertTextContent(xEnd
, xContent2
, False)
2999 helper
.postinserted(nod1
, xContent1
)
3000 helper
.postinserted(nod2
, xContent2
)
3003 root
.appendchild(TextNode("12"))
3004 root
.appendchild(met1
.dup()
3005 .appendchild(nod1
.dup())
3006 .appendchild(TextNode("AB"))
3007 .appendchild(nod2
.dup()))
3008 root
.appendchild(TextNode("6789"))
3009 self
.dotest(root
, False)
3011 xMeta
.setString("AB")
3012 xStart
= xMeta
.getStart()
3013 xEnd
= xMeta
.getEnd()
3015 nod1
= helper
.mktreenode()
3016 nod2
= helper
.mktreenode()
3017 xContent1
= helper
.mktextcontent(inserter
, nod1
)
3018 xContent2
= helper
.mktextcontent(inserter
, nod2
)
3020 xTextCursor
= xMeta
.createTextCursor()
3021 xTextCursor
.gotoStart(False)
3023 ## insertTextContent with meta cursor
3024 xMeta
.insertTextContent(xTextCursor
, xContent1
, False)
3025 xTextCursor
.gotoEnd(False)
3026 xMeta
.insertTextContent(xTextCursor
, xContent2
, False)
3028 helper
.postinserted(nod1
, xContent1
)
3029 helper
.postinserted(nod2
, xContent2
)
3032 root
.appendchild(TextNode("12"))
3033 root
.appendchild(met1
.dup()
3034 .appendchild(nod1
.dup())
3035 .appendchild(TextNode("AB"))
3036 .appendchild(nod2
.dup()))
3037 root
.appendchild(TextNode("6789"))
3038 self
.dotest(root
, False)
3040 if not helper
.isattribute():
3041 # xMeta.setString("AB")
3042 xStart
= xMeta
.getStart()
3043 xEnd
= xMeta
.getEnd()
3045 nod1
= helper
.mktreenode()
3046 nod2
= helper
.mktreenode()
3047 xContent1
= helper
.mktextcontent(inserter
, nod1
)
3048 xContent2
= helper
.mktextcontent(inserter
, nod2
)
3050 xTextCursor
= xMeta
.createTextCursor()
3051 xTextCursor
.gotoStart(False)
3052 xTextCursor
.goRight(1, True)
3054 ## insertTextContent with meta cursor and absorb
3055 xMeta
.insertTextContent(xTextCursor
, xContent1
, True)
3056 xTextCursor
.gotoEnd(False)
3057 xTextCursor
.goLeft(1, True)
3058 xMeta
.insertTextContent(xTextCursor
, xContent2
, True)
3060 helper
.postinserted(nod1
, xContent1
)
3061 helper
.postinserted(nod2
, xContent2
)
3064 root
.appendchild(TextNode("12"))
3065 root
.appendchild(met1
.dup()
3066 .appendchild(nod1
.dup())
3067 .appendchild(TextNode("AB"))
3068 .appendchild(nod2
.dup()))
3069 root
.appendchild(TextNode("6789"))
3070 self
.dotest(root
, False)
3072 xMeta
.setString("AB")
3073 xStart
= xMeta
.getStart()
3074 xEnd
= xMeta
.getEnd()
3076 nod1
= helper
.mktreenode()
3077 nod2
= helper
.mktreenode()
3078 xContent1
= helper
.mktextcontent(inserter
, nod1
)
3079 xContent2
= helper
.mktextcontent(inserter
, nod2
)
3081 xDocTextCursor
.gotoRange(xStart
, False)
3083 ## insertTextContent with document cursor
3084 xMeta
.insertTextContent(xDocTextCursor
, xContent1
, False)
3085 xDocTextCursor
.gotoRange(xEnd
, False)
3086 xMeta
.insertTextContent(xDocTextCursor
, xContent2
, False)
3088 helper
.postinserted(nod1
, xContent1
)
3089 helper
.postinserted(nod2
, xContent2
)
3092 root
.appendchild(TextNode("12"))
3093 root
.appendchild(met1
.dup()
3094 .appendchild(nod1
.dup())
3095 .appendchild(TextNode("AB"))
3096 .appendchild(nod2
.dup()))
3097 root
.appendchild(TextNode("6789"))
3098 self
.dotest(root
, False)
3100 if not helper
.isattribute():
3101 xStart
= xMeta
.getStart()
3102 xEnd
= xMeta
.getEnd()
3104 nod1
= helper
.mktreenode()
3105 nod2
= helper
.mktreenode()
3106 xContent1
= helper
.mktextcontent(inserter
, nod1
)
3107 xContent2
= helper
.mktextcontent(inserter
, nod2
)
3109 xDocTextCursor
.gotoRange(xStart
, False)
3110 xDocTextCursor
.goRight(1, True)
3112 ## insertTextContent with document cursor and absorb
3113 xMeta
.insertTextContent(xDocTextCursor
, xContent1
, True)
3114 xDocTextCursor
.gotoRange(xEnd
, False)
3115 xDocTextCursor
.goLeft(1, True)
3116 xMeta
.insertTextContent(xDocTextCursor
, xContent2
, True)
3118 helper
.postinserted(nod1
, xContent1
)
3119 helper
.postinserted(nod2
, xContent2
)
3122 root
.appendchild(TextNode("12"))
3123 root
.appendchild(met1
.dup()
3124 .appendchild(nod1
.dup())
3125 .appendchild(TextNode("AB"))
3126 .appendchild(nod2
.dup()))
3127 root
.appendchild(TextNode("6789"))
3128 self
.dotest(root
, False)
3130 xMeta
.setString("AB")
3131 xStart
= xMeta
.getStart()
3132 xEnd
= xMeta
.getEnd()
3134 nod1
= helper
.mktreenode()
3135 nod2
= helper
.mktreenode()
3136 xContent1
= helper
.mktextcontent(inserter
, nod1
)
3137 xContent2
= helper
.mktextcontent(inserter
, nod2
)
3139 ## attach to range from meta getStart()/getEnd()
3140 xContent1
.attach(xStart
)
3141 xContent2
.attach(xEnd
)
3143 helper
.postinserted(nod1
, xContent1
)
3144 helper
.postinserted(nod2
, xContent2
)
3147 root
.appendchild(TextNode("12"))
3148 root
.appendchild(met1
.dup()
3149 .appendchild(nod1
.dup())
3150 .appendchild(TextNode("AB"))
3151 .appendchild(nod2
.dup()))
3152 root
.appendchild(TextNode("6789"))
3153 self
.dotest(root
, False)
3155 xMeta
.setString("AB")
3156 xStart
= xMeta
.getStart()
3157 xEnd
= xMeta
.getEnd()
3159 nod1
= helper
.mktreenode()
3160 nod2
= helper
.mktreenode()
3161 xContent1
= helper
.mktextcontent(inserter
, nod1
)
3162 xContent2
= helper
.mktextcontent(inserter
, nod2
)
3164 xTextCursor
= xMeta
.createTextCursor()
3165 xTextCursor
.gotoStart(False)
3167 ## attach to cursor from meta XText
3168 xContent1
.attach(xTextCursor
)
3169 xTextCursor
.gotoEnd(False)
3170 xContent2
.attach(xTextCursor
)
3172 helper
.postinserted(nod1
, xContent1
)
3173 helper
.postinserted(nod2
, xContent2
)
3176 root
.appendchild(TextNode("12"))
3177 root
.appendchild(met1
.dup()
3178 .appendchild(nod1
.dup())
3179 .appendchild(TextNode("AB"))
3180 .appendchild(nod2
.dup()))
3181 root
.appendchild(TextNode("6789"))
3182 self
.dotest(root
, False)
3184 def test_metafield_xtextfield(self
):
3185 xDoc
= self
.__class
__.xDoc
3186 smgr
= self
.__class
__._uno
.xContext
.ServiceManager
3187 xRepo
= xDoc
.getRDFRepository()
3188 ## for testing just add it to the first graph
3189 Graphs
= xRepo
.getGraphNames()
3190 xGraph
= xRepo
.getGraph(Graphs
[0])
3191 xOdfPrefix
= smgr
.createInstance("com.sun.star.rdf.URI")
3192 xOdfPrefix
.initialize((ODF_PREFIX
,))
3193 xOdfSuffix
= smgr
.createInstance("com.sun.star.rdf.URI")
3194 xOdfSuffix
.initialize((ODF_SUFFIX
,))
3196 xPrefix
= smgr
.createInstance("com.sun.star.rdf.Literal")
3197 xPrefix
.initialize(("foo",))
3198 xSuffix
= smgr
.createInstance("com.sun.star.rdf.Literal")
3199 xSuffix
.initialize(("bar",))
3201 inserter
= RangeInserter(xDoc
)
3202 text
= TextNode("abc")
3203 inserter
.insertrange(Range(0, 0, text
))
3204 xDocText
= xDoc
.getText()
3205 xDocTextCursor
= xDocText
.createTextCursor()
3206 xDocTextCursor
.goRight(1, False)
3207 xDocTextCursor
.goRight(3, True)
3209 xMetaField
= inserter
.makemetafield()
3211 xDocText
.insertTextContent(xDocTextCursor
, xMetaField
, True)
3213 xMetaField
.ensureMetadataReference
3215 xGraph
.addStatement(xMetaField
, xOdfPrefix
, xPrefix
)
3216 xGraph
.addStatement(xMetaField
, xOdfSuffix
, xSuffix
)
3217 self
.assertEqual("fooabcbar", xMetaField
.getPresentation(False),
3218 "getPresentation(): wrong")
3219 inserter
.insertrange(Range(0, 0, text
))
3221 def test_metafield_xpropertyset(self
):
3222 xDoc
= self
.__class
__.xDoc
3223 inserter
= RangeInserter(xDoc
)
3224 text
= TextNode("123")
3225 inserter
.insertrange(Range(0, 0, text
))
3226 xDocText
= xDoc
.getText()
3227 xDocTextCursor
= xDocText
.createTextCursor()
3228 xDocTextCursor
.goRight(1, False)
3229 xDocTextCursor
.goRight(3, True)
3231 xMetaField
= inserter
.makemetafield()
3233 xDocText
.insertTextContent(xDocTextCursor
, xMetaField
, True)
3235 self
.assertIsNotNone(xMetaField
, "PropertySet: not supported?")
3236 xPropertySetInfo
= xMetaField
.getPropertySetInfo()
3237 self
.assertTrue(xPropertySetInfo
.hasPropertyByName("NumberFormat"),
3238 'hasPropertyByName("NumberFormat"):')
3239 self
.assertTrue(xPropertySetInfo
.hasPropertyByName("IsFixedLanguage"),
3240 'hasPropertyByName("IsFixedLanguage"):')
3242 def_
= xMetaField
.NumberFormat
3243 print("NumberFormat: default is {}".format(def_
))
3244 xMetaField
.NumberFormat
= NUMBER_INT
3245 xMetaField
.IsFixedLanguage
= True
3246 format
= xMetaField
.NumberFormat
3247 self
.assertEqual(NUMBER_INT
, format
, "NumberFormat: failed")
3248 isfixed
= xMetaField
.IsFixedLanguage
3249 self
.assertTrue(isfixed
, "IsFixedLanguage: failed")
3251 def dostore(self
, xComp
, file):
3252 print("Storing test document...")
3253 file = uno
.systemPathToFileUrl(file)
3254 xComp
.storeToURL(file, ())
3257 def doload(self
, file):
3259 print("Loading test document...")
3260 xComp
= self
.__class
__._uno
.openDocFromAbsolutePath(file)
3261 self
.assertIsNotNone(xComp
, "cannot load: {}".format(file))
3265 def close(self
, i_comp
):
3269 except Exception as e
:
3272 def test_load_store(self
):
3274 filename
= "TESTMETA.odt"
3276 xComp
= self
.__class
__._uno
.openDocFromTDOC(filename
)
3278 self
.checkloadmeta(xComp
)
3279 with
TemporaryDirectory() as tempdir
:
3280 if os
.altsep
: # we need URL so replace "\" with "/"
3281 tempdir
= tempdir
.replace(os
.sep
, os
.altsep
)
3282 file = tempdir
+ "/" + filename
3283 self
.dostore(xComp
, file)
3287 xComp2
= self
.doload(file)
3288 self
.checkloadmeta(xComp2
)
3294 def checkloadmeta(self
, xTextDoc
):
3295 xText
= xTextDoc
.getText()
3296 print("Checking meta(-field)s in loaded test document...")
3298 root
.appendchild(RubyNode("ruby1")
3299 .appendchild(TextNode("1")))
3300 root
.appendchild(MetaNode(self
.mkid_("id1"))
3301 .appendchild(TextNode("2")))
3302 root
.appendchild(MetaFieldNode(self
.mkid_("id2"))
3303 .appendchild(TextNode("3")))
3304 root
.appendchild(RubyNode("ruby2")
3305 .appendchild(MetaNode(self
.mkid_("id3"))
3306 .appendchild(TextNode("4"))))
3307 root
.appendchild(RubyNode("ruby3")
3308 .appendchild(MetaFieldNode(self
.mkid_("id4"))
3309 .appendchild(TextNode("5"))))
3310 root
.appendchild(MetaNode(self
.mkid_("id5"))
3311 .appendchild(RubyNode("ruby4")
3312 .appendchild(TextNode("6"))))
3313 root
.appendchild(MetaFieldNode(self
.mkid_("id6"))
3314 .appendchild(RubyNode("ruby5")
3315 .appendchild(TextNode("7"))))
3316 root
.appendchild(MetaNode(self
.mkid_("id7"))
3317 .appendchild(MetaNode(self
.mkid_("id8"))
3318 .appendchild(TextNode("8"))))
3319 root
.appendchild(MetaNode(self
.mkid_("id9"))
3320 .appendchild(MetaFieldNode(self
.mkid_("id10"))
3321 .appendchild(TextNode("9"))))
3322 root
.appendchild(MetaFieldNode(self
.mkid_("id11"))
3323 .appendchild(MetaNode(self
.mkid_("id12"))
3324 .appendchild(TextNode("10"))))
3325 root
.appendchild(MetaFieldNode(self
.mkid_("id13"))
3326 .appendchild(MetaFieldNode(self
.mkid_("id14"))
3327 .appendchild(TextNode("11"))))
3328 root
.appendchild(MetaNode(self
.mkid_("id15"))
3329 .appendchild(RubyNode("ruby6")
3330 .appendchild(MetaFieldNode(self
.mkid_("id16"))
3331 .appendchild(TextNode("12")))))
3333 class MetaNode_(MetaNode
):
3334 def __init__(self
, id):
3335 super().__init
__(id)
3336 def __eq__(self
, other
):
3337 return isinstance(other
, MetaNode
)
3338 root
.appendchild(MetaNode_(self
.mkid_(""))
3339 .appendchild(TextNode("13")))
3340 root
.appendchild(TextNode(" X X "))
3341 self
._dotest
(xTextDoc
, root
, False)
3344 def test_load_store_xmlid(self
):
3346 filename
= "TESTXMLID.odt"
3348 xComp
= self
.__class
__._uno
.openDocFromTDOC(filename
)
3350 self
.checkloadxmlid(xComp
)
3351 with
TemporaryDirectory() as tempdir
:
3352 if os
.altsep
: # we need URL so replace "\" with "/"
3353 tempdir
= tempdir
.replace(os
.sep
, os
.altsep
)
3354 file = tempdir
+ "/" + filename
3355 self
.dostore(xComp
, file)
3359 xComp2
= self
.doload(file)
3360 self
.checkloadxmlid(xComp2
)
3366 def checkloadxmlid(self
, xTextDoc
):
3367 xText
= xTextDoc
.getText()
3368 xRepo
= xTextDoc
.getRDFRepository()
3370 print("Checking bookmarks in loaded test document...")
3371 xBookmarks
= xTextDoc
.getBookmarks()
3372 xMark1
= xBookmarks
["mk1"]
3373 self
.assertTrue(self
.eq(xMark1
.MetadataReference
,
3374 StringPair("content.xml", "id90")), "mark1")
3375 xMark2
= xBookmarks
["mk2"]
3376 result
= xRepo
.getStatementRDFa(xMark2
)
3377 self
.assertTrue(len(result
.First
) == 1 and
3378 result
.First
[0].Subject
.StringValue
== "uri:foo" and
3379 result
.First
[0].Predicate
.StringValue
== "uri:bar" and
3380 result
.First
[0].Object
.Value
== "a fooish bar",
3382 xMark3
= xBookmarks
["mk3"]
3383 self
.assertTrue(self
.eq(xMark3
.MetadataReference
,
3384 StringPair("content.xml", "id91")), "mark3")
3387 print("Checking sections in loaded test document...")
3388 xSections
= xTextDoc
.getTextSections()
3389 xSection1
= xSections
["Section 1"]
3390 self
.assertTrue(self
.eq(xSection1
.MetadataReference
,
3391 StringPair("content.xml", "idSection1")), "idsection1")
3392 xSection2
= xSections
["Section 2"]
3393 self
.assertTrue(self
.eq(xSection2
.MetadataReference
,
3394 StringPair("content.xml", "idSection2")),"idSection2")
3395 xSection3
= xSections
["Table of Contents1_Head"]
3396 self
.assertTrue(self
.eq(xSection3
.MetadataReference
,
3397 StringPair("content.xml", "idTOCTitle")), "idTOCTitle")
3398 xSection4
= xSections
["Alphabetical Index1_Head"]
3399 self
.assertTrue(self
.eq(xSection4
.MetadataReference
,
3400 StringPair("content.xml", "idAITitle")), "idAITitle")
3401 xSection5
= xSections
["Illustration Index1_Head"]
3402 self
.assertTrue(self
.eq(xSection5
.MetadataReference
,
3403 StringPair("content.xml", "idIITitle")), "idIITitle")
3404 xSection6
= xSections
["Index of Tables1_Head"]
3405 self
.assertTrue(self
.eq(xSection6
.MetadataReference
,
3406 StringPair("content.xml", "idIOTTitle")), "idIOTTitle")
3407 xSection7
= xSections
["User-Defined1_Head"]
3408 self
.assertTrue(self
.eq(xSection7
.MetadataReference
,
3409 StringPair("content.xml", "idUDTitle")), "idUDTitle")
3410 xSection8
= xSections
["Table of Objects1_Head"]
3411 self
.assertTrue(self
.eq(xSection8
.MetadataReference
,
3412 StringPair("content.xml", "idTOOTitle")), "idTOOTitle")
3413 xSection9
= xSections
["Bibliography1_Head"]
3414 self
.assertTrue(self
.eq(xSection9
.MetadataReference
,
3415 StringPair("content.xml", "idBibTitle")), "idBibTitle")
3418 print("Checking indexes in loaded test document...")
3419 xIndexes
= xTextDoc
.getDocumentIndexes()
3420 xIndex1
= xIndexes
["Table of Contents1"]
3421 self
.assertTrue(self
.eq(xIndex1
.MetadataReference
,
3422 StringPair("content.xml", "idTOC")), "idTOC")
3423 xIndex1s
= xSections
["Table of Contents1"]
3424 self
.assertTrue(self
.eq(xIndex1s
.MetadataReference
,
3425 StringPair("content.xml", "idTOC")), "idTOC")
3426 xIndex2
= xIndexes
["Alphabetical Index1"]
3427 self
.assertTrue(self
.eq(xIndex2
.MetadataReference
,
3428 StringPair("content.xml", "idAI")), "idAI")
3429 xIndex2s
= xSections
["Alphabetical Index1"]
3430 self
.assertTrue(self
.eq(xIndex2s
.MetadataReference
,
3431 StringPair("content.xml", "idAI")), "idAI")
3432 xIndex3
= xIndexes
["Illustration Index1"]
3433 self
.assertTrue(self
.eq(xIndex3
.MetadataReference
,
3434 StringPair("content.xml", "idII")), "idII")
3435 xIndex3s
= xSections
["Table of Figures1"]
3436 self
.assertTrue(self
.eq(xIndex3s
.MetadataReference
,
3437 StringPair("content.xml", "idII")), "idII")
3438 xIndex4
= xIndexes
["Index of Tables1"]
3439 self
.assertTrue(self
.eq(xIndex4
.MetadataReference
,
3440 StringPair("content.xml", "idIOT")), "idIOT")
3441 xIndex4s
= xSections
["Index of Tables1"]
3442 self
.assertTrue(self
.eq(xIndex4s
.MetadataReference
,
3443 StringPair("content.xml", "idIOT")), "idIOT")
3444 xIndex5
= xIndexes
["User-Defined1"]
3445 self
.assertTrue(self
.eq(xIndex5
.MetadataReference
,
3446 StringPair("content.xml", "idUD")), "idUD")
3447 xIndex5s
= xSections
["User-Defined1"]
3448 self
.assertTrue(self
.eq(xIndex5s
.MetadataReference
,
3449 StringPair("content.xml", "idUD")), "idUD")
3450 xIndex6
= xIndexes
["Table of Objects1"]
3451 self
.assertTrue(self
.eq(xIndex6
.MetadataReference
,
3452 StringPair("content.xml", "idTOO")), "idTOO")
3453 xIndex6s
= xSections
["Table of Objects1"]
3454 self
.assertTrue(self
.eq(xIndex6s
.MetadataReference
,
3455 StringPair("content.xml", "idTOO")), "idTOO")
3456 xIndex7
= xIndexes
["Bibliography1"]
3457 self
.assertTrue(self
.eq(xIndex7
.MetadataReference
,
3458 StringPair("content.xml", "idBib")), "idBib")
3459 xIndex7s
= xSections
["Bibliography1"]
3460 self
.assertTrue(self
.eq(xIndex7s
.MetadataReference
,
3461 StringPair("content.xml", "idBib")), "idBib")
3464 def dotest(self
, intree
, insert
=True):
3465 xDoc
= self
.__class
__.xDoc
3466 self
._dotest
(xDoc
, intree
, insert
)
3468 def _dotest(self
, xDoc
, intree
, insert
):
3469 self
._dumptree
(intree
, "I: ")
3471 TreeInserter(xDoc
).inserttree(intree
)
3472 xText
= xDoc
.getText()
3473 xTextEnum
= xText
.createEnumeration()
3474 ## skip to right paragraph
3475 xTextEnum
.nextElement(); # skip first -- always empty!
3476 xElement
= xTextEnum
.nextElement() # second contains test case
3477 xEnum
= xElement
.createEnumeration()
3478 outtree
= EnumConverter().convert(xEnum
)
3479 self
._dumptree
(outtree
, "O: ")
3480 FuzzyTester().dotest(intree
, outtree
)
3482 def _dumptree(self
, tree
, prefix
):
3483 print('{}{}'.format(prefix
, str(tree
)))
3484 children
= tree
.createenumeration()
3485 for node
in children
:
3486 self
._dumptree
(node
, "{} ".format(prefix
))
3488 def mkname(self
, prefix
):
3489 self
.__class
__.count
+= 1
3490 return "{}{}".format(prefix
, self
.__class
__.count
)
3492 def mkid(self
, prefix
):
3493 id = self
.mkname(prefix
)
3494 return StringPair("content.xml", self
.mkname(prefix
))
3496 def mkid_(self
, id):
3497 return StringPair("content.xml", id)
3499 def eq(self
, left
, right
):
3500 return (left
.First
== right
.First
and
3501 left
.Second
== right
.Second
)
3504 if __name__
== '__main__':