改进语法,去除节点层次。
This commit is contained in:
parent
b500e9d095
commit
7cbe3dd220
|
@ -7,7 +7,8 @@ open System.Linq
|
|||
/// 带有地址的对象
|
||||
type AstObject() =
|
||||
class
|
||||
member this.address() = string(this.GetHashCode ())
|
||||
abstract member address:unit -> string
|
||||
default this.address():string = string(this.GetHashCode ())
|
||||
|
||||
abstract member members:unit -> AstObject list
|
||||
default this.members(): AstObject list = []
|
||||
|
@ -51,19 +52,17 @@ open System.Linq
|
|||
end
|
||||
|
||||
/// 引用节点
|
||||
type PointRef(bind: XmlElement, texts: TextItem list) =
|
||||
type FragmentRef(bind: XmlElement, texts: TextItem list) =
|
||||
class
|
||||
inherit AstObject()
|
||||
new(bind: XmlElement) = PointRef(bind, [])
|
||||
new(bind: XmlElement) = FragmentRef(bind, [])
|
||||
|
||||
member this.pointRef() =
|
||||
bind.GetAttribute "point"
|
||||
member this.sliceRef() =
|
||||
bind.GetAttribute "slice"
|
||||
member this.storyRef() =
|
||||
bind.GetAttribute "story"
|
||||
member this.appendChild(objs: TextItem list) =
|
||||
PointRef(bind, texts@objs)
|
||||
FragmentRef(bind, texts@objs)
|
||||
member this.children() =
|
||||
texts
|
||||
|
||||
|
@ -75,77 +74,35 @@ open System.Linq
|
|||
| null -> []
|
||||
| _ ->
|
||||
match TextItem.GenerateText(child) with
|
||||
| Some text -> text::PointRef.GenerateFromChildSibling(child.NextSibling)
|
||||
| None -> PointRef.GenerateFromChildSibling(child.NextSibling)
|
||||
| Some text -> text::FragmentRef.GenerateFromChildSibling(child.NextSibling)
|
||||
| None -> FragmentRef.GenerateFromChildSibling(child.NextSibling)
|
||||
|
||||
static member GeneratePointRef(ref_opt: XmlNode): Option<PointRef> =
|
||||
static member GeneratePointRef(ref_opt: XmlNode): Option<FragmentRef> =
|
||||
match ref_opt with
|
||||
| :? XmlElement as refo when refo.Name.Equals "refer" ->
|
||||
let text_objects = PointRef.GenerateFromChildSibling(refo.FirstChild)
|
||||
Some(PointRef(refo, text_objects))
|
||||
let text_objects = FragmentRef.GenerateFromChildSibling(refo.FirstChild)
|
||||
Some(FragmentRef(refo, text_objects))
|
||||
| _ -> None
|
||||
end
|
||||
|
||||
/// 定义节点
|
||||
type PointChildType = |Text of TextItem |Refer of PointRef
|
||||
type PointDef(bind: XmlElement, objs: AstObject list) =
|
||||
class
|
||||
inherit AstObject()
|
||||
new(bind: XmlElement) = PointDef(bind, [])
|
||||
|
||||
member this.name() = bind.GetAttribute "name"
|
||||
|
||||
member this.appendChild(o: PointChildType) =
|
||||
match o with
|
||||
|Text t -> PointDef(bind, objs@[t])
|
||||
|Refer r -> PointDef(bind, objs@[r])
|
||||
|
||||
member this.children() = objs
|
||||
|
||||
override this.members(): AstObject list = objs
|
||||
|
||||
static member GenerateFromChildSibling(child: XmlNode): PointChildType list =
|
||||
match child with
|
||||
| null -> []
|
||||
| _ ->
|
||||
let h = match child.Name with
|
||||
| "text-section" -> Some(Text(TextItem.GenerateText(child).Value))
|
||||
| "refer" -> Some(Refer(PointRef.GeneratePointRef(child).Value))
|
||||
| _ -> None
|
||||
match h with
|
||||
| Some childx -> childx::PointDef.GenerateFromChildSibling(child.NextSibling)
|
||||
| None -> PointDef.GenerateFromChildSibling(child.NextSibling)
|
||||
|
||||
static member GeneratePointDef(def_opt: XmlNode) : Option<PointDef> =
|
||||
match def_opt with
|
||||
| :? XmlElement as defo when defo.Name.Equals "point" ->
|
||||
let child_objs = PointDef.GenerateFromChildSibling(defo.FirstChild)
|
||||
let objs = child_objs |> List.map (
|
||||
fun o-> match o with
|
||||
|Refer refs -> refs :> AstObject
|
||||
|Text text -> text :> AstObject
|
||||
)
|
||||
Some(PointDef(defo, objs))
|
||||
| _ -> None
|
||||
|
||||
end
|
||||
|
||||
type SliceChildType = |Text of TextItem |Define of PointDef
|
||||
type SliceChildType = |Text of TextItem |Ref of FragmentRef
|
||||
/// 情节节点
|
||||
type SliceDef(bind: XmlElement, objs: AstObject list) =
|
||||
type FragmentSlice(bind: XmlElement, objs: AstObject list) =
|
||||
class
|
||||
inherit AstObject()
|
||||
new(bind: XmlElement) = SliceDef(bind, [])
|
||||
new(bind: XmlElement) = FragmentSlice(bind, [])
|
||||
|
||||
member this.name() =
|
||||
bind.GetAttribute "name"
|
||||
member this.appendChild(o: SliceChildType) =
|
||||
match o with
|
||||
| Text t -> SliceDef(bind, objs@[t])
|
||||
| Define d -> SliceDef(bind, objs@[d])
|
||||
| Text t -> FragmentSlice(bind, objs@[t])
|
||||
| Ref d -> FragmentSlice(bind, objs@[d])
|
||||
member this.children() = objs
|
||||
|
||||
override this.members(): AstObject list = objs
|
||||
override this.address (): string =
|
||||
bind.GetAttribute "address"
|
||||
|
||||
static member GenerateFromChildSibling(child: XmlNode): SliceChildType list =
|
||||
match child with
|
||||
|
@ -153,27 +110,27 @@ open System.Linq
|
|||
| _ ->
|
||||
let h = match child.Name with
|
||||
| "text-section" -> Some(Text(TextItem.GenerateText(child).Value))
|
||||
| "point" -> Some(Define(PointDef.GeneratePointDef(child).Value))
|
||||
| "refer" -> Some(Ref(FragmentRef.GeneratePointRef(child).Value))
|
||||
| _ -> None
|
||||
|
||||
match h with
|
||||
| Some value -> value::SliceDef.GenerateFromChildSibling(child.NextSibling)
|
||||
| _ -> SliceDef.GenerateFromChildSibling(child.NextSibling)
|
||||
| Some value -> value::FragmentSlice.GenerateFromChildSibling(child.NextSibling)
|
||||
| _ -> FragmentSlice.GenerateFromChildSibling(child.NextSibling)
|
||||
|
||||
static member GenerateSliceDef(slice_opt: XmlNode): Option<SliceDef> =
|
||||
static member GenerateSliceDef(slice_opt: XmlNode): Option<FragmentSlice> =
|
||||
match slice_opt with
|
||||
| :? XmlElement as slice when slice.Name.Equals "slice" ->
|
||||
let mbrs = SliceDef.GenerateFromChildSibling(slice.FirstChild)
|
||||
let mbrs = FragmentSlice.GenerateFromChildSibling(slice.FirstChild)
|
||||
let objs = mbrs |> List.map (
|
||||
fun o-> match o with
|
||||
|Define defs -> defs :> AstObject
|
||||
|Ref defs -> defs :> AstObject
|
||||
|Text text -> text :> AstObject
|
||||
)
|
||||
Some(SliceDef(slice, objs))
|
||||
Some(FragmentSlice(slice, objs))
|
||||
| _ -> None
|
||||
end
|
||||
|
||||
type StoryChildType = |Text of TextItem |Slice of SliceDef
|
||||
type StoryChildType = |Text of TextItem |Slice of FragmentSlice
|
||||
/// 故事节点
|
||||
type StoryDef(bind: XmlElement, objs: AstObject list) =
|
||||
class
|
||||
|
@ -191,6 +148,8 @@ open System.Linq
|
|||
member this.children() = objs
|
||||
|
||||
override this.members(): AstObject list = objs
|
||||
override this.address (): string =
|
||||
bind.GetAttribute "address"
|
||||
|
||||
static member GenerateFromChildSibling(child: XmlNode): StoryChildType list =
|
||||
match child with
|
||||
|
@ -198,7 +157,7 @@ open System.Linq
|
|||
| _ ->
|
||||
let h = match child.Name with
|
||||
| "text-section" -> Some(Text(TextItem.GenerateText(child).Value))
|
||||
| "slice" -> Some(Slice(SliceDef.GenerateSliceDef(child).Value))
|
||||
| "slice" -> Some(Slice(FragmentSlice.GenerateSliceDef(child).Value))
|
||||
| _->None
|
||||
match h with
|
||||
| Some value -> value::StoryDef.GenerateFromChildSibling(child.NextSibling)
|
||||
|
@ -218,7 +177,7 @@ open System.Linq
|
|||
| _ -> None
|
||||
end
|
||||
|
||||
type ArticleChildType = |Text of TextItem |Refer of PointRef
|
||||
type ArticleChildType = |Text of TextItem |Refer of FragmentRef
|
||||
/// 章节节点
|
||||
type ArticleDef(bind: XmlElement, objs: AstObject list) =
|
||||
class
|
||||
|
@ -237,6 +196,8 @@ open System.Linq
|
|||
ArticleDef(bind, objs@items)
|
||||
|
||||
override this.members(): AstObject list = objs
|
||||
override this.address (): string =
|
||||
bind.GetAttribute "address"
|
||||
|
||||
static member GenerateFromChildSibling(child: XmlNode): ArticleChildType list =
|
||||
match child with
|
||||
|
@ -244,7 +205,7 @@ open System.Linq
|
|||
| _ ->
|
||||
let data = match child.Name with
|
||||
| "text-section" -> Some(Text(TextItem.GenerateText(child).Value))
|
||||
| "refer" -> Some(Refer(PointRef.GeneratePointRef(child).Value))
|
||||
| "refer" -> Some(Refer(FragmentRef.GeneratePointRef(child).Value))
|
||||
| _ -> None
|
||||
match data with
|
||||
| Some value -> value::ArticleDef.GenerateFromChildSibling(child.NextSibling)
|
||||
|
@ -281,6 +242,8 @@ open System.Linq
|
|||
VolumeDef(bind, objs@items)
|
||||
|
||||
override this.members(): AstObject list = objs
|
||||
override this.address (): string =
|
||||
bind.GetAttribute "address"
|
||||
|
||||
static member GenerateFromChildSibling(child: XmlNode): VolumeChildType list =
|
||||
match child with
|
||||
|
|
File diff suppressed because it is too large
Load Diff
|
@ -39,18 +39,18 @@ entry.visitWith(visitor) |> ignore
|
|||
|
||||
let volume_pages = volume_page_assemble(visitor.contents()) |> List.map<VolumePage, IDomUnit> (fun x->x)
|
||||
let story_pages = story_page_assemble(visitor.contents()) |> List.map<StoryPage, IDomUnit> (fun x->x)
|
||||
let point_pages = point_page_assemble(volume_pages @ story_pages)
|
||||
let point_pages = slice_page_assemble(volume_pages @ story_pages)
|
||||
|
||||
volume_pages @ story_pages @ point_pages |> List.iter (fun it -> (it:?>PageAccess).setPageRoot(out_dir))
|
||||
let makers = volume_pages @ story_pages @ point_pages
|
||||
|> List.map(fun page_unit ->
|
||||
match page_unit with
|
||||
| :? PointPage as point ->
|
||||
PageMaker<PointPage>(point) :> PageText
|
||||
| :? SlicePage as point ->
|
||||
PageMaker(point) :> PageText
|
||||
| :? VolumePage as vol ->
|
||||
PageMaker<VolumePage>(vol)
|
||||
PageMaker(vol)
|
||||
| :? StoryPage as story ->
|
||||
PageMaker<StoryPage>(story)
|
||||
PageMaker(story)
|
||||
| _ -> failwith ""
|
||||
)
|
||||
|
||||
|
@ -63,17 +63,17 @@ for refs in makers do
|
|||
let file_path = (refs.bindPage() :?> PageAccess).pageURL()
|
||||
File.WriteAllLines(file_path, [refs.getHtmlText()])
|
||||
|
||||
let graph = StorylineGraphMake("故事线网络", story_pages|> List.map(fun x -> x :?> PageAccess))
|
||||
let graph_code = graph.getGraphCode()
|
||||
//let graph = StorylineGraphMake("故事线网络", story_pages|> List.map(fun x -> x :?> PageAccess))
|
||||
//let graph_code = graph.getGraphCode()
|
||||
|
||||
let stream = new StreamWriter(Path.Combine(dir_o.FullName, "storys_display.dot"), false)
|
||||
stream.Write(graph_code)
|
||||
stream.Flush()
|
||||
Process.Start("dot", $"""-Tsvg -o{Path.Combine(dir_o.FullName, "storys_display.svg")} {Path.Combine(dir_o.FullName, "storys_display.dot")}""") |> ignore
|
||||
//let stream = new StreamWriter(Path.Combine(dir_o.FullName, "storys_display.dot"), false)
|
||||
//stream.Write(graph_code)
|
||||
//stream.Flush()
|
||||
//Process.Start("dot", $"""-Tsvg -o{Path.Combine(dir_o.FullName, "storys_display.svg")} {Path.Combine(dir_o.FullName, "storys_display.dot")}""") |> ignore
|
||||
|
||||
let graph2 = VolumeGraphMake("卷章引用网络", (volume_pages@story_pages)|> List.map(fun d -> d :?> PageAccess))
|
||||
let graph2_code = graph2.getGraphCode()
|
||||
let stream2 = new StreamWriter(Path.Combine(dir_o.FullName, "volume_display.dot"), false)
|
||||
stream2.Write(graph2_code)
|
||||
stream2.Flush()
|
||||
Process.Start("dot", $"""-Tsvg -o{Path.Combine(dir_o.FullName, "volume_display.svg")} {Path.Combine(dir_o.FullName, "volume_display.dot")}""") |> ignore
|
||||
//let graph2 = VolumeGraphMake("卷章引用网络", (volume_pages@story_pages)|> List.map(fun d -> d :?> PageAccess))
|
||||
//let graph2_code = graph2.getGraphCode()
|
||||
//let stream2 = new StreamWriter(Path.Combine(dir_o.FullName, "volume_display.dot"), false)
|
||||
//stream2.Write(graph2_code)
|
||||
//stream2.Flush()
|
||||
//Process.Start("dot", $"""-Tsvg -o{Path.Combine(dir_o.FullName, "volume_display.svg")} {Path.Combine(dir_o.FullName, "volume_display.dot")}""") |> ignore
|
||||
|
|
|
@ -16,81 +16,51 @@
|
|||
|
||||
{故事 故事名称5
|
||||
故事介绍段落 aldkfjl flwief
|
||||
{剧情 剧情名称}
|
||||
{情节 情节名称}
|
||||
}
|
||||
|
||||
{故事 故事名称6
|
||||
故事介绍段落 aldkfjl flwief
|
||||
{剧情 剧情名称 剧情介绍}
|
||||
{情节 情节名称 情节介绍}
|
||||
}
|
||||
|
||||
{故事 故事名称7
|
||||
故事介绍段落 aldkfjl flwief
|
||||
{剧情 剧情名称
|
||||
剧情介绍
|
||||
{情节 情节名称
|
||||
情节介绍
|
||||
{@情节 故事名称6&情节名称}
|
||||
}
|
||||
}
|
||||
|
||||
{故事 故事名称8
|
||||
故事介绍段落 aldkfjl flwief
|
||||
{剧情 剧情名称
|
||||
剧情介绍
|
||||
{节点 节点名称}
|
||||
{情节 情节名称
|
||||
情节介绍
|
||||
{@情节 故事名称6&情节名称 引用简介}
|
||||
}
|
||||
}
|
||||
|
||||
{故事 故事名称9
|
||||
故事介绍段落 aldkfjl flwief
|
||||
{剧情 剧情名称
|
||||
剧情介绍
|
||||
{节点 节点名称
|
||||
奥龙订饭;爱领克 非两爱看扥}
|
||||
{情节 情节名称
|
||||
情节介绍
|
||||
{@情节 故事名称6&情节名称
|
||||
引用简介
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
{故事 故事名称10
|
||||
故事介绍段落 aldkfjl flwief
|
||||
{剧情 剧情名称
|
||||
剧情介绍
|
||||
{节点 节点名称
|
||||
奥龙订饭;爱领克 非两爱看扥
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
{故事 故事名称11
|
||||
故事介绍段落 aldkfjl flwief
|
||||
{剧情 剧情名称
|
||||
剧情介绍
|
||||
{节点 节点名称
|
||||
奥龙订饭;爱领克 非两爱看扥
|
||||
{@节点 故事名称10&剧情名称&节点名称}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
{故事 故事名称4
|
||||
故事介绍段落 aldkfjl flwief
|
||||
{剧情 剧情名称
|
||||
剧情介绍
|
||||
{节点 节点名称
|
||||
奥龙订饭;爱领克 非两爱看扥
|
||||
{@节点 故事名称10&剧情名称&节点名称
|
||||
asldkfj 来看房莱肯}
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
{故事 故事名称4
|
||||
故事介绍段落 aldkfjl flwief
|
||||
{剧情 剧情名称
|
||||
剧情介绍
|
||||
{节点 节点名称
|
||||
奥龙订饭;爱领克 非两爱看扥
|
||||
{@节点 故事名称10&剧情名称&节点名称
|
||||
asldkfj 来看房莱肯
|
||||
}
|
||||
}
|
||||
{情节 情节名称
|
||||
情节介绍
|
||||
{@情节 故事名称6&情节名称
|
||||
引用简介
|
||||
}
|
||||
|
||||
{@情节 故事名称8&情节名称
|
||||
引用简介
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -116,14 +86,14 @@
|
|||
{分卷 卷宗名称
|
||||
拉开茯苓领赛季发啦肯 lakdjf;alfj
|
||||
{章节 章节名称 昂来看申领发
|
||||
{@节点 故事名称10&剧情名称&节点名称}
|
||||
{@情节 故事名称7&情节名称}
|
||||
}
|
||||
}
|
||||
|
||||
{分卷 卷宗名称
|
||||
拉开茯苓领赛季发啦肯 lakdjf;alfj
|
||||
{章节 章节名称 昂来看申领发
|
||||
{@节点 故事名称10&剧情名称&节点名称
|
||||
森铃但凡拉动垦局}
|
||||
}
|
||||
{@情节 故事名称7&情节名称
|
||||
森铃但凡拉动垦局}
|
||||
}
|
||||
}
|
|
@ -55,7 +55,7 @@ bool printer::AstGenerate::visit(std::shared_ptr<const ast_gen::ElementAccess> s
|
|||
{
|
||||
decltype(this->element_stack) temp_stack;
|
||||
std::copy_if(element_stack.begin(), element_stack.end(),
|
||||
std::back_inserter(temp_stack), [=](std::pair<int, QDomElement> ep){ return ep.first < depth; });
|
||||
std::back_inserter(temp_stack), [=](std::pair<int, QDomElement> ep) { return ep.first < depth; });
|
||||
this->element_stack = temp_stack;
|
||||
|
||||
auto current_ast = element_stack.last();
|
||||
|
@ -87,25 +87,6 @@ bool printer::AstGenerate::visit(std::shared_ptr<const ast_gen::ElementAccess> s
|
|||
dom_slice.setAttribute("name", slice_node->name());
|
||||
dom_slice.setAttribute("address", (qulonglong) slice_node.get());
|
||||
}break;
|
||||
case NovelNode::PointDefines:
|
||||
{
|
||||
decltype(this->element_stack) temp_stack;
|
||||
std::copy_if(element_stack.begin(), element_stack.end(),
|
||||
std::back_inserter(temp_stack), [=](std::pair<int, QDomElement> ep) { return ep.first < depth; });
|
||||
this->element_stack = temp_stack;
|
||||
|
||||
auto current_slice = element_stack.last();
|
||||
auto point_node = std::dynamic_pointer_cast<const example_novel::PointDefines>(syntax_element->element());
|
||||
auto dom_point = doc.createElement("point");
|
||||
current_slice.second.appendChild(dom_point);
|
||||
element_stack.append(std::make_pair(depth, dom_point));
|
||||
|
||||
dom_point.setAttribute("name", point_node->name());
|
||||
dom_point.setAttribute("address", (qulonglong) point_node.get());
|
||||
dom_point.setAttribute("file-path", src_root.relativeFilePath(point_node->filePath()));
|
||||
|
||||
append_tokens(dom_point, point_node);
|
||||
}break;
|
||||
case NovelNode::TextSection:
|
||||
{
|
||||
decltype(this->element_stack) temp_stack;
|
||||
|
@ -123,7 +104,7 @@ bool printer::AstGenerate::visit(std::shared_ptr<const ast_gen::ElementAccess> s
|
|||
|
||||
append_tokens(dom_text, text_node);
|
||||
}break;
|
||||
case NovelNode::PointRefers:
|
||||
case NovelNode::FragmentRefers:
|
||||
{
|
||||
decltype(this->element_stack) temp_stack;
|
||||
std::copy_if(element_stack.begin(), element_stack.end(),
|
||||
|
@ -131,14 +112,13 @@ bool printer::AstGenerate::visit(std::shared_ptr<const ast_gen::ElementAccess> s
|
|||
this->element_stack = temp_stack;
|
||||
|
||||
auto current_pnode = element_stack.last();
|
||||
auto refer_node = std::dynamic_pointer_cast<const example_novel::PointRefers>(syntax_element->element());
|
||||
auto refer_node = std::dynamic_pointer_cast<const example_novel::FragmentRefers>(syntax_element->element());
|
||||
auto dom_refer = doc.createElement("refer");
|
||||
current_pnode.second.appendChild(dom_refer);
|
||||
element_stack.append(std::make_pair(depth, dom_refer));
|
||||
|
||||
dom_refer.setAttribute("story", refer_node->storyRefer());
|
||||
dom_refer.setAttribute("slice", refer_node->sliceRefer());
|
||||
dom_refer.setAttribute("point", refer_node->pointRefer());
|
||||
dom_refer.setAttribute("file-path", src_root.relativeFilePath(refer_node->filePath()));
|
||||
|
||||
append_tokens(dom_refer, refer_node);
|
||||
|
|
|
@ -51,7 +51,7 @@ int main(int argc, char* argv[]) {
|
|||
|
||||
auto source_dir = QDir(src_dir->value().toString());
|
||||
if (!source_dir.exists()) {
|
||||
cout << "%编译指定的源代码目录不存在!" << endl;
|
||||
qDebug() << "%编译指定的源代码目录不存在!" << source_dir.absolutePath() << endl;
|
||||
exit(0);
|
||||
}
|
||||
auto destination_dir = QDir::current();
|
||||
|
@ -60,7 +60,7 @@ int main(int argc, char* argv[]) {
|
|||
destination_dir = QDir(target_output.toString());
|
||||
}
|
||||
else {
|
||||
cout << "%编译指定的生成目录不存在,重置为:" << destination_dir.absolutePath().toLocal8Bit().data() << endl;
|
||||
qDebug() << "%编译指定的生成目录不存在,重置为:" << destination_dir.absolutePath().toLocal8Bit().data() << endl;
|
||||
}
|
||||
|
||||
auto files = source_dir.entryInfoList(QStringList() << "*.story");
|
||||
|
|
|
@ -19,7 +19,7 @@ void ElementsCache::clearCache() {
|
|||
std::shared_ptr<const SyntaxElement> ElementsCache::appendToCache(std::shared_ptr<const SyntaxElement> named_node) {
|
||||
auto mixed_key = QString("%1<%2>").arg(named_node->signature()).arg(named_node->typeMark());
|
||||
if (node_cache.contains(mixed_key))
|
||||
return node_cache[mixed_key];
|
||||
throw new CheckException(QString("节点命名重复:%1!").arg(mixed_key));
|
||||
node_cache[mixed_key] = named_node;
|
||||
return nullptr;
|
||||
}
|
||||
|
@ -40,12 +40,12 @@ void example_novel::FragmentExistsCheck::nodes_regist(std::shared_ptr<ElementsCa
|
|||
}
|
||||
|
||||
void FragmentExistsCheck::exists_check(std::shared_ptr<ElementsCache> root, std::shared_ptr<const ElementAccess> target) const {
|
||||
if (target->element()->typeMark() == (int) NovelNode::PointRefers) {
|
||||
auto refer = std::dynamic_pointer_cast<const PointRefers>(target->element());
|
||||
auto signature = refer->storyRefer() + "&" + refer->sliceRefer() + "&" + refer->pointRefer();
|
||||
if (!root->getNamedNodeBy((int) NovelNode::PointDefines, signature))
|
||||
if (target->element()->typeMark() == (int) NovelNode::FragmentRefers) {
|
||||
auto refer = std::dynamic_pointer_cast<const FragmentRefers>(target->element());
|
||||
auto signature = refer->storyRefer() + "&" + refer->sliceRefer();
|
||||
if (!root->getNamedNodeBy((int) NovelNode::FragmentSlice, signature))
|
||||
throw new SyntaxException(QString("CheckError[0x0005]系统中不包含指定签名的节点:%1<type:%2>{%3:(%4)}")
|
||||
.arg(signature).arg((int) NovelNode::PointDefines).arg(refer->signature()).arg(refer->filePath()));
|
||||
.arg(signature).arg((int) NovelNode::FragmentRefers).arg(refer->signature()).arg(refer->filePath()));
|
||||
}
|
||||
|
||||
for (auto& xit : target->children()) {
|
||||
|
@ -152,7 +152,7 @@ void PointGraphCheck::validCheck(std::shared_ptr<const ElementAccess> root) cons
|
|||
auto story_children = story->children();
|
||||
for (auto ins : story_children) {
|
||||
switch (ins->element()->typeMark()) {
|
||||
case (int) NovelNode::PointDefines:
|
||||
case (int) NovelNode::FragmentSlice:
|
||||
return_temp << ins;
|
||||
break;
|
||||
default:
|
||||
|
@ -171,7 +171,7 @@ void PointGraphCheck::validCheck(std::shared_ptr<const ElementAccess> root) cons
|
|||
auto x_children = defs->children();
|
||||
for (auto ins : x_children) {
|
||||
switch (ins->element()->typeMark()) {
|
||||
case (int) NovelNode::PointRefers:
|
||||
case (int) NovelNode::FragmentRefers:
|
||||
return_temp << ins;
|
||||
break;
|
||||
default:
|
||||
|
@ -191,7 +191,7 @@ void PointGraphCheck::validCheck(std::shared_ptr<const ElementAccess> root) cons
|
|||
|
||||
// 构建情节节点列表
|
||||
for (auto point_primitive : point_items) {
|
||||
auto target_node = std::dynamic_pointer_cast<const PointDefines>(point_primitive->element());
|
||||
auto target_node = std::dynamic_pointer_cast<const FragmentSlice>(point_primitive->element());
|
||||
auto finst = std::make_shared<PointGraphHelper>(target_node);
|
||||
self->setElement(finst);
|
||||
}
|
||||
|
@ -200,12 +200,12 @@ void PointGraphCheck::validCheck(std::shared_ptr<const ElementAccess> root) cons
|
|||
// 获取绑定节点名称
|
||||
auto get_name = [](std::shared_ptr<const ElementAccess> node)->QString {
|
||||
switch (node->element()->typeMark()) {
|
||||
case (int) NovelNode::PointDefines: {
|
||||
auto def_node = std::dynamic_pointer_cast<const PointDefines>(node->element());
|
||||
case (int) NovelNode::FragmentSlice: {
|
||||
auto def_node = std::dynamic_pointer_cast<const FragmentSlice>(node->element());
|
||||
return def_node->signature();
|
||||
}break;
|
||||
case (int) NovelNode::PointRefers: {
|
||||
auto ref_node = std::dynamic_pointer_cast<const PointRefers>(node->element());
|
||||
case (int) NovelNode::FragmentRefers: {
|
||||
auto ref_node = std::dynamic_pointer_cast<const FragmentRefers>(node->element());
|
||||
return ref_node->referSignature();
|
||||
}break;
|
||||
}
|
||||
|
@ -275,9 +275,9 @@ QString PointGraphCheck::name() const {
|
|||
return "情节网络有效性检查器";
|
||||
}
|
||||
|
||||
PointGraphHelper::PointGraphHelper(std::shared_ptr<const PointDefines> node) : node_peer(node) { }
|
||||
PointGraphHelper::PointGraphHelper(std::shared_ptr<const FragmentSlice> node) : node_peer(node) { }
|
||||
|
||||
std::shared_ptr<const PointDefines> PointGraphHelper::nodePeer() const {
|
||||
std::shared_ptr<const FragmentSlice> PointGraphHelper::nodePeer() const {
|
||||
return this->node_peer;
|
||||
}
|
||||
|
||||
|
|
|
@ -74,14 +74,14 @@ namespace example_novel {
|
|||
|
||||
class PointGraphHelper : public std::enable_shared_from_this<PointGraphHelper> {
|
||||
private:
|
||||
std::shared_ptr<const example_novel::PointDefines> node_peer;
|
||||
std::shared_ptr<const example_novel::FragmentSlice> node_peer;
|
||||
QList<std::shared_ptr<PointGraphHelper>> next_nodes;
|
||||
uint indegree = 0;
|
||||
|
||||
public:
|
||||
PointGraphHelper(std::shared_ptr<const example_novel::PointDefines> node);
|
||||
PointGraphHelper(std::shared_ptr<const example_novel::FragmentSlice> node);
|
||||
|
||||
std::shared_ptr<const example_novel::PointDefines> nodePeer() const;
|
||||
std::shared_ptr<const example_novel::FragmentSlice> nodePeer() const;
|
||||
|
||||
void appendNext(std::shared_ptr<PointGraphHelper> node);
|
||||
QList<std::shared_ptr<PointGraphHelper>> nextList() const;
|
||||
|
|
|
@ -22,59 +22,34 @@ QString TextSection::signature() const {
|
|||
return parent().lock()->signature() + "&::section";
|
||||
}
|
||||
|
||||
PointRefers::PointRefers(std::shared_ptr<const ExprRule> rule_bind)
|
||||
FragmentRefers::FragmentRefers(std::shared_ptr<const ExprRule> rule_bind)
|
||||
: AbstractImpl(rule_bind) { }
|
||||
|
||||
QString PointRefers::storyRefer() const {
|
||||
QString FragmentRefers::storyRefer() const {
|
||||
return story_refs;
|
||||
}
|
||||
|
||||
void PointRefers::setStoryRefer(const QString& refer) {
|
||||
void FragmentRefers::setStoryRefer(const QString& refer) {
|
||||
this->story_refs = refer;
|
||||
}
|
||||
|
||||
QString PointRefers::sliceRefer() const {
|
||||
QString FragmentRefers::sliceRefer() const {
|
||||
return slice_ref;
|
||||
}
|
||||
|
||||
void PointRefers::setSliceRefer(const QString& refer) {
|
||||
void FragmentRefers::setSliceRefer(const QString& refer) {
|
||||
slice_ref = refer;
|
||||
}
|
||||
|
||||
QString PointRefers::pointRefer() const {
|
||||
return point_ref;
|
||||
QString FragmentRefers::referSignature() const {
|
||||
return storyRefer() + "&" + sliceRefer();
|
||||
}
|
||||
|
||||
void PointRefers::setPointRefer(const QString& refer) {
|
||||
this->point_ref = refer;
|
||||
}
|
||||
|
||||
QString PointRefers::referSignature() const {
|
||||
return storyRefer() + "&" + sliceRefer() + "&" + pointRefer();
|
||||
}
|
||||
|
||||
QString PointRefers::signature() const {
|
||||
QString FragmentRefers::signature() const {
|
||||
QString signature = "@" + referSignature();
|
||||
return parent().lock()->signature() + "&" + signature;
|
||||
}
|
||||
|
||||
|
||||
PointDefines::PointDefines(std::shared_ptr<const ExprRule> rule_bind)
|
||||
: AbstractImpl(rule_bind) { }
|
||||
|
||||
QString PointDefines::name() const {
|
||||
return name_store;
|
||||
}
|
||||
|
||||
void PointDefines::setName(const QString& nm) {
|
||||
this->name_store = nm;
|
||||
}
|
||||
|
||||
QString PointDefines::signature() const {
|
||||
return parent().lock()->signature() + "&" + name();
|
||||
}
|
||||
|
||||
|
||||
StoryDefine::StoryDefine(std::shared_ptr<const ExprRule> rule_bind)
|
||||
: AbstractImpl(rule_bind), sort_index(0) { }
|
||||
|
||||
|
|
|
@ -105,14 +105,13 @@ namespace example_novel {
|
|||
enum class NovelNode {
|
||||
GlobalElement = 0,
|
||||
TextSection = 1,
|
||||
PointRefers = 2,
|
||||
PointDefines = 3,
|
||||
FragmentRefers = 2,
|
||||
FragmentSlice = 3,
|
||||
StoryDefine = 4,
|
||||
Document = 5,
|
||||
ArticleDefine = 6,
|
||||
VolumeDefine = 7,
|
||||
RankDeclaration = 8,
|
||||
FragmentSlice = 9,
|
||||
};
|
||||
|
||||
/*
|
||||
|
@ -123,15 +122,13 @@ namespace example_novel {
|
|||
| |-TextSection
|
||||
| \-FragmentSlice
|
||||
| |-TextSection
|
||||
| |-PointDefines
|
||||
| | \-TextSection
|
||||
| \-PointRefers
|
||||
| \-FragmentRefers
|
||||
| \-TextSection
|
||||
\-VolumeDefine
|
||||
|-TextSection
|
||||
\-ArticleDefine
|
||||
|-TextSection
|
||||
\-PointRefers
|
||||
\-FragmentRefers
|
||||
\-TextSection
|
||||
*/
|
||||
|
||||
|
@ -189,7 +186,7 @@ namespace example_novel {
|
|||
};
|
||||
|
||||
/**
|
||||
* @brief 故事情节
|
||||
* @brief 故事情节定义
|
||||
*/
|
||||
class LIBSYNTAX_EXPORT FragmentSlice : public AbstractImpl<NovelNode::FragmentSlice, true> {
|
||||
private:
|
||||
|
@ -206,14 +203,14 @@ namespace example_novel {
|
|||
};
|
||||
|
||||
/**
|
||||
* @brief 节点引用定义
|
||||
* @brief 情节引用定义
|
||||
*/
|
||||
class LIBSYNTAX_EXPORT PointRefers : public AbstractImpl<NovelNode::PointRefers, false> {
|
||||
class LIBSYNTAX_EXPORT FragmentRefers : public AbstractImpl<NovelNode::FragmentRefers, false> {
|
||||
private:
|
||||
QString story_refs, slice_ref, point_ref;
|
||||
QString story_refs, slice_ref;
|
||||
|
||||
public:
|
||||
PointRefers(std::shared_ptr<const lib_syntax::ExprRule> rule_bind);
|
||||
FragmentRefers(std::shared_ptr<const lib_syntax::ExprRule> rule_bind);
|
||||
|
||||
QString storyRefer() const;
|
||||
void setStoryRefer(const QString& refer);
|
||||
|
@ -221,31 +218,12 @@ namespace example_novel {
|
|||
QString sliceRefer() const;
|
||||
void setSliceRefer(const QString& refer);
|
||||
|
||||
QString pointRefer() const;
|
||||
void setPointRefer(const QString& refer);
|
||||
|
||||
QString referSignature() const;
|
||||
|
||||
// 通过 AbstractImpl 继承
|
||||
virtual QString signature() const override;
|
||||
};
|
||||
|
||||
/**
|
||||
* @brief 节点定义
|
||||
*/
|
||||
class LIBSYNTAX_EXPORT PointDefines : public AbstractImpl<NovelNode::PointDefines, true> {
|
||||
private:
|
||||
QString name_store;
|
||||
|
||||
public:
|
||||
PointDefines(std::shared_ptr<const lib_syntax::ExprRule> rule_bind);
|
||||
|
||||
QString name() const;
|
||||
void setName(const QString& nm);
|
||||
|
||||
// 通过 AbstractImpl 继承
|
||||
virtual QString signature() const override;
|
||||
};
|
||||
|
||||
/**
|
||||
* @brief 章节定义
|
||||
|
|
|
@ -12,22 +12,14 @@ using namespace std;
|
|||
#include "syntax_templets.h"
|
||||
using namespace lib_composit;
|
||||
|
||||
void point_nm_set(std::shared_ptr<PointDefines> inst, std::shared_ptr<const lib_token::IToken> token) {
|
||||
inst->addToken(token);
|
||||
inst->setName(token->content());
|
||||
}
|
||||
void ref_story_set(std::shared_ptr<PointRefers> inst, std::shared_ptr<const lib_token::IToken> token) {
|
||||
void ref_story_set(std::shared_ptr<FragmentRefers> inst, std::shared_ptr<const lib_token::IToken> token) {
|
||||
inst->addToken(token);
|
||||
inst->setStoryRefer(token->content());
|
||||
}
|
||||
void ref_slice_set(std::shared_ptr<PointRefers> inst, std::shared_ptr<const lib_token::IToken> token) {
|
||||
void ref_slice_set(std::shared_ptr<FragmentRefers> inst, std::shared_ptr<const lib_token::IToken> token) {
|
||||
inst->addToken(token);
|
||||
inst->setSliceRefer(token->content());
|
||||
}
|
||||
void ref_point_set(std::shared_ptr<PointRefers> inst, std::shared_ptr<const lib_token::IToken> token) {
|
||||
inst->addToken(token);
|
||||
inst->setPointRefer(token->content());
|
||||
}
|
||||
void slice_nm_set(std::shared_ptr<FragmentSlice> inst, std::shared_ptr<const lib_token::IToken> token) {
|
||||
inst->addToken(token);
|
||||
inst->setName(token->content());
|
||||
|
@ -136,12 +128,12 @@ public:
|
|||
};
|
||||
|
||||
|
||||
using ReferSyntaxDef = lib_composit::Seqs<Match<LBracket>, Match<ReferMk>, Match<PointWord>, Action<PointRefers, NameText, ref_story_set>, Match<SplitMk>, Action<PointRefers, NameText, ref_slice_set>, Match<SplitMk>, Action<PointRefers, NameText, ref_point_set>,
|
||||
using ReferSyntaxDef = lib_composit::Seqs<Match<LBracket>, Match<ReferMk>, Match<SliceWord>, Action<FragmentRefers, NameText, ref_story_set>, Match<SplitMk>, Action<FragmentRefers, NameText, ref_slice_set>,
|
||||
OptMulti<DeclSyntax>,
|
||||
Match<RBracket>>;
|
||||
class ReferSyntax : public ElementRule<PointRefers, (int) NovelNode::PointRefers, ReferSyntaxDef> {
|
||||
class ReferSyntax : public ElementRule<FragmentRefers, (int) NovelNode::FragmentRefers, ReferSyntaxDef> {
|
||||
public:
|
||||
ReferSyntax() : ElementRule<PointRefers, (int) NovelNode::PointRefers, ReferSyntaxDef>("point_refer") { }
|
||||
ReferSyntax() : ElementRule<FragmentRefers, (int) NovelNode::FragmentRefers, ReferSyntaxDef>("fragment_refer") { }
|
||||
|
||||
// 通过 ElementRule 继承
|
||||
QList<std::shared_ptr<const MatchCursor>> expr_rule_parse(std::shared_ptr<const MatchCursor> cursor) const override {
|
||||
|
@ -150,27 +142,12 @@ public:
|
|||
};
|
||||
|
||||
|
||||
using PointSyntaxDef = lib_composit::Seqs<Match<LBracket>, Match<PointWord>, Action<PointDefines, NameText, point_nm_set>,
|
||||
OptMulti<Any<ReferSyntax, DeclSyntax>>,
|
||||
Match<RBracket>>;
|
||||
class PointSyntax : public ElementRule<PointDefines, (int) NovelNode::PointDefines, PointSyntaxDef> {
|
||||
public:
|
||||
PointSyntax() : ElementRule<PointDefines, (int) NovelNode::PointDefines, PointSyntaxDef>("point_define") { }
|
||||
|
||||
// 通过 ElementRule 继承
|
||||
QList<std::shared_ptr<const MatchCursor>> expr_rule_parse(std::shared_ptr<const MatchCursor> cursor) const override {
|
||||
return _children_store->parse(cursor);
|
||||
}
|
||||
};
|
||||
|
||||
|
||||
|
||||
using SliceSyntaxDef = lib_composit::Seqs<Match<LBracket>, Match<SliceWord>, Action<FragmentSlice, NameText, slice_nm_set>,
|
||||
lib_composit::OptMulti<Any<PointSyntax, DeclSyntax>>,
|
||||
lib_composit::OptMulti<Any<ReferSyntax, DeclSyntax>>,
|
||||
Match<RBracket>>;
|
||||
class SliceSyntax : public ElementRule<FragmentSlice, (int) NovelNode::FragmentSlice, SliceSyntaxDef> {
|
||||
public:
|
||||
SliceSyntax() : ElementRule<FragmentSlice, (int) NovelNode::FragmentSlice, SliceSyntaxDef>("slice_define") { }
|
||||
SliceSyntax() : ElementRule<FragmentSlice, (int) NovelNode::FragmentSlice, SliceSyntaxDef>("fragment_define") { }
|
||||
|
||||
// 通过 ElementRule 继承
|
||||
QList<std::shared_ptr<const MatchCursor>> expr_rule_parse(std::shared_ptr<const MatchCursor> cursor) const override {
|
||||
|
@ -179,7 +156,6 @@ public:
|
|||
};
|
||||
|
||||
|
||||
|
||||
using StorySyntaxDef = lib_composit::Seqs<Match<LBracket>, Match<StoryWord>, Action<StoryDefine, NameText, story_nm_set>,
|
||||
lib_composit::OptMulti<Any<SliceSyntax, DeclSyntax>>,
|
||||
Match<RBracket>>;
|
||||
|
|
|
@ -219,9 +219,7 @@ inline example_novel::RankWord::RankWord() : __keywords("排序", 0xAEu) { }
|
|||
|
||||
inline example_novel::StoryWord::StoryWord() : __keywords("故事", 0xAAu) { }
|
||||
|
||||
inline example_novel::SliceWord::SliceWord() : __keywords("剧情", 0xAFu) { }
|
||||
|
||||
inline example_novel::PointWord::PointWord() : __keywords("节点", 0xABu) { }
|
||||
inline example_novel::SliceWord::SliceWord() : __keywords("情节", 0xAFu) { }
|
||||
|
||||
inline example_novel::VolumeWord::VolumeWord() : __keywords("分卷", 0xACu) { }
|
||||
|
||||
|
|
|
@ -66,10 +66,6 @@ namespace example_novel {
|
|||
public:
|
||||
SliceWord();
|
||||
};
|
||||
class LIBSYNTAX_EXPORT PointWord : public __keywords {
|
||||
public:
|
||||
PointWord();
|
||||
};
|
||||
class LIBSYNTAX_EXPORT VolumeWord : public __keywords {
|
||||
public:
|
||||
VolumeWord();
|
||||
|
|
Loading…
Reference in New Issue