From d45945989f35cd37e20239219fab895fea900540 Mon Sep 17 00:00:00 2001 From: Pavel Lobashov Date: Thu, 8 Sep 2016 15:26:40 +0300 Subject: [PATCH] Add Parsing `NumberingLevel#suffix` --- Changelog.md | 1 + .../docx_data/document_structure.rb | 2 +- .../docx_data/document_structure/numbering.rb | 12 +++---- .../numbering/abstract_numbering.rb | 17 +++++----- .../abstract_numbering/numbering_level.rb | 32 +++++++++++------- .../numbering_level/suffix.rb | 31 +++++++++++++++++ .../numbering/numbering_definition.rb | 12 +++---- .../abstract_numbering_id.rb | 10 +++--- .../paragraph/numbering/numbering_suffix.docx | Bin 0 -> 10494 bytes .../elements/paragraph/numbering_spec.rb | 5 +++ 10 files changed, 81 insertions(+), 41 deletions(-) create mode 100644 lib/ooxml_parser/docx_parser/docx_data/document_structure/numbering/abstract_numbering/numbering_level/suffix.rb create mode 100644 spec/document/elements/paragraph/numbering/numbering_suffix.docx diff --git a/Changelog.md b/Changelog.md index 523c74c4..340b0e51 100644 --- a/Changelog.md +++ b/Changelog.md @@ -36,6 +36,7 @@ * `ParagraphTab` now stored in `Tabs` in `ParagraphProperties` * Add `OoxmlSize` support of `one_240th_cm` and use in `Spacing` * Add parsing `PresetColor` to `GradientStop` +* Add Parsing `NumberingLevel#suffix` ### Fixes * Fix parsing document style id - it can be string, not only digit diff --git a/lib/ooxml_parser/docx_parser/docx_data/document_structure.rb b/lib/ooxml_parser/docx_parser/docx_data/document_structure.rb index ea6c9ec2..65d132fa 100644 --- a/lib/ooxml_parser/docx_parser/docx_data/document_structure.rb +++ b/lib/ooxml_parser/docx_parser/docx_data/document_structure.rb @@ -130,7 +130,7 @@ def self.parse end parse_default_style doc_structure = DocumentStructure.new - doc_structure.numbering = Numbering.parse + doc_structure.numbering = Numbering.new(parent: doc_structure).parse doc_structure.document_styles = DocumentStyle.parse_list(doc_structure) number = 0 OOXMLDocumentObject.add_to_xmls_stack('word/document.xml') diff --git a/lib/ooxml_parser/docx_parser/docx_data/document_structure/numbering.rb b/lib/ooxml_parser/docx_parser/docx_data/document_structure/numbering.rb index fc06cf8a..b02c8614 100644 --- a/lib/ooxml_parser/docx_parser/docx_data/document_structure/numbering.rb +++ b/lib/ooxml_parser/docx_parser/docx_data/document_structure/numbering.rb @@ -8,9 +8,10 @@ class Numbering < OOXMLDocumentObject # @return [Array, NumberingDefinition] numbering definition list attr_accessor :numbering_definition_list - def initialize + def initialize(parent: nil) @abstract_numbering_list = [] @numbering_definition_list = [] + @parent = parent end def properties_by_num_id(num_id) @@ -26,20 +27,19 @@ def properties_by_num_id(num_id) end end - def self.parse - numbering = Numbering.new + def parse numbering_xml = OOXMLDocumentObject.path_to_folder + 'word/numbering.xml' return nil unless File.exist?(numbering_xml) node = Nokogiri::XML(File.open(numbering_xml), 'r:UTF-8') node.xpath('w:numbering/*').each do |numbering_child_node| case numbering_child_node.name when 'abstractNum' - numbering.abstract_numbering_list << AbstractNumbering.parse(numbering_child_node) + @abstract_numbering_list << AbstractNumbering.new(parent: self).parse(numbering_child_node) when 'num' - numbering.numbering_definition_list << NumberingDefinition.parse(numbering_child_node) + @numbering_definition_list << NumberingDefinition.new(parent: self).parse(numbering_child_node) end end - numbering + self end end end diff --git a/lib/ooxml_parser/docx_parser/docx_data/document_structure/numbering/abstract_numbering.rb b/lib/ooxml_parser/docx_parser/docx_data/document_structure/numbering/abstract_numbering.rb index 1b8f8b41..69697a13 100644 --- a/lib/ooxml_parser/docx_parser/docx_data/document_structure/numbering/abstract_numbering.rb +++ b/lib/ooxml_parser/docx_parser/docx_data/document_structure/numbering/abstract_numbering.rb @@ -4,7 +4,7 @@ module OoxmlParser # This element specifies a set of properties which shall dictate the appearance and # behavior of a set of numbered # paragraphs in a WordprocessingML document. - class AbstractNumbering + class AbstractNumbering < OOXMLDocumentObject # @return [Integer] abstruct numbering id attr_accessor :id # @return [MultilevelType] myltylevel type @@ -12,32 +12,31 @@ class AbstractNumbering # @return [Array, NumberingLevel] numbering level data list attr_accessor :level_list - def initialize + def initialize(parent: nil) @level_list = [] + @parent = parent end # Parse Abstract Numbering data # @param [Nokogiri::XML:Element] node with Abstract Numbering data # @return [AbstractNumbering] value of Abstract Numbering data - def self.parse(node) - abstract_numbering = AbstractNumbering.new - + def parse(node) node.attributes.each do |key, value| case key when 'abstractNumId' - abstract_numbering.id = value.value.to_f + @id = value.value.to_f end end node.xpath('*').each do |numbering_child_node| case numbering_child_node.name when 'multiLevelType' - abstract_numbering.multilevel_type = MultilevelType.new(parent: abstract_numbering).parse(numbering_child_node) + @multilevel_type = MultilevelType.new(parent: self).parse(numbering_child_node) when 'lvl' - abstract_numbering.level_list << NumberingLevel.parse(numbering_child_node) + @level_list << NumberingLevel.new(parent: self).parse(numbering_child_node) end end - abstract_numbering + self end end end diff --git a/lib/ooxml_parser/docx_parser/docx_data/document_structure/numbering/abstract_numbering/numbering_level.rb b/lib/ooxml_parser/docx_parser/docx_data/document_structure/numbering/abstract_numbering/numbering_level.rb index 65ef402a..955d2739 100644 --- a/lib/ooxml_parser/docx_parser/docx_data/document_structure/numbering/abstract_numbering/numbering_level.rb +++ b/lib/ooxml_parser/docx_parser/docx_data/document_structure/numbering/abstract_numbering/numbering_level.rb @@ -2,10 +2,11 @@ require_relative 'numbering_level/level_text' require_relative 'numbering_level/numbering_format' require_relative 'numbering_level/start' +require_relative 'numbering_level/suffix' module OoxmlParser # This element specifies the appearance and behavior of a numbering level # within a given abstract numbering - class NumberingLevel + class NumberingLevel < OOXMLDocumentObject # @return [Integer] level id attr_accessor :ilvl # @return [Start] start data @@ -20,38 +21,45 @@ class NumberingLevel attr_accessor :paragraph_properties # @return [RunProperties] properties of run attr_accessor :run_properties + # @return [Suffix] value of Suffix + attr_accessor :suffix + + def initialize(parent: nil) + @parent = parent + @suffix = Suffix.new(parent: self) + end # Parse Numbering Level data # @param [Nokogiri::XML:Element] node with Numbering Level data # @return [NumberingLevel] value of Numbering Level data - def self.parse(node) - level = NumberingLevel.new - + def parse(node) node.attributes.each do |key, value| case key when 'ilvl' - level.ilvl = value.value.to_f + @ilvl = value.value.to_f end end node.xpath('*').each do |num_level_child| case num_level_child.name when 'start' - level.start = Start.parse(num_level_child) + @start = Start.parse(num_level_child) when 'numFmt' - level.numbering_format = NumberingFormat.parse(num_level_child) + @numbering_format = NumberingFormat.parse(num_level_child) when 'lvlText' - level.text = LevelText.parse(num_level_child) + @text = LevelText.parse(num_level_child) when 'lvlJc' - level.justification = LevelJustification.parse(num_level_child) + @justification = LevelJustification.parse(num_level_child) when 'pPr' - level.paragraph_properties = ParagraphProperties.new(parent: level).parse(num_level_child) + @paragraph_properties = ParagraphProperties.new(parent: self).parse(num_level_child) when 'rPr' - level.run_properties = RunProperties.new(parent: level).parse(num_level_child) + @run_properties = RunProperties.new(parent: self).parse(num_level_child) + when 'suff' + @suffix = @suffix.parse(num_level_child) end end - level + self end end end diff --git a/lib/ooxml_parser/docx_parser/docx_data/document_structure/numbering/abstract_numbering/numbering_level/suffix.rb b/lib/ooxml_parser/docx_parser/docx_data/document_structure/numbering/abstract_numbering/numbering_level/suffix.rb new file mode 100644 index 00000000..f385b8ba --- /dev/null +++ b/lib/ooxml_parser/docx_parser/docx_data/document_structure/numbering/abstract_numbering/numbering_level/suffix.rb @@ -0,0 +1,31 @@ +module OoxmlParser + # Class for storing Suffix `w:suff` + # This element specifies the content which + # shall be added between a given numbering level's text and the text of + # every numbered paragraph which references that numbering level. + # If this element is omitted, then its value shall be assumed to be tab. + # >ECMA-376, 3rd Edition (June, 2011), Fundamentals and Markup Language Reference 17.9.29. + class Suffix < OOXMLDocumentObject + # @return [String] value of suffix + attr_accessor :value + + def initialize(value = :tab, + parent: nil) + @value = value + @parent = parent + end + + # Parse Suffix + # @param [Nokogiri::XML:Node] node with Suffix + # @return [Suffix] result of parsing + def parse(node) + node.attributes.each do |key, value| + case key + when 'val' + @value = value.value.to_sym + end + end + self + end + end +end diff --git a/lib/ooxml_parser/docx_parser/docx_data/document_structure/numbering/numbering_definition.rb b/lib/ooxml_parser/docx_parser/docx_data/document_structure/numbering/numbering_definition.rb index b10ffe63..02ac5f6e 100644 --- a/lib/ooxml_parser/docx_parser/docx_data/document_structure/numbering/numbering_definition.rb +++ b/lib/ooxml_parser/docx_parser/docx_data/document_structure/numbering/numbering_definition.rb @@ -2,7 +2,7 @@ module OoxmlParser # This element specifies a unique instance of numbering information that can be referenced by zero or more # paragraphs within the parent WordprocessingML document. - class NumberingDefinition + class NumberingDefinition < OOXMLDocumentObject # @return [Integer] num id attr_accessor :id # @return [AbstractNumberingId] abstract numbering id @@ -11,23 +11,21 @@ class NumberingDefinition # Parse NumberingDefinition data # @param [Nokogiri::XML:Element] node with NumberingDefinition data # @return [NumberingDefinition] value of Abstract Numbering data - def self.parse(node) - num = NumberingDefinition.new - + def parse(node) node.attributes.each do |key, value| case key when 'numId' - num.id = value.value.to_f + @id = value.value.to_f end end node.xpath('*').each do |numbering_child_node| case numbering_child_node.name when 'abstractNumId' - num.abstract_numbering_id = AbstractNumberingId.parse(numbering_child_node) + @abstract_numbering_id = AbstractNumberingId.new(parent: self).parse(numbering_child_node) end end - num + self end end end diff --git a/lib/ooxml_parser/docx_parser/docx_data/document_structure/numbering/numbering_definition/abstract_numbering_id.rb b/lib/ooxml_parser/docx_parser/docx_data/document_structure/numbering/numbering_definition/abstract_numbering_id.rb index 52b0fbcc..51f51b47 100644 --- a/lib/ooxml_parser/docx_parser/docx_data/document_structure/numbering/numbering_definition/abstract_numbering_id.rb +++ b/lib/ooxml_parser/docx_parser/docx_data/document_structure/numbering/numbering_definition/abstract_numbering_id.rb @@ -1,22 +1,20 @@ module OoxmlParser # Class for storing AbstractNumberingId - class AbstractNumberingId + class AbstractNumberingId < OOXMLDocumentObject # @return [String] value of start attr_accessor :value # Parse AbstractNumberingId # @param [Nokogiri::XML:Node] node with AbstractNumberingId # @return [AbstractNumberingId] result of parsing - def self.parse(node) - abstract_id = AbstractNumberingId.new - + def parse(node) node.attributes.each do |key, value| case key when 'val' - abstract_id.value = value.value.to_i + @value = value.value.to_i end end - abstract_id + self end end end diff --git a/spec/document/elements/paragraph/numbering/numbering_suffix.docx b/spec/document/elements/paragraph/numbering/numbering_suffix.docx new file mode 100644 index 0000000000000000000000000000000000000000..6a86ac8de8859aeabe4644998935f75d675102d3 GIT binary patch literal 10494 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 literal 0 HcmV?d00001 diff --git a/spec/document/elements/paragraph/numbering_spec.rb b/spec/document/elements/paragraph/numbering_spec.rb index 98bcb74b..5c656bd2 100644 --- a/spec/document/elements/paragraph/numbering_spec.rb +++ b/spec/document/elements/paragraph/numbering_spec.rb @@ -41,4 +41,9 @@ docx = OoxmlParser::DocxParser.parse_docx('spec/document/elements/paragraph/numbering/numbering_in_table.docx') expect(docx.element_by_description(location: :canvas, type: :table).first.numbering.abstruct_numbering.level_list.first.text.value).to eq('ยจ') end + + it 'numbering_suffix' do + docx = OoxmlParser::Parser.parse('spec/document/elements/paragraph/numbering/numbering_suffix.docx') + expect(docx.element_by_description.first.numbering.abstruct_numbering.level_list.first.suffix.value).to eq(:space) + end end