Impl comment reader (#212)
* feat: Impl comments reader * feat: Impl comment extended reader * feat: Fixup comment reader * feat: Update snaps * faet: Update snaps * fix: comment overwritten bug * fix: parent comment id seeker * fix: update js reader snapsmain
parent
e346121dee
commit
089772a12c
|
@ -7,7 +7,6 @@ pub fn main() {
|
|||
let mut file = File::open("./test.docx").unwrap();
|
||||
let mut buf = vec![];
|
||||
file.read_to_end(&mut buf).unwrap();
|
||||
dbg!(read_docx(&buf).unwrap().json());
|
||||
|
||||
let mut file = File::create("./test.json").unwrap();
|
||||
let res = read_docx(&buf).unwrap().json();
|
||||
|
|
|
@ -7,13 +7,22 @@ use serde::Serialize;
|
|||
#[derive(Debug, Clone, PartialEq, Serialize)]
|
||||
#[serde(rename_all = "camelCase")]
|
||||
pub struct Comments {
|
||||
comments: Vec<Comment>,
|
||||
pub(crate) comments: Vec<Comment>,
|
||||
}
|
||||
|
||||
impl Comments {
|
||||
pub fn new() -> Self {
|
||||
Default::default()
|
||||
}
|
||||
|
||||
pub fn inner(&self) -> &[Comment] {
|
||||
&self.comments
|
||||
}
|
||||
|
||||
pub fn into_inner(self) -> Vec<Comment> {
|
||||
self.comments
|
||||
}
|
||||
|
||||
pub(crate) fn add_comments(&mut self, comments: Vec<Comment>) {
|
||||
self.comments = comments;
|
||||
}
|
||||
|
|
|
@ -5,11 +5,10 @@ use crate::documents::BuildXML;
|
|||
use crate::xml_builder::*;
|
||||
|
||||
// i.e. <w15:commentEx w15:paraId="00000001" w15:paraIdParent="57D1BD7C" w15:done="0"/>
|
||||
|
||||
#[derive(Debug, Clone, PartialEq, Serialize)]
|
||||
#[serde(rename_all = "camelCase")]
|
||||
pub struct CommentsExtended {
|
||||
children: Vec<CommentExtended>,
|
||||
pub children: Vec<CommentExtended>,
|
||||
}
|
||||
|
||||
impl CommentsExtended {
|
||||
|
|
|
@ -4,6 +4,7 @@ use crate::documents::{BuildXML, Paragraph};
|
|||
use crate::xml_builder::*;
|
||||
|
||||
#[derive(Serialize, Debug, Clone, PartialEq)]
|
||||
#[serde(rename_all = "camelCase")]
|
||||
pub struct Comment {
|
||||
pub id: usize,
|
||||
pub author: String,
|
||||
|
|
|
@ -6,9 +6,9 @@ use crate::xml_builder::*;
|
|||
#[derive(Debug, Clone, PartialEq, Serialize)]
|
||||
#[serde(rename_all = "camelCase")]
|
||||
pub struct CommentExtended {
|
||||
paragraph_id: String,
|
||||
done: bool,
|
||||
parent_paragraph_id: Option<String>,
|
||||
pub paragraph_id: String,
|
||||
pub done: bool,
|
||||
pub parent_paragraph_id: Option<String>,
|
||||
}
|
||||
|
||||
impl CommentExtended {
|
||||
|
@ -38,3 +38,23 @@ impl BuildXML for CommentExtended {
|
|||
.build()
|
||||
}
|
||||
}
|
||||
|
||||
#[cfg(test)]
|
||||
mod tests {
|
||||
|
||||
use super::*;
|
||||
#[cfg(test)]
|
||||
use pretty_assertions::assert_eq;
|
||||
#[test]
|
||||
fn test_comment_extended_json() {
|
||||
let ex = CommentExtended {
|
||||
paragraph_id: "00002".to_owned(),
|
||||
done: false,
|
||||
parent_paragraph_id: Some("0004".to_owned()),
|
||||
};
|
||||
assert_eq!(
|
||||
serde_json::to_string(&ex).unwrap(),
|
||||
r#"{"paragraphId":"00002","done":false,"parentParagraphId":"0004"}"#
|
||||
);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -6,8 +6,8 @@ use crate::xml_builder::*;
|
|||
|
||||
#[derive(Serialize, Debug, Clone, PartialEq)]
|
||||
pub struct CommentRangeStart {
|
||||
id: usize,
|
||||
comment: Comment,
|
||||
pub id: usize,
|
||||
pub comment: Comment,
|
||||
}
|
||||
|
||||
impl CommentRangeStart {
|
||||
|
@ -18,9 +18,17 @@ impl CommentRangeStart {
|
|||
}
|
||||
}
|
||||
|
||||
pub(crate) fn comment(&self) -> Comment {
|
||||
pub(crate) fn comment(&mut self, comment: Comment) {
|
||||
self.comment = comment;
|
||||
}
|
||||
|
||||
pub(crate) fn get_comment(&self) -> Comment {
|
||||
self.comment.clone()
|
||||
}
|
||||
|
||||
pub(crate) fn get_id(&self) -> usize {
|
||||
self.id
|
||||
}
|
||||
}
|
||||
|
||||
impl BuildXML for CommentRangeStart {
|
||||
|
|
|
@ -87,10 +87,16 @@ impl Serialize for ParagraphChild {
|
|||
t.serialize_field("data", r)?;
|
||||
t.end()
|
||||
}
|
||||
// TODO: Add comment later
|
||||
_ => {
|
||||
let mut t = serializer.serialize_struct("Unsupported", 2)?;
|
||||
t.serialize_field("type", "unsupported")?;
|
||||
ParagraphChild::CommentStart(ref r) => {
|
||||
let mut t = serializer.serialize_struct("CommentRangeStart", 2)?;
|
||||
t.serialize_field("type", "commentRangeStart")?;
|
||||
t.serialize_field("data", r)?;
|
||||
t.end()
|
||||
}
|
||||
ParagraphChild::CommentEnd(ref r) => {
|
||||
let mut t = serializer.serialize_struct("CommentRangeEnd", 2)?;
|
||||
t.serialize_field("type", "commentRangeEnd")?;
|
||||
t.serialize_field("data", r)?;
|
||||
t.end()
|
||||
}
|
||||
}
|
||||
|
@ -102,6 +108,11 @@ impl Paragraph {
|
|||
Default::default()
|
||||
}
|
||||
|
||||
pub fn id(mut self, id: impl Into<String>) -> Self {
|
||||
self.id = id.into();
|
||||
self
|
||||
}
|
||||
|
||||
pub fn children(&self) -> &Vec<ParagraphChild> {
|
||||
&self.children
|
||||
}
|
||||
|
|
|
@ -134,6 +134,16 @@ impl Docx {
|
|||
self
|
||||
}
|
||||
|
||||
pub fn comments(mut self, c: Comments) -> Self {
|
||||
self.comments = c;
|
||||
self
|
||||
}
|
||||
|
||||
pub fn comments_extended(mut self, c: CommentsExtended) -> Self {
|
||||
self.comments_extended = c;
|
||||
self
|
||||
}
|
||||
|
||||
pub fn add_paragraph(mut self, p: Paragraph) -> Docx {
|
||||
if p.has_numbering {
|
||||
// If this document has numbering, set numberings.xml to document_rels.
|
||||
|
@ -253,7 +263,6 @@ impl Docx {
|
|||
}
|
||||
|
||||
pub fn json(&mut self) -> String {
|
||||
self.update_comments();
|
||||
serde_json::to_string_pretty(&self).unwrap()
|
||||
}
|
||||
|
||||
|
@ -268,7 +277,7 @@ impl Docx {
|
|||
DocumentChild::Paragraph(paragraph) => {
|
||||
for child in ¶graph.children {
|
||||
if let ParagraphChild::CommentStart(c) = child {
|
||||
let comment = c.comment();
|
||||
let comment = c.get_comment();
|
||||
let para_id = comment.paragraph.id.clone();
|
||||
comment_map.insert(comment.id(), para_id.clone());
|
||||
}
|
||||
|
@ -282,7 +291,7 @@ impl Docx {
|
|||
TableCellContent::Paragraph(paragraph) => {
|
||||
for child in ¶graph.children {
|
||||
if let ParagraphChild::CommentStart(c) = child {
|
||||
let comment = c.comment();
|
||||
let comment = c.get_comment();
|
||||
let para_id = comment.paragraph.id.clone();
|
||||
comment_map.insert(comment.id(), para_id.clone());
|
||||
}
|
||||
|
@ -302,9 +311,9 @@ impl Docx {
|
|||
DocumentChild::Paragraph(paragraph) => {
|
||||
for child in ¶graph.children {
|
||||
if let ParagraphChild::CommentStart(c) = child {
|
||||
let comment = c.comment();
|
||||
let comment = c.get_comment();
|
||||
let para_id = comment.paragraph.id.clone();
|
||||
comments.push(c.comment());
|
||||
comments.push(c.get_comment());
|
||||
let comment_extended = CommentExtended::new(para_id);
|
||||
if let Some(parent_comment_id) = comment.parent_comment_id {
|
||||
let parent_para_id =
|
||||
|
@ -325,9 +334,9 @@ impl Docx {
|
|||
TableCellContent::Paragraph(paragraph) => {
|
||||
for child in ¶graph.children {
|
||||
if let ParagraphChild::CommentStart(c) = child {
|
||||
let comment = c.comment();
|
||||
let comment = c.get_comment();
|
||||
let para_id = comment.paragraph.id.clone();
|
||||
comments.push(c.comment());
|
||||
comments.push(c.get_comment());
|
||||
let comment_extended =
|
||||
CommentExtended::new(para_id);
|
||||
if let Some(parent_comment_id) =
|
||||
|
@ -367,6 +376,53 @@ impl Docx {
|
|||
self.comments.add_comments(comments);
|
||||
}
|
||||
|
||||
// Traverse and clone comments from document and add to comments node.
|
||||
pub(crate) fn store_comments(&mut self, comments: &[Comment]) {
|
||||
for child in &mut self.document.children {
|
||||
match child {
|
||||
DocumentChild::Paragraph(paragraph) => {
|
||||
for child in &mut paragraph.children {
|
||||
if let ParagraphChild::CommentStart(ref mut c) = child {
|
||||
let comment_id = c.get_id();
|
||||
if let Some(comment) = comments.iter().find(|c| c.id() == comment_id) {
|
||||
let comment = comment.clone();
|
||||
c.as_mut().comment(comment);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
DocumentChild::Table(table) => {
|
||||
for row in &mut table.rows {
|
||||
for cell in &mut row.cells {
|
||||
for content in &mut cell.children {
|
||||
match content {
|
||||
TableCellContent::Paragraph(paragraph) => {
|
||||
for child in &mut paragraph.children {
|
||||
if let ParagraphChild::CommentStart(ref mut c) = child {
|
||||
let comment_id = c.get_id();
|
||||
if let Some(comment) =
|
||||
comments.iter().find(|c| c.id() == comment_id)
|
||||
{
|
||||
let comment = comment.clone();
|
||||
c.as_mut().comment(comment);
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
_ => {}
|
||||
}
|
||||
}
|
||||
|
||||
if !comments.is_empty() {
|
||||
self.document_rels.has_comments = true;
|
||||
}
|
||||
}
|
||||
|
||||
// Traverse and collect images from document.
|
||||
fn create_images(&mut self) -> (Vec<usize>, Vec<(usize, Vec<u8>)>) {
|
||||
let mut image_ids: Vec<usize> = vec![];
|
||||
|
|
|
@ -1,8 +1,12 @@
|
|||
use xml::attribute::OwnedAttribute;
|
||||
|
||||
pub fn is_false(v: &str) -> bool {
|
||||
v == "0" || v == "false"
|
||||
}
|
||||
|
||||
pub fn read_bool(attrs: &[OwnedAttribute]) -> bool {
|
||||
if let Some(v) = attrs.get(0) {
|
||||
if &v.value == "0" || &v.value == "false" {
|
||||
if is_false(&v.value) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -13,3 +13,15 @@ pub use indent_level::*;
|
|||
pub use name::*;
|
||||
pub use val::*;
|
||||
pub use width::*;
|
||||
|
||||
use xml::attribute::OwnedAttribute;
|
||||
|
||||
pub fn read(attrs: &[OwnedAttribute], target: &str) -> Option<String> {
|
||||
for a in attrs {
|
||||
let local_name = &a.name.local_name;
|
||||
if local_name == target {
|
||||
return Some(a.value.to_owned());
|
||||
}
|
||||
}
|
||||
None
|
||||
}
|
||||
|
|
|
@ -0,0 +1,46 @@
|
|||
use std::io::Read;
|
||||
use std::str::FromStr;
|
||||
|
||||
use xml::attribute::OwnedAttribute;
|
||||
use xml::reader::{EventReader, XmlEvent};
|
||||
|
||||
use super::*;
|
||||
|
||||
impl ElementReader for Comment {
|
||||
fn read<R: Read>(
|
||||
r: &mut EventReader<R>,
|
||||
attrs: &[OwnedAttribute],
|
||||
) -> Result<Self, ReaderError> {
|
||||
let id = usize::from_str(&read(attrs, "id").expect("should comment id exists."))?;
|
||||
let mut comment = Comment::new(id);
|
||||
if let Some(author) = read(attrs, "author") {
|
||||
comment = comment.author(author);
|
||||
};
|
||||
if let Some(date) = read(attrs, "date") {
|
||||
comment = comment.date(date);
|
||||
}
|
||||
loop {
|
||||
let e = r.next();
|
||||
match e {
|
||||
Ok(XmlEvent::StartElement {
|
||||
name, attributes, ..
|
||||
}) => {
|
||||
let e = XMLElement::from_str(&name.local_name)
|
||||
.expect("should convert to XMLElement");
|
||||
if let XMLElement::Paragraph = e {
|
||||
let p = Paragraph::read(r, &attributes)?;
|
||||
comment = comment.paragraph(p);
|
||||
}
|
||||
}
|
||||
Ok(XmlEvent::EndElement { name, .. }) => {
|
||||
let e = XMLElement::from_str(&name.local_name).unwrap();
|
||||
if e == XMLElement::Comment {
|
||||
return Ok(comment);
|
||||
}
|
||||
}
|
||||
Err(_) => return Err(ReaderError::XMLReadError),
|
||||
_ => {}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
|
@ -0,0 +1,25 @@
|
|||
use std::io::Read;
|
||||
|
||||
use xml::attribute::OwnedAttribute;
|
||||
use xml::reader::EventReader;
|
||||
|
||||
use super::*;
|
||||
|
||||
impl ElementReader for CommentExtended {
|
||||
fn read<R: Read>(
|
||||
_r: &mut EventReader<R>,
|
||||
attrs: &[OwnedAttribute],
|
||||
) -> Result<Self, ReaderError> {
|
||||
let para_id = read(attrs, "paraId").expect("should comment id exists.");
|
||||
let mut comment_extended = CommentExtended::new(para_id);
|
||||
if let Some(done) = read(attrs, "done") {
|
||||
if !is_false(&done) {
|
||||
comment_extended = comment_extended.done();
|
||||
}
|
||||
};
|
||||
if let Some(parent_id) = read(attrs, "paraIdParent") {
|
||||
comment_extended = comment_extended.parent_paragraph_id(parent_id);
|
||||
}
|
||||
Ok(comment_extended)
|
||||
}
|
||||
}
|
|
@ -0,0 +1,38 @@
|
|||
use std::io::Read;
|
||||
use std::str::FromStr;
|
||||
|
||||
use xml::reader::{EventReader, XmlEvent};
|
||||
|
||||
use super::*;
|
||||
|
||||
impl FromXML for Comments {
|
||||
fn from_xml<R: Read>(reader: R) -> Result<Self, ReaderError> {
|
||||
let mut r = EventReader::new(reader);
|
||||
let mut comments: Vec<Comment> = vec![];
|
||||
loop {
|
||||
let e = r.next();
|
||||
match e {
|
||||
Ok(XmlEvent::StartElement {
|
||||
name, attributes, ..
|
||||
}) => {
|
||||
let e = XMLElement::from_str(&name.local_name)
|
||||
.expect("should convert to XMLElement");
|
||||
if let XMLElement::Comment = e {
|
||||
comments.push(Comment::read(&mut r, &attributes)?);
|
||||
}
|
||||
}
|
||||
Ok(XmlEvent::EndElement { name, .. }) => {
|
||||
let e = XMLElement::from_str(&name.local_name).unwrap();
|
||||
if e == XMLElement::Comments {
|
||||
return Ok(Comments { comments });
|
||||
}
|
||||
}
|
||||
Ok(XmlEvent::EndDocument { .. }) => {
|
||||
return Ok(Comments { comments });
|
||||
}
|
||||
Err(_) => return Err(ReaderError::XMLReadError),
|
||||
_ => {}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
|
@ -0,0 +1,42 @@
|
|||
use std::io::Read;
|
||||
use std::str::FromStr;
|
||||
|
||||
use xml::reader::{EventReader, XmlEvent};
|
||||
|
||||
use super::*;
|
||||
|
||||
impl FromXML for CommentsExtended {
|
||||
fn from_xml<R: Read>(reader: R) -> Result<Self, ReaderError> {
|
||||
let mut r = EventReader::new(reader);
|
||||
let mut comments_extended: Vec<CommentExtended> = vec![];
|
||||
loop {
|
||||
let e = r.next();
|
||||
match e {
|
||||
Ok(XmlEvent::StartElement {
|
||||
name, attributes, ..
|
||||
}) => {
|
||||
let e = XMLElement::from_str(&name.local_name)
|
||||
.expect("should convert to XMLElement");
|
||||
if let XMLElement::CommentExtended = e {
|
||||
comments_extended.push(CommentExtended::read(&mut r, &attributes)?);
|
||||
}
|
||||
}
|
||||
Ok(XmlEvent::EndElement { name, .. }) => {
|
||||
let e = XMLElement::from_str(&name.local_name).unwrap();
|
||||
if e == XMLElement::CommentsExtended {
|
||||
return Ok(CommentsExtended {
|
||||
children: comments_extended,
|
||||
});
|
||||
}
|
||||
}
|
||||
Ok(XmlEvent::EndDocument { .. }) => {
|
||||
return Ok(CommentsExtended {
|
||||
children: comments_extended,
|
||||
});
|
||||
}
|
||||
Err(_) => return Err(ReaderError::XMLReadError),
|
||||
_ => {}
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
|
@ -3,6 +3,10 @@ mod a_graphic_data;
|
|||
mod attributes;
|
||||
mod bookmark_end;
|
||||
mod bookmark_start;
|
||||
mod comment;
|
||||
mod comment_extended;
|
||||
mod comments;
|
||||
mod comments_extended;
|
||||
mod delete;
|
||||
mod doc_defaults;
|
||||
mod document;
|
||||
|
@ -58,6 +62,10 @@ const NUMBERING_RELATIONSHIP_TYPE: &str =
|
|||
"http://schemas.openxmlformats.org/officeDocument/2006/relationships/numbering";
|
||||
const SETTINGS_TYPE: &str =
|
||||
"http://schemas.openxmlformats.org/officeDocument/2006/relationships/settings";
|
||||
const COMMENTS_TYPE: &str =
|
||||
"http://schemas.openxmlformats.org/officeDocument/2006/relationships/comments";
|
||||
const COMMENTS_EXTENDED_TYPE: &str =
|
||||
"http://schemas.microsoft.com/office/2011/relationships/commentsExtended";
|
||||
|
||||
pub fn read_docx(buf: &[u8]) -> Result<Docx, ReaderError> {
|
||||
let cur = Cursor::new(buf);
|
||||
|
@ -86,14 +94,77 @@ pub fn read_docx(buf: &[u8]) -> Result<Docx, ReaderError> {
|
|||
} else {
|
||||
"word/document.xml".to_owned()
|
||||
};
|
||||
|
||||
let rels = read_document_rels(&mut archive, &document_path)?;
|
||||
|
||||
// Read commentsExtended
|
||||
let comments_extended_path = rels.find_target_path(COMMENTS_EXTENDED_TYPE);
|
||||
let comments_extended = if let Some(comments_extended_path) = comments_extended_path {
|
||||
let data = read_zip(
|
||||
&mut archive,
|
||||
comments_extended_path
|
||||
.to_str()
|
||||
.expect("should have comments extended."),
|
||||
);
|
||||
if let Ok(data) = data {
|
||||
CommentsExtended::from_xml(&data[..])?
|
||||
} else {
|
||||
CommentsExtended::default()
|
||||
}
|
||||
} else {
|
||||
CommentsExtended::default()
|
||||
};
|
||||
|
||||
// Read comments
|
||||
let comments_path = rels.find_target_path(COMMENTS_TYPE);
|
||||
let comments = if let Some(comments_path) = comments_path {
|
||||
let data = read_zip(
|
||||
&mut archive,
|
||||
comments_path.to_str().expect("should have comments."),
|
||||
);
|
||||
if let Ok(data) = data {
|
||||
let mut comments = Comments::from_xml(&data[..])?.into_inner();
|
||||
for i in 0..comments.len() {
|
||||
let c = &comments[i];
|
||||
let extended = comments_extended
|
||||
.children
|
||||
.iter()
|
||||
.find(|ex| ex.paragraph_id == c.paragraph.id);
|
||||
if let Some(CommentExtended {
|
||||
parent_paragraph_id: Some(parent_paragraph_id),
|
||||
..
|
||||
}) = extended
|
||||
{
|
||||
if let Some(parent_comment) = comments
|
||||
.iter()
|
||||
.find(|c| &c.paragraph.id == parent_paragraph_id)
|
||||
{
|
||||
comments[i].parent_comment_id = Some(parent_comment.id);
|
||||
}
|
||||
}
|
||||
}
|
||||
Comments { comments }
|
||||
} else {
|
||||
Comments::default()
|
||||
}
|
||||
} else {
|
||||
Comments::default()
|
||||
};
|
||||
|
||||
let document = {
|
||||
let data = read_zip(&mut archive, &document_path)?;
|
||||
Document::from_xml(&data[..])?
|
||||
};
|
||||
let mut docx = Docx::new().document(document);
|
||||
// Read document relationships
|
||||
let rels = read_document_rels(&mut archive, &document_path)?;
|
||||
|
||||
// store comments to paragraphs.
|
||||
if !comments.inner().is_empty() {
|
||||
docx.store_comments(comments.inner());
|
||||
docx = docx.comments(comments);
|
||||
docx = docx.comments_extended(comments_extended);
|
||||
}
|
||||
|
||||
// Read document relationships
|
||||
// Read styles
|
||||
let style_path = rels.find_target_path(STYLE_RELATIONSHIP_TYPE);
|
||||
if let Some(style_path) = style_path {
|
||||
|
|
|
@ -25,6 +25,9 @@ impl ElementReader for Paragraph {
|
|||
attrs: &[OwnedAttribute],
|
||||
) -> Result<Self, ReaderError> {
|
||||
let mut p = Paragraph::new();
|
||||
if let Some(para_id) = read(attrs, "paraId") {
|
||||
p = p.id(para_id);
|
||||
}
|
||||
loop {
|
||||
let e = r.next();
|
||||
match e {
|
||||
|
@ -62,7 +65,12 @@ impl ElementReader for Paragraph {
|
|||
continue;
|
||||
}
|
||||
XMLElement::CommentRangeStart => {
|
||||
// TODO: Support comment later.
|
||||
if let Some(id) = read(&attributes, "id") {
|
||||
if let Ok(id) = usize::from_str(&id) {
|
||||
let comment = Comment::new(id);
|
||||
p = p.add_comment_start(comment);
|
||||
}
|
||||
}
|
||||
continue;
|
||||
}
|
||||
XMLElement::CommentRangeEnd => {
|
||||
|
|
|
@ -43,8 +43,12 @@ pub enum XMLElement {
|
|||
DeleteText,
|
||||
BookmarkStart,
|
||||
BookmarkEnd,
|
||||
Comment,
|
||||
Comments,
|
||||
CommentRangeStart,
|
||||
CommentRangeEnd,
|
||||
CommentExtended,
|
||||
CommentsExtended,
|
||||
VAlign,
|
||||
Table,
|
||||
TableProperty,
|
||||
|
@ -201,8 +205,12 @@ impl FromStr for XMLElement {
|
|||
"delText" => Ok(XMLElement::DeleteText),
|
||||
"bookmarkStart" => Ok(XMLElement::BookmarkStart),
|
||||
"bookmarkEnd" => Ok(XMLElement::BookmarkEnd),
|
||||
"comments" => Ok(XMLElement::Comments),
|
||||
"comment" => Ok(XMLElement::Comment),
|
||||
"commentRangeStart" => Ok(XMLElement::CommentRangeStart),
|
||||
"commentRangeEnd" => Ok(XMLElement::CommentRangeEnd),
|
||||
"commentEx" => Ok(XMLElement::CommentExtended),
|
||||
"commentsEx" => Ok(XMLElement::CommentsExtended),
|
||||
"tbl" => Ok(XMLElement::Table),
|
||||
"tblPr" => Ok(XMLElement::TableProperty),
|
||||
"tr" => Ok(XMLElement::TableRow),
|
||||
|
|
|
@ -43,7 +43,7 @@ where
|
|||
zip.write_all(&xml.numberings)?;
|
||||
zip.start_file("word/header1.xml", options)?;
|
||||
zip.write_all(&xml.header)?;
|
||||
zip.start_file("word/CommentsExtended.xml", options)?;
|
||||
zip.start_file("word/commentsExtended.xml", options)?;
|
||||
zip.write_all(&xml.comments_extended)?;
|
||||
|
||||
if !xml.media.is_empty() {
|
||||
|
|
|
@ -229,3 +229,33 @@ pub fn read_lvl_override() {
|
|||
file.write_all(json.as_bytes()).unwrap();
|
||||
file.flush().unwrap();
|
||||
}
|
||||
|
||||
#[test]
|
||||
pub fn read_comment() {
|
||||
let mut file = File::open("../fixtures/comment/comment.docx").unwrap();
|
||||
let mut buf = vec![];
|
||||
file.read_to_end(&mut buf).unwrap();
|
||||
let json = read_docx(&buf).unwrap().json();
|
||||
|
||||
assert_json_snapshot!("read_comment", &json);
|
||||
|
||||
let path = std::path::Path::new("./tests/output/comment.json");
|
||||
let mut file = std::fs::File::create(&path).unwrap();
|
||||
file.write_all(json.as_bytes()).unwrap();
|
||||
file.flush().unwrap();
|
||||
}
|
||||
|
||||
#[test]
|
||||
pub fn read_extended_comment() {
|
||||
let mut file = File::open("../fixtures/extended_comments/extended_comments.docx").unwrap();
|
||||
let mut buf = vec![];
|
||||
file.read_to_end(&mut buf).unwrap();
|
||||
let json = read_docx(&buf).unwrap().json();
|
||||
|
||||
assert_json_snapshot!("read_extended_comments", &json);
|
||||
|
||||
let path = std::path::Path::new("./tests/output/extended_comments.json");
|
||||
let mut file = std::fs::File::create(&path).unwrap();
|
||||
file.write_all(json.as_bytes()).unwrap();
|
||||
file.flush().unwrap();
|
||||
}
|
||||
|
|
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
File diff suppressed because one or more lines are too long
|
@ -0,0 +1,18 @@
|
|||
import { ParagraphJSON } from "../";
|
||||
|
||||
export type CommentJSON = {
|
||||
id: number;
|
||||
author: string;
|
||||
date: string;
|
||||
paragraph: ParagraphJSON;
|
||||
parentCommentId: number | null;
|
||||
};
|
||||
|
||||
export type CommentRangeStartJSON = {
|
||||
id: number;
|
||||
comment: CommentJSON;
|
||||
};
|
||||
|
||||
export type CommentRangeEndJSON = {
|
||||
id: number;
|
||||
};
|
|
@ -1,6 +1,7 @@
|
|||
import { StylesJSON } from "./styles";
|
||||
import { DocumentJSON } from "./document";
|
||||
import { NumberingsJSON } from "./numbering";
|
||||
import { CommentJSON } from "./comment";
|
||||
|
||||
export type DocxJSON = {
|
||||
contentType: {
|
||||
|
@ -31,7 +32,7 @@ export type DocxJSON = {
|
|||
styles: StylesJSON;
|
||||
document: DocumentJSON;
|
||||
comments: {
|
||||
comments: any[]; // TODO:
|
||||
comments: CommentJSON[];
|
||||
};
|
||||
numberings: NumberingsJSON;
|
||||
settings: {
|
||||
|
@ -52,5 +53,6 @@ export * from "./run";
|
|||
export * from "./table";
|
||||
export * from "./numbering";
|
||||
export * from "./drawing";
|
||||
export * from "./comment";
|
||||
export * from "./textbox-content";
|
||||
export * from "./section-property";
|
||||
|
|
|
@ -1,10 +1,13 @@
|
|||
import { RunJSON, RunChildJSON, RunPropertyJSON } from "./run";
|
||||
import { IndentJSON } from "./indent";
|
||||
import { CommentRangeStartJSON, CommentRangeEndJSON } from "..";
|
||||
|
||||
export type ParagraphChildJSON =
|
||||
| RunJSON
|
||||
| InsertJSON
|
||||
| DeleteJSON
|
||||
| CommentRangeStartJSON
|
||||
| CommentRangeEndJSON
|
||||
| BookmarkStartJSON
|
||||
| BookmarkEndJSON;
|
||||
|
||||
|
|
File diff suppressed because it is too large
Load Diff
|
@ -20,6 +20,12 @@ describe("reader", () => {
|
|||
const json = w.readDocx(buf);
|
||||
expect(json).toMatchSnapshot();
|
||||
});
|
||||
|
||||
test("should read extended comments docx", () => {
|
||||
const buf = readFileSync("../fixtures/extended_comments/extended_comments.docx");
|
||||
const json = w.readDocx(buf);
|
||||
expect(json).toMatchSnapshot();
|
||||
});
|
||||
});
|
||||
|
||||
describe("writer", () => {
|
||||
|
|
|
@ -0,0 +1,22 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<Types xmlns="http://schemas.openxmlformats.org/package/2006/content-types">
|
||||
<Default ContentType="image/png" Extension="png" />
|
||||
<Default ContentType="image/jpeg" Extension="jpeg" />
|
||||
<Default ContentType="image/jpg" Extension="jpg" />
|
||||
<Default ContentType="image/bmp" Extension="bmp" />
|
||||
<Default ContentType="image/gif" Extension="gif" />
|
||||
<Default ContentType="application/vnd.openxmlformats-package.relationships+xml" Extension="rels" />
|
||||
<Default ContentType="application/xml" Extension="xml" />
|
||||
<Override PartName="/_rels/.rels" ContentType="application/vnd.openxmlformats-package.relationships+xml" />
|
||||
<Override PartName="/docProps/app.xml" ContentType="application/vnd.openxmlformats-officedocument.extended-properties+xml" />
|
||||
<Override PartName="/docProps/core.xml" ContentType="application/vnd.openxmlformats-package.core-properties+xml" />
|
||||
<Override PartName="/word/_rels/document.xml.rels" ContentType="application/vnd.openxmlformats-package.relationships+xml" />
|
||||
<Override PartName="/word/comments.xml" ContentType="application/vnd.openxmlformats-officedocument.wordprocessingml.comments+xml" />
|
||||
<Override PartName="/word/commentsExtended.xml" ContentType="application/vnd.openxmlformats-officedocument.wordprocessingml.commentsExtended+xml" />
|
||||
<Override PartName="/word/document.xml" ContentType="application/vnd.openxmlformats-officedocument.wordprocessingml.document.main+xml" />
|
||||
<Override PartName="/word/fontTable.xml" ContentType="application/vnd.openxmlformats-officedocument.wordprocessingml.fontTable+xml" />
|
||||
<Override PartName="/word/header1.xml" ContentType="application/vnd.openxmlformats-officedocument.wordprocessingml.header+xml" />
|
||||
<Override PartName="/word/numbering.xml" ContentType="application/vnd.openxmlformats-officedocument.wordprocessingml.numbering+xml" />
|
||||
<Override PartName="/word/settings.xml" ContentType="application/vnd.openxmlformats-officedocument.wordprocessingml.settings+xml" />
|
||||
<Override PartName="/word/styles.xml" ContentType="application/vnd.openxmlformats-officedocument.wordprocessingml.styles+xml" />
|
||||
</Types>
|
|
@ -0,0 +1,6 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<Relationships xmlns="http://schemas.openxmlformats.org/package/2006/relationships">
|
||||
<Relationship Id="rId1" Type="http://schemas.openxmlformats.org/package/2006/relationships/metadata/core-properties" Target="docProps/core.xml" />
|
||||
<Relationship Id="rId2" Type="http://schemas.openxmlformats.org/officeDocument/2006/relationships/extended-properties" Target="docProps/app.xml" />
|
||||
<Relationship Id="rId3" Type="http://schemas.openxmlformats.org/officeDocument/2006/relationships/officeDocument" Target="word/document.xml" />
|
||||
</Relationships>
|
|
@ -0,0 +1,2 @@
|
|||
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
|
||||
<Properties xmlns="http://schemas.openxmlformats.org/officeDocument/2006/extended-properties" xmlns:vt="http://schemas.openxmlformats.org/officeDocument/2006/docPropsVTypes" />
|
|
@ -0,0 +1,8 @@
|
|||
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
|
||||
<cp:coreProperties xmlns:cp="http://schemas.openxmlformats.org/package/2006/metadata/core-properties" xmlns:dc="http://purl.org/dc/elements/1.1/" xmlns:dcterms="http://purl.org/dc/terms/" xmlns:dcmitype="http://purl.org/dc/dcmitype/" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance">
|
||||
<dcterms:created xsi:type="dcterms:W3CDTF">1970-01-01T00:00:00Z</dcterms:created>
|
||||
<dc:creator>unknown</dc:creator>
|
||||
<cp:lastModifiedBy>unknown</cp:lastModifiedBy>
|
||||
<dcterms:modified xsi:type="dcterms:W3CDTF">1970-01-01T00:00:00Z</dcterms:modified>
|
||||
<cp:revision>1</cp:revision>
|
||||
</cp:coreProperties>
|
Binary file not shown.
|
@ -0,0 +1,9 @@
|
|||
<?xml version="1.0" encoding="UTF-8"?>
|
||||
<Relationships xmlns="http://schemas.openxmlformats.org/package/2006/relationships">
|
||||
<Relationship Id="rId1" Type="http://schemas.openxmlformats.org/officeDocument/2006/relationships/styles" Target="styles.xml" />
|
||||
<Relationship Id="rId2" Type="http://schemas.openxmlformats.org/officeDocument/2006/relationships/fontTable" Target="fontTable.xml" />
|
||||
<Relationship Id="rId3" Type="http://schemas.openxmlformats.org/officeDocument/2006/relationships/settings" Target="settings.xml" />
|
||||
<Relationship Id="rId4" Type="http://schemas.openxmlformats.org/officeDocument/2006/relationships/header" Target="header1.xml" />
|
||||
<Relationship Id="rId5" Type="http://schemas.microsoft.com/office/2011/relationships/commentsExtended" Target="commentsExtended.xml" />
|
||||
<Relationship Id="rId6" Type="http://schemas.openxmlformats.org/officeDocument/2006/relationships/comments" Target="comments.xml" />
|
||||
</Relationships>
|
|
@ -0,0 +1,39 @@
|
|||
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
|
||||
<w:comments xmlns:o="urn:schemas-microsoft-com:office:office"
|
||||
xmlns:r="http://schemas.openxmlformats.org/officeDocument/2006/relationships"
|
||||
xmlns:v="urn:schemas-microsoft-com:vml"
|
||||
xmlns:w="http://schemas.openxmlformats.org/wordprocessingml/2006/main"
|
||||
xmlns:w10="urn:schemas-microsoft-com:office:word"
|
||||
xmlns:wp="http://schemas.openxmlformats.org/drawingml/2006/wordprocessingDrawing"
|
||||
xmlns:wps="http://schemas.microsoft.com/office/word/2010/wordprocessingShape"
|
||||
xmlns:wpg="http://schemas.microsoft.com/office/word/2010/wordprocessingGroup"
|
||||
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
|
||||
xmlns:wp14="http://schemas.microsoft.com/office/word/2010/wordprocessingDrawing"
|
||||
xmlns:w14="http://schemas.microsoft.com/office/word/2010/wordml" mc:Ignorable="w14 wp14">
|
||||
<w:comment w:id="1" w:author="あどみん てすと" w:date="2020-12-15T15:54:25.705Z" w:initials="">
|
||||
<w:p w14:paraId="00000064">
|
||||
<w:pPr>
|
||||
<w:rPr />
|
||||
</w:pPr>
|
||||
<w:r>
|
||||
<w:rPr>
|
||||
<w:rFonts />
|
||||
</w:rPr>
|
||||
<w:t xml:space="preserve">yey</w:t>
|
||||
</w:r>
|
||||
</w:p>
|
||||
</w:comment>
|
||||
<w:comment w:id="2" w:author="あどみん てすと" w:date="2020-12-15T15:54:32.752Z" w:initials="">
|
||||
<w:p w14:paraId="00000066">
|
||||
<w:pPr>
|
||||
<w:rPr />
|
||||
</w:pPr>
|
||||
<w:r>
|
||||
<w:rPr>
|
||||
<w:rFonts />
|
||||
</w:rPr>
|
||||
<w:t xml:space="preserve">yo</w:t>
|
||||
</w:r>
|
||||
</w:p>
|
||||
</w:comment>
|
||||
</w:comments>
|
|
@ -0,0 +1,34 @@
|
|||
<w15:commentsEx xmlns:wpc="http://schemas.microsoft.com/office/word/2010/wordprocessingCanvas"
|
||||
xmlns:cx="http://schemas.microsoft.com/office/drawing/2014/chartex"
|
||||
xmlns:cx1="http://schemas.microsoft.com/office/drawing/2015/9/8/chartex"
|
||||
xmlns:cx2="http://schemas.microsoft.com/office/drawing/2015/10/21/chartex"
|
||||
xmlns:cx3="http://schemas.microsoft.com/office/drawing/2016/5/9/chartex"
|
||||
xmlns:cx4="http://schemas.microsoft.com/office/drawing/2016/5/10/chartex"
|
||||
xmlns:cx5="http://schemas.microsoft.com/office/drawing/2016/5/11/chartex"
|
||||
xmlns:cx6="http://schemas.microsoft.com/office/drawing/2016/5/12/chartex"
|
||||
xmlns:cx7="http://schemas.microsoft.com/office/drawing/2016/5/13/chartex"
|
||||
xmlns:cx8="http://schemas.microsoft.com/office/drawing/2016/5/14/chartex"
|
||||
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
|
||||
xmlns:aink="http://schemas.microsoft.com/office/drawing/2016/ink"
|
||||
xmlns:am3d="http://schemas.microsoft.com/office/drawing/2017/model3d"
|
||||
xmlns:o="urn:schemas-microsoft-com:office:office"
|
||||
xmlns:r="http://schemas.openxmlformats.org/officeDocument/2006/relationships"
|
||||
xmlns:m="http://schemas.openxmlformats.org/officeDocument/2006/math"
|
||||
xmlns:v="urn:schemas-microsoft-com:vml"
|
||||
xmlns:wp14="http://schemas.microsoft.com/office/word/2010/wordprocessingDrawing"
|
||||
xmlns:wp="http://schemas.openxmlformats.org/drawingml/2006/wordprocessingDrawing"
|
||||
xmlns:w10="urn:schemas-microsoft-com:office:word"
|
||||
xmlns:w="http://schemas.openxmlformats.org/wordprocessingml/2006/main"
|
||||
xmlns:w14="http://schemas.microsoft.com/office/word/2010/wordml"
|
||||
xmlns:w15="http://schemas.microsoft.com/office/word/2012/wordml"
|
||||
xmlns:w16cex="http://schemas.microsoft.com/office/word/2018/wordml/cex"
|
||||
xmlns:w16cid="http://schemas.microsoft.com/office/word/2016/wordml/cid"
|
||||
xmlns:w16="http://schemas.microsoft.com/office/word/2018/wordml"
|
||||
xmlns:w16se="http://schemas.microsoft.com/office/word/2015/wordml/symex"
|
||||
xmlns:wpg="http://schemas.microsoft.com/office/word/2010/wordprocessingGroup"
|
||||
xmlns:wpi="http://schemas.microsoft.com/office/word/2010/wordprocessingInk"
|
||||
xmlns:wne="http://schemas.microsoft.com/office/word/2006/wordml"
|
||||
xmlns:wps="http://schemas.microsoft.com/office/word/2010">
|
||||
<w15:commentEx w15:paraId="00000064" w15:done="0" />
|
||||
<w15:commentEx w15:paraId="00000066" w15:paraIdParent="00000064" w15:done="0" />
|
||||
</w15:commentsEx>
|
|
@ -0,0 +1,82 @@
|
|||
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
|
||||
<w:document xmlns:o="urn:schemas-microsoft-com:office:office"
|
||||
xmlns:r="http://schemas.openxmlformats.org/officeDocument/2006/relationships"
|
||||
xmlns:v="urn:schemas-microsoft-com:vml"
|
||||
xmlns:w="http://schemas.openxmlformats.org/wordprocessingml/2006/main"
|
||||
xmlns:w10="urn:schemas-microsoft-com:office:word"
|
||||
xmlns:wp="http://schemas.openxmlformats.org/drawingml/2006/wordprocessingDrawing"
|
||||
xmlns:wps="http://schemas.microsoft.com/office/word/2010/wordprocessingShape"
|
||||
xmlns:wpg="http://schemas.microsoft.com/office/word/2010/wordprocessingGroup"
|
||||
xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006"
|
||||
xmlns:wp14="http://schemas.microsoft.com/office/word/2010/wordprocessingDrawing"
|
||||
xmlns:w14="http://schemas.microsoft.com/office/word/2010/wordml"
|
||||
xmlns:w15="http://schemas.microsoft.com/office/word/2012/wordml" mc:Ignorable="w14 wp14">
|
||||
<w:body>
|
||||
<w:bookmarkStart w:id="1" w:name="LWG=563188eb-11ef-484b-9fe4-088029361a5d" />
|
||||
<w:p w14:paraId="00000062">
|
||||
<w:pPr>
|
||||
<w:rPr>
|
||||
<w:sz w:val="21" />
|
||||
<w:szCs w:val="21" />
|
||||
</w:rPr>
|
||||
<w:jc w:val="left" />
|
||||
<w:ind w:left="0" w:right="0" />
|
||||
</w:pPr>
|
||||
<w:r>
|
||||
<w:rPr>
|
||||
<w:sz w:val="21" />
|
||||
<w:szCs w:val="21" />
|
||||
<w:rFonts w:eastAsia="MS 明朝" />
|
||||
</w:rPr>
|
||||
<w:t xml:space="preserve">Hello w</w:t>
|
||||
</w:r>
|
||||
<w:commentRangeStart w:id="1" />
|
||||
<w:bookmarkStart w:id="2" w:name="LRC=a187fb71-b95b-46d9-a379-121fe85b1fdc" />
|
||||
<w:commentRangeStart w:id="2" />
|
||||
<w:bookmarkStart w:id="3" w:name="LRC=a187fb71-b95b-46d9-a379-121fe85b1fdc" />
|
||||
<w:r>
|
||||
<w:rPr>
|
||||
<w:sz w:val="21" />
|
||||
<w:szCs w:val="21" />
|
||||
<w:rFonts w:eastAsia="MS 明朝" />
|
||||
</w:rPr>
|
||||
<w:t xml:space="preserve">orld</w:t>
|
||||
</w:r>
|
||||
<w:r>
|
||||
<w:rPr />
|
||||
</w:r>
|
||||
<w:commentRangeEnd w:id="1" />
|
||||
<w:r>
|
||||
<w:commentReference w:id="1" />
|
||||
</w:r>
|
||||
<w:bookmarkEnd w:id="2" />
|
||||
<w:r>
|
||||
<w:rPr />
|
||||
</w:r>
|
||||
<w:commentRangeEnd w:id="2" />
|
||||
<w:r>
|
||||
<w:commentReference w:id="2" />
|
||||
</w:r>
|
||||
<w:bookmarkEnd w:id="3" />
|
||||
</w:p>
|
||||
<w:bookmarkEnd w:id="1" />
|
||||
<w:p w14:paraId="00000067">
|
||||
<w:pPr>
|
||||
<w:rPr />
|
||||
</w:pPr>
|
||||
<w:r>
|
||||
<w:rPr>
|
||||
<w:rFonts />
|
||||
</w:rPr>
|
||||
<w:t xml:space="preserve"></w:t>
|
||||
</w:r>
|
||||
</w:p>
|
||||
<w:sectPr>
|
||||
<w:pgSz w:w="11906" w:h="16838" />
|
||||
<w:pgMar w:top="1985" w:right="1701" w:bottom="1701" w:left="1701" w:header="851" w:footer="992" w:gutter="0" />
|
||||
<w:headerReference w:type="default" r:id="rId4" />
|
||||
<w:cols w:space="425" />
|
||||
<w:docGrid w:type="lines" w:linePitch="360" />
|
||||
</w:sectPr>
|
||||
</w:body>
|
||||
</w:document>
|
|
@ -0,0 +1,14 @@
|
|||
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
|
||||
<w:fonts xmlns:w="http://schemas.openxmlformats.org/wordprocessingml/2006/main" xmlns:r="http://schemas.openxmlformats.org/officeDocument/2006/relationships"><w:font w:name="Times New Roman">
|
||||
<w:charset w:val="00" />
|
||||
<w:family w:val="roman" />
|
||||
<w:pitch w:val="variable" />
|
||||
</w:font><w:font w:name="Symbol">
|
||||
<w:charset w:val="02" />
|
||||
<w:family w:val="roman" />
|
||||
<w:pitch w:val="variable" />
|
||||
</w:font><w:font w:name="Arial">
|
||||
<w:charset w:val="00" />
|
||||
<w:family w:val="swiss" />
|
||||
<w:pitch w:val="variable" />
|
||||
</w:font></w:fonts>
|
|
@ -0,0 +1,2 @@
|
|||
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
|
||||
<w:hdr xmlns:r="http://schemas.openxmlformats.org/officeDocument/2006/relationships" xmlns:o="urn:schemas-microsoft-com:office:office" xmlns:v="urn:schemas-microsoft-com:vml" xmlns:w="http://schemas.openxmlformats.org/wordprocessingml/2006/main" xmlns:w10="urn:schemas-microsoft-com:office:word" xmlns:wp="http://schemas.openxmlformats.org/drawingml/2006/wordprocessingDrawing" xmlns:wps="http://schemas.microsoft.com/office/word/2010/wordprocessingShape" xmlns:wpg="http://schemas.microsoft.com/office/word/2010/wordprocessingGroup" xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" xmlns:wp14="http://schemas.microsoft.com/office/word/2010/wordprocessingDrawing" xmlns:w14="http://schemas.microsoft.com/office/word/2010/wordml" mc:Ignorable="w14 wp14" />
|
|
@ -0,0 +1,4 @@
|
|||
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
|
||||
<w:numbering xmlns:r="http://schemas.openxmlformats.org/officeDocument/2006/relationships" xmlns:o="urn:schemas-microsoft-com:office:office" xmlns:v="urn:schemas-microsoft-com:vml" xmlns:w="http://schemas.openxmlformats.org/wordprocessingml/2006/main"><w:abstractNum w:abstractNumId="1"><w:lvl w:ilvl="0"><w:start w:val="1" /><w:numFmt w:val="decimal" /><w:lvlText w:val="%1." /><w:lvlJc w:val="left" /><w:pPr><w:rPr /><w:ind w:left="420" w:right="0" w:hanging="420" /></w:pPr><w:rPr /></w:lvl><w:lvl w:ilvl="1"><w:start w:val="1" /><w:numFmt w:val="decimal" /><w:lvlText w:val="(%2)" /><w:lvlJc w:val="left" /><w:pPr><w:rPr /><w:ind w:left="840" w:right="0" w:hanging="420" /></w:pPr><w:rPr /></w:lvl><w:lvl w:ilvl="2"><w:start w:val="1" /><w:numFmt w:val="decimalEnclosedCircle" /><w:lvlText w:val="%3" /><w:lvlJc w:val="left" /><w:pPr><w:rPr /><w:ind w:left="1260" w:right="0" w:hanging="420" /></w:pPr><w:rPr /></w:lvl><w:lvl w:ilvl="3"><w:start w:val="1" /><w:numFmt w:val="decimal" /><w:lvlText w:val="%4." /><w:lvlJc w:val="left" /><w:pPr><w:rPr /><w:ind w:left="1680" w:right="0" w:hanging="420" /></w:pPr><w:rPr /></w:lvl><w:lvl w:ilvl="4"><w:start w:val="1" /><w:numFmt w:val="decimal" /><w:lvlText w:val="(%5)" /><w:lvlJc w:val="left" /><w:pPr><w:rPr /><w:ind w:left="2100" w:right="0" w:hanging="420" /></w:pPr><w:rPr /></w:lvl><w:lvl w:ilvl="5"><w:start w:val="1" /><w:numFmt w:val="decimalEnclosedCircle" /><w:lvlText w:val="%6" /><w:lvlJc w:val="left" /><w:pPr><w:rPr /><w:ind w:left="2520" w:right="0" w:hanging="420" /></w:pPr><w:rPr /></w:lvl><w:lvl w:ilvl="6"><w:start w:val="1" /><w:numFmt w:val="decimal" /><w:lvlText w:val="%7." /><w:lvlJc w:val="left" /><w:pPr><w:rPr /><w:ind w:left="2940" w:right="0" w:hanging="420" /></w:pPr><w:rPr /></w:lvl><w:lvl w:ilvl="7"><w:start w:val="1" /><w:numFmt w:val="decimal" /><w:lvlText w:val="(%8)" /><w:lvlJc w:val="left" /><w:pPr><w:rPr /><w:ind w:left="3360" w:right="0" w:hanging="420" /></w:pPr><w:rPr /></w:lvl><w:lvl w:ilvl="8"><w:start w:val="1" /><w:numFmt w:val="decimalEnclosedCircle" /><w:lvlText w:val="%9" /><w:lvlJc w:val="left" /><w:pPr><w:rPr /><w:ind w:left="3780" w:right="0" w:hanging="420" /></w:pPr><w:rPr /></w:lvl></w:abstractNum><w:num w:numId="1">
|
||||
<w:abstractNumId w:val="1" />
|
||||
</w:num></w:numbering>
|
|
@ -0,0 +1,16 @@
|
|||
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
|
||||
<w:settings xmlns:w="http://schemas.openxmlformats.org/wordprocessingml/2006/main" xmlns:w14="http://schemas.microsoft.com/office/word/2010/wordml" xmlns:w15="http://schemas.microsoft.com/office/word/2012/wordml"><w:defaultTabStop w:val="709" /><w:zoom w:percent="100" /><w:compat>
|
||||
<w:spaceForUL />
|
||||
<w:balanceSingleByteDoubleByteWidth />
|
||||
<w:doNotLeaveBackslashAlone />
|
||||
<w:ulTrailSpace />
|
||||
<w:doNotExpandShiftReturn />
|
||||
<w:adjustLineHeightInTable />
|
||||
<w:useFELayout />
|
||||
<w:compatSetting w:name="compatibilityMode" w:uri="http://schemas.microsoft.com/office/word" w:val="15" />
|
||||
<w:compatSetting w:name="overrideTableStyleFontSizeAndJustification" w:uri="http://schemas.microsoft.com/office/word" w:val="1" />
|
||||
<w:compatSetting w:name="enableOpenTypeFeatures" w:uri="http://schemas.microsoft.com/office/word" w:val="1" />
|
||||
<w:compatSetting w:name="doNotFlipMirrorIndents" w:uri="http://schemas.microsoft.com/office/word" w:val="1" />
|
||||
<w:compatSetting w:name="differentiateMultirowTableHeaders" w:uri="http://schemas.microsoft.com/office/word" w:val="1" />
|
||||
<w:compatSetting w:name="useWord2013TrackBottomHyphenation" w:uri="http://schemas.microsoft.com/office/word" w:val="0" />
|
||||
</w:compat><w15:docId w15:val="{50d61cff-8055-4197-917b-3993d0243c46}" /></w:settings>
|
|
@ -0,0 +1 @@
|
|||
<w:styles xmlns:mc="http://schemas.openxmlformats.org/markup-compatibility/2006" xmlns:r="http://schemas.openxmlformats.org/officeDocument/2006/relationships" xmlns:w="http://schemas.openxmlformats.org/wordprocessingml/2006/main" xmlns:w14="http://schemas.microsoft.com/office/word/2010/wordml" xmlns:w15="http://schemas.microsoft.com/office/word/2012/wordml" mc:Ignorable="w14 w15"><w:docDefaults><w:rPrDefault><w:rPr><w:sz w:val="21" /><w:szCs w:val="21" /><w:rFonts w:eastAsia="MS 明朝" /></w:rPr></w:rPrDefault></w:docDefaults><w:style w:type="paragraph" w:styleId="Normal"><w:name w:val="Normal" /><w:rPr /><w:pPr><w:rPr /></w:pPr><w:basedOn w:val="Normal" /><w:next w:val="Normal" /><w:qFormat /></w:style></w:styles>
|
Loading…
Reference in New Issue