This commit is contained in:
玉宇清音 2022-12-09 03:43:42 +08:00
parent c9d4b1374c
commit d3f0438af4
22 changed files with 361 additions and 99 deletions

View File

@ -1,7 +1,7 @@
#单元 中南世界的故事片段
{
中南世界,主角从一个小角色,逐渐混成大佬的事迹。
#情节 故事的开端{
#情节 故事的开端 19201202{
中南世界的街头,异常热闹的故事开场{@节点 示例脉络 示例节点},主角从这里出发
}
}
@ -9,7 +9,7 @@
{
中南世界,主角从一个小角色,逐渐混成大佬的事迹。
asfjlakdjf;aldkjf;aldsf
#情节 故事的开端{
#情节 故事的开端 16601045{
中南世界的街头,异常热闹的故事开场{@节点 示例脉络 示例节点},主角从这里出发
}
}

View File

@ -40,7 +40,7 @@ int main(int argc, char *argv[])
MakeTools::StoryTool tool(&core);
// auto path = "D:\\Projects\\Cpp\\QtNovelDesc\\DesParser\\example.storyvolume";
auto path = "D:\\Projects\\Cpp\\QtNovelDesc\\DesParser\\example.storyconcept";
auto path = "D:\\Projects\\Cpp\\QtNovelDesc\\DesParser\\example.storyunit";
tool.compile(QFileInfo(path), "后台编译");
auto doc = core.queryDocument(QFileInfo(path));

View File

@ -1,6 +1,6 @@
<?xml version="1.0" encoding="UTF-8"?>
<!DOCTYPE QtCreatorProject>
<!-- Written by QtCreator 4.15.0, 2022-12-01T15:03:57. -->
<!-- Written by QtCreator 4.15.0, 2022-12-09T02:02:06. -->
<qtcreator>
<data>
<variable>EnvironmentId</variable>

View File

@ -13,6 +13,7 @@ SOURCES += \
SensitiveCore.cpp \
SourceEditView.cpp \
appcore.cpp \
fragmentsorderview.cpp \
keywordshightlighter.cpp \
main.cpp \
mainwindow.cpp \
@ -34,6 +35,7 @@ HEADERS += \
SensitiveCore.h \
SourceEditView.h \
appcore.h \
fragmentsorderview.h \
keywordshightlighter.h \
mainwindow.h \
messagepresent.h \

View File

@ -0,0 +1,77 @@
#include "fragmentsorderview.h"
#include "SensitiveCore.h"
#include <comdef.h>
#include <StoryUnitDocumentParser.h>
#include <QVBoxLayout>
using namespace Components;
using namespace Parse;
FragmentsOrderView::FragmentsOrderView(Core::AppCore *core, QWidget *parent)
: QWidget(parent), core_ins(core), table_view(new QTableView(this)),
table_base(new QStandardItemModel(this))
{
this->table_view->setModel(table_base);
table_base->setHorizontalHeaderLabels(QStringList() << "情节名称" << "单元名称" << "索引值");
auto layout = new QVBoxLayout(this);
layout->addWidget(table_view);
connect(this->table_view, &QTableView::doubleClicked, this, &FragmentsOrderView::double_click);
}
void FragmentsOrderView::refresh()
{
table_base->clear();
table_base->setHorizontalHeaderLabels(QStringList() << "情节名称" << "单元名称" << "索引值");
auto node_list = core_ins->parseCore()->queryOrdersFragment();
for(auto &ins : node_list){
QList<QStandardItem*> row;
row << new QStandardItem(ins.first->name()[0]);
row << new QStandardItem(ins.first->name()[1]);
row << new QStandardItem(QString("%1").arg(ins.second, 8, 'f'));
for(auto &i : row) i->setEditable(false);
table_base->appendRow(row);
}
}
void FragmentsOrderView::double_click(const QModelIndex &index)
{
if(!index.isValid())
return;
auto frag = table_base->item(index.row());
auto unit = table_base->item(index.row(), 1);
QList<QString> path;
path << unit->text() << frag->text();
auto unit_ins = this->core_ins->parseCore()->queryStoryUnit(path[0]).first();
auto unit_doc = unit_ins->doc();
this->core_ins->openTextDocument(unit_doc->filePath(), unit_doc->docName());
auto present = this->core_ins->getFramework()->queryTextComponent(QFileInfo(unit_doc->filePath()));
if(path.size()){
present->jumpTo(path);
}
}

View File

@ -0,0 +1,31 @@
#ifndef FRAGMENTSORDERVIEW_H
#define FRAGMENTSORDERVIEW_H
#include <QStandardItemModel>
#include <QTableView>
#include <QWidget>
#include <libParse.h>
#include "appcore.h"
namespace Components {
class FragmentsOrderView : public QWidget
{
Q_OBJECT
public:
explicit FragmentsOrderView(Core::AppCore *core, QWidget *parent = nullptr);
void refresh();
void double_click(const QModelIndex &index);
private:
Core::AppCore *const core_ins;
QTableView *const table_view;
QStandardItemModel *const table_base;
};
}
#endif // FRAGMENTSORDERVIEW_H

View File

@ -45,7 +45,8 @@ MainWindow::MainWindow(QWidget *parent)
units_view(new StoryUnitsPresent(app_core, this)),
errors_present(new MessagePresent(app_core->getMake_tool(), this)),
boards_view(new StoryBoardsPresent(app_core, this)),
concept_view(new StoryConceptsPresent(app_core, this))
concept_view(new StoryConceptsPresent(app_core, this)),
fragments_order(new FragmentsOrderView(app_core, this))
{
QApplication::instance()->installEventFilter(this);
this->app_core->setCurrentProject(project_manager);
@ -58,6 +59,7 @@ MainWindow::MainWindow(QWidget *parent)
errors_present->setVisible(false);
boards_view->setVisible(false);
concept_view->setVisible(false);
fragments_order->setVisible(false);
project_structure->setVisible(false);
left_funcs->setVisible(false);
right_funcs->setVisible(false);
@ -277,6 +279,15 @@ MainWindow::MainWindow(QWidget *parent)
sync_kernel->registerAutoRun([this]()->bool{return right_funcs->indexOf(concept_view)!=-1;},
[concept_v](bool v){if(v != concept_v->isChecked()) concept_v->setChecked(v);});
}
// 情节序列
{
auto fragments_v = func->addAction("情节序列", [this](bool v){
toggle_widget_visible(v, right_funcs, fragments_order, "情节序列");
});
fragments_v->setCheckable(true);
sync_kernel->registerAutoRun([this]()->bool{return right_funcs->indexOf(fragments_order)!=-1;},
[fragments_v](bool v){if(v != fragments_v->isChecked()) fragments_v->setChecked(v);});
}
// 工具菜单
auto tool = mbar->addMenu("工具");
@ -361,6 +372,7 @@ MainWindow::MainWindow(QWidget *parent)
this->errors_present->refresh();
this->boards_view->refresh();
this->concept_view->refresh();
this->fragments_order->refresh();
});
@ -425,6 +437,7 @@ void MainWindow::build_internal(bool all_from_disk)
units_view->refresh();
boards_view->refresh();
concept_view->refresh();
fragments_order->refresh();
}
void MainWindow::toggle_widget_visible(bool visible, QTabWidget *con, QWidget *target, const QString &title)

View File

@ -16,6 +16,7 @@
#include "ContentPresent.h"
#include "storyboardspresent.h"
#include "storyconceptspresent.h"
#include "fragmentsorderview.h"
#include "tools.h"
class MainWindow : public QMainWindow
@ -49,6 +50,7 @@ private:
Components::MessagePresent *const errors_present;
Components::StoryBoardsPresent *const boards_view;
Components::StoryConceptsPresent *const concept_view;
Components::FragmentsOrderView *const fragments_order;
// 内部逻辑 ===========================================
void build_internal(bool all_from_disk = false);

View File

@ -18,7 +18,12 @@ void NodeStoryBoard::setIndex(const QString &val)
QString NodeStoryBoard::index() const
{
return index_store;
return this->index_store;
}
int NodeStoryBoard::indexValue(bool &valid) const
{
return index_store.toInt(&valid);
}
bool NodeStoryBoard::check(QList<ErrorMessage> &reasons) const
@ -26,7 +31,7 @@ bool NodeStoryBoard::check(QList<ErrorMessage> &reasons) const
auto nodes = doc()->core()->queryStoryBoard(name()[0]);
if(nodes.size() > 1){
ErrorMessage ins;
ErrorMessage ins(this);
ins.Reason = "重复定义大纲";
ins.Text = name()[0];
ins.FilePath = doc()->filePath();
@ -35,12 +40,27 @@ bool NodeStoryBoard::check(QList<ErrorMessage> &reasons) const
reasons << ins;
}
bool is_valid = false;
indexValue(is_valid);
if(!is_valid){
ErrorMessage msg(this);
msg.CodeRow = refered().first()->row();
msg.CodeCol = refered().first()->column();
msg.FilePath = doc()->filePath();
msg.Text = index();
msg.Reason = "指定故事编排索引格式错误";
reasons << msg;
return false;
}
return nodes.size() == 1;
}
QString NodeStoryBoard::toString() const
{
QString des = "#故事 "+name()[0] + " " + index() +" {";
bool ignore;
QString des = "#故事 "+name()[0] + " " + QString("%1").arg(indexValue(ignore)) +" {";
for(auto n : children())
des += "\n" + n->toString();
des += "\n}";
@ -59,11 +79,16 @@ QString NodeStoryFragmentRefer::unit() const{
return this->unit_name_store;
}
QString NodeStoryFragmentRefer::fragment() const
{
return this->fragment_name;
}
bool NodeStoryFragmentRefer::check(QList<ErrorMessage> &reasons) const
{
auto unitx = doc()->core()->queryStoryUnit(unit());
if(!unitx.size()){
ErrorMessage ins;
ErrorMessage ins(this);
ins.Reason = "指定的单元不存在";
ins.Text = unit();
ins.FilePath = doc()->filePath();
@ -75,7 +100,7 @@ bool NodeStoryFragmentRefer::check(QList<ErrorMessage> &reasons) const
auto fragment = doc()->core()->queryStoryFragment(unitx[0], name()[0]);
if(!fragment.size()){
ErrorMessage ins;
ErrorMessage ins(this);
ins.Reason = "指定的情节不存在";
ins.Text = unit() + "" + name()[0];
ins.FilePath = doc()->filePath();

View File

@ -19,6 +19,7 @@ namespace Parse {
void setIndex(const QString &val);
QString index() const;
int indexValue(bool &valid) const;
// DesNode interface
public:
@ -58,6 +59,8 @@ namespace Parse {
void setUnit(const QString &name);
QString unit() const;
QString fragment() const;
// DesNode interface
public:
virtual bool check(QList<ErrorMessage> &reasons) const override;

View File

@ -155,7 +155,7 @@ bool NodeStoryChain::check(QList<ErrorMessage> &reasons) const
{
auto nodes = doc()->core()->queryStoryChain(name()[0]);
if(nodes.size() > 1){
ErrorMessage ins;
ErrorMessage ins(this);
ins.Reason = "重复定义脉络";
ins.Text = name()[0];
ins.FilePath = doc()->filePath();
@ -190,7 +190,8 @@ bool NodeStoryPoint::check(QList<ErrorMessage> &reasons) const
auto chain = parent();
auto nodes = chain->doc()->core()->queryStoryPoint(chain, name()[0]);
if(nodes.size() > 1){ ErrorMessage ins;
if(nodes.size() > 1){
ErrorMessage ins(this);
ins.Reason = "重复定义脉络节点";
ins.Text = static_cast<NamedNode*>(chain)->name()[0] +""+ name()[0];
ins.FilePath = doc()->filePath();

View File

@ -79,7 +79,8 @@ bool NodeStoryDepiction::check(QList<ErrorMessage> &reasons) const
{
auto nodes = doc()->core()->queryStoryDepiction(name()[0]);
if(nodes.size() > 1){ ErrorMessage ins;
if(nodes.size() > 1){
ErrorMessage ins(this);
ins.Reason = "重复定义叙述";
ins.Text = name()[0];
ins.FilePath = doc()->filePath();

View File

@ -9,9 +9,10 @@
using namespace MakeTools;
using namespace Parse;
using namespace Parse::Result;
using namespace CheckTools;
StoryTool::StoryTool(Parse::Result::ParseCore *core)
: parse_core(core){}
: parse_core(core), fragment_check(new FragmentsCheck(core)){}
QList<QString> StoryTool::compile(const QFileInfo &file, const QString &doc_name)
{
@ -118,7 +119,7 @@ bool StoryTool::checkPass(QList<ErrorMessage> &errors)
auto docs = this->parse_core->allDocuments();
for(auto &d : docs){
for(auto &w : d->unknowns()->refered()){
ErrorMessage error;
ErrorMessage error(w->host());
error.Reason = "无法识别内容";
error.Text = w->toString();
error.FilePath = d->filePath();
@ -131,6 +132,7 @@ bool StoryTool::checkPass(QList<ErrorMessage> &errors)
for(auto &n : this->parse_core->queryRootNodes(d))
error_check(n, errors);
}
fragment_check->check(errors);
return errors.size() == 0;
}

View File

@ -3,6 +3,7 @@
#include "SyntaxBase.h"
#include "libParse.h"
#include "parsechecks.h"
#include <QFileInfo>
@ -22,6 +23,7 @@ namespace MakeTools {
private:
Parse::Result::ParseCore *const parse_core;
CheckTools::FragmentsCheck *const fragment_check;
bool error_check(Parse::Result::DesNode *node, QList<Parse::ErrorMessage> &err_out);
};

View File

@ -14,7 +14,7 @@ bool NodeStoryUnit::check(QList<ErrorMessage> &reasons) const
auto unit_nodes = doc()->core()->queryStoryUnit(name()[0]);
if(unit_nodes.size() > 1){
ErrorMessage ins;
ErrorMessage ins(this);
ins.Reason = "重复定义单元";
ins.Text = name()[0];
ins.FilePath = doc()->filePath();
@ -22,6 +22,7 @@ bool NodeStoryUnit::check(QList<ErrorMessage> &reasons) const
ins.CodeCol = refered().first()->column();
reasons << ins;
}
return unit_nodes.size() == 1;
}
@ -35,14 +36,24 @@ QString NodeStoryUnit::toString() const
}
NodeStoryFragment::NodeStoryFragment(NodeStoryUnit * unit, const QString & name)
: Result::NamedNode(name, unit->doc(), NODE_STORYFRAGMENT, unit){ store_name = name; }
NodeStoryFragment::NodeStoryFragment(NodeStoryUnit * unit, const QString & name, const QString &order)
: Result::NamedNode(name, unit->doc(), NODE_STORYFRAGMENT, unit){ store_name = name; order_text = order; }
QString NodeStoryFragment::order() const
{
return order_text;
}
double NodeStoryFragment::orderValue(bool &isvalid) const
{
return order_text.toDouble(&isvalid);
}
bool NodeStoryFragment::check(QList<ErrorMessage> &reasons) const
{
auto nodes = doc()->core()->queryStoryFragment(parent(), name()[0]);
if(nodes.size() > 1){
ErrorMessage ins;
ErrorMessage ins(this);
ins.Reason = "重复定义情节";
ins.Text = name()[0];
ins.FilePath = doc()->filePath();
@ -51,13 +62,27 @@ bool NodeStoryFragment::check(QList<ErrorMessage> &reasons) const
reasons << ins;
}
bool isvalid = false;
this->orderValue(isvalid);
if(!isvalid){
ErrorMessage msg(this);
msg.CodeRow = refered().first()->row();
msg.CodeCol = refered().first()->column();
msg.FilePath = doc()->filePath();
msg.Text = this->order();
msg.Reason = "指定情节序列格式错误";
reasons << msg;
return false;
}
return nodes.size() == 1;
}
QString NodeStoryFragment::toString() const
{
QString rets = QString(depth(), ' ') + "#情节 " + name()[0] + "{";
for (auto cin : children())
QString rets = QString(depth(), ' ') + "#情节 " + name()[0] +" " + order() + "{";
for (auto &cin : children())
rets += "\n" + QString(depth(), ' ') + cin->toString();
return rets + "\n"+QString(depth(), ' ') + "}";
}
@ -88,7 +113,7 @@ bool NodeStoryPointRefer::check(QList<ErrorMessage> &reasons) const
{
auto chain = doc()->core()->queryStoryChain(chainName());
if(!chain.size()){
ErrorMessage ins;
ErrorMessage ins(this);
ins.Reason = "指定脉络不存在";
ins.Text = chainName();
ins.FilePath = doc()->filePath();
@ -100,7 +125,7 @@ bool NodeStoryPointRefer::check(QList<ErrorMessage> &reasons) const
else{
auto point = doc()->core()->queryStoryPoint(chain[0], pointName());
if(!point.size()){
ErrorMessage ins;
ErrorMessage ins(this);
ins.Reason = "指定脉络节点不存在";
ins.Text = chainName() + "" + pointName();
ins.FilePath = doc()->filePath();
@ -118,72 +143,6 @@ QString NodeStoryPointRefer::toString() const
return QString("{@节点 %1 %2}").arg(chain_name).arg(point_name);
}
//NodeStoryFragmentComment::NodeStoryFragmentComment(DesNode * parent,
// const QString &order, const QString & name)
// : parent_ins(parent), name_store(name), order_name(order)
//{
//}
//QString NodeStoryFragmentComment::order() const
//{
// return order_name;
//}
//DocCore * NodeStoryFragmentComment::document() const
//{
// return parent_ins->document();
//}
//int NodeStoryFragmentComment::typeValue() const
//{
// return NODE_ORDEREDCOMMENT;
//}
//DesNode * NodeStoryFragmentComment::parent() const
//{
// return parent_ins;
//}
//void NodeStoryFragmentComment::appendChild(DesNode * ins)
//{
// children_nodes << ins;
//}
//QList<DesNode*> NodeStoryFragmentComment::children() const
//{
// return children_nodes;
//}
//bool NodeStoryFragmentComment::check(QList<QString>& reasons) const
//{
// return false;
//}
//QString NodeStoryFragmentComment::toString() const
//{
// auto xrets = QString(depth(), ' ') + "#注解 " + name() +" "+ order() +" "+ orderValue() + "{";
// for (auto it : children_nodes)
// xrets += "\n" + QString(depth(), ' ') + it->toString();
// xrets += "\n" + QString(depth(), ' ') + "}";
// return xrets;
//}
//QString NodeStoryFragmentComment::name() const
//{
// return name_store;
//}
//QString NodeStoryFragmentComment::orderValue() const
//{
// return order_value;
//}
//void NodeStoryFragmentComment::resetValue(const QString &value)
//{
// this->order_value = value;
//}
NodeStoryUnitParser::NodeStoryUnitParser(ParseCore * core)
: XSyntaxBase("故事单元"), pjt_core(core)
{
@ -256,22 +215,25 @@ NodeStoryFragmentParser::NodeStoryFragmentParser(NodeStoryUnitParser * pparser)
{
set_common_expression("::换行前缀", {Elm("{换行符}"),Elm("{换行符}", true)});
auto rule = addRule("进入情节解析", 0, [this](const QList<LexResult> &seqs, int cnt)->ParseResult {
auto nmidx = cnt - 1, defidx = cnt - 2;;
auto nmidx = cnt - 2, defidx = cnt - 3, ordidx=cnt-1;
auto parent_parser = nodeStoryUnitParser();
auto node = new NodeStoryFragment(static_cast<NodeStoryUnit*>(parent_parser->currNode()), seqs[nmidx].Text);
auto node = new NodeStoryFragment(static_cast<NodeStoryUnit*>(parent_parser->currNode()),
seqs[nmidx].Text, seqs[ordidx].Text);
this->refocusNode(node);
parent_parser->currNode()->appendChild(node);
auto word0 = new Words(node, docRef(), seqs[defidx].Text, seqs[defidx].StartRow, seqs[defidx].StartCol);
auto word1 = new Words(node, docRef(), seqs[nmidx].Text, seqs[nmidx].StartRow, seqs[nmidx].StartCol);
auto word2 = new Words(node, docRef(), seqs[ordidx].Text, seqs[ordidx].StartRow, seqs[ordidx].StartCol);
docRef()->append(word0);
docRef()->append(word1);
docRef()->append(word2);
return ParseResult::SelfManipulate;
});
rule->addExpression("基础情节解析", { Elm("{情节定义}"), Elm("{描述文本}", true) });
rule->addExpression("基础情节解析", { Elm("{情节定义}"), Elm("{描述文本}1"), Elm("{描述文本}2", true) });
rule->addExpression("拓展情节解析", { Exp("::换行前缀"), Exp("基础情节解析", true) });
rule = addRule("情节成分解析", 1, [this](const QList<LexResult> &seqs, int cnt)->ParseResult {

View File

@ -37,9 +37,12 @@ namespace Parse {
class NodeStoryFragment : public Result::NamedNode
{
public:
explicit NodeStoryFragment(NodeStoryUnit* unit, const QString &name);
explicit NodeStoryFragment(NodeStoryUnit* unit, const QString &name, const QString& order);
virtual ~NodeStoryFragment() = default;
QString order() const;
double orderValue(bool &isvalid) const;
// 通过 NamedNode 继承
virtual bool check(QList<ErrorMessage>& reasons) const override;
virtual QString toString() const override;
@ -48,6 +51,7 @@ namespace Parse {
private:
QString store_name;
QString order_text;
};
/**

View File

@ -1,5 +1,6 @@
#include "libParse.h"
#include "SyntaxBase.h"
#include "StoryUnitDocumentParser.h"
#include <QFileInfo>
using namespace Parse;
@ -29,6 +30,8 @@ namespace Parse {
};
}
ErrorMessage::ErrorMessage(const DesNode *obj): object(obj){}
NamedNode::NamedNode(const QString &name, DocCore *core, int type, DesNode *pnode)
: Result::DesNode(core, type, pnode), name_store(name){}
@ -230,6 +233,33 @@ QList<Result::DesNode*> ParseCore::queryStoryFragment(DesNode *unit, const QStri
return retlist;
}
QList<std::pair<NamedNode *, double> > ParseCore::queryOrdersFragment() const
{
QList<std::pair<NamedNode*, double>> node_list;
auto units = allStoryUnits();
for(auto &uins : units){
auto children = uins->children();
for(auto &c : children){
if(c->typeValue() != NODE_STORYFRAGMENT)
continue;
bool isvalid;
auto fragment = static_cast<NodeStoryFragment*>(c);
node_list << std::make_pair(fragment, fragment->orderValue(isvalid));
}
}
std::sort(node_list.begin(), node_list.end(),
[](const std::pair<NamedNode*, double> &a, const std::pair<NamedNode*, double> &b)->bool{
bool valid;
auto val_a = static_cast<NodeStoryFragment*>(a.first)->orderValue(valid);
auto val_b = static_cast<NodeStoryFragment*>(b.first)->orderValue(valid);
return val_a < val_b;
});
return node_list;
}
QList<DesNode *> ParseCore::allStoryBoards() const
{
QList<Result::DesNode*> retlist;

View File

@ -10,20 +10,28 @@
namespace Parse
{
struct ErrorMessage
namespace Result
{
class DesNode;
}
class ErrorMessage
{
public:
ErrorMessage(const Result::DesNode *obj);
QString Reason;
QString Text;
QString FilePath;
int CodeRow;
int CodeCol;
const Result::DesNode *const object;
};
namespace Result
{
namespace Result{
class ParseCore;
class DocCore;
class DesNode;
enum class DocType
{
@ -314,6 +322,7 @@ namespace Parse
virtual QList<Result::DesNode*> allStoryUnits() const;
virtual QList<Result::DesNode*> queryStoryUnit(const QString &name) const;
virtual QList<Result::DesNode*> queryStoryFragment(Result::DesNode *unit, const QString &name) const;
virtual QList<std::pair<Result::NamedNode*, double>> queryOrdersFragment() const;
virtual QList<Result::DesNode*> allStoryBoards() const;
virtual QList<Result::DesNode*> queryStoryBoard(const QString &name) const;

View File

@ -20,6 +20,7 @@ SOURCES += \
WordsPeak.cpp \
XSyntaxBase.cpp \
libParse.cpp \
parsechecks.cpp \
storyconceptdocumentparser.cpp
HEADERS += \
@ -36,6 +37,7 @@ HEADERS += \
XSyntaxBase.h \
libParse.h \
libParse_global.h \
parsechecks.h \
storyconceptdocumentparser.h
TRANSLATIONS += \

49
libParse/parsechecks.cpp Normal file
View File

@ -0,0 +1,49 @@
#include "parsechecks.h"
#include "StoryBoardDocumentParser.h"
#include "StoryUnitDocumentParser.h"
#include "../WordsIDE/opstream.h"
using namespace Parse;
CheckTools::FragmentsCheck::FragmentsCheck(Parse::Result::ParseCore *const core)
: core_ins(core){}
bool CheckTools::FragmentsCheck::check(QList<Parse::ErrorMessage> &reasons) const
{
auto stories = core_ins->allStoryBoards();
// 编排索引顺序校验
for(auto &ins : stories){
auto xins = static_cast<Parse::NodeStoryBoard*>(ins);
double temp = -DBL_MAX;
auto refers = xins->children();
for(auto &ref : refers){
if(ref->typeValue() == NODE_FRAGMENTREFERENCE){
auto ins_ref = static_cast<NodeStoryFragmentRefer*>(ref);
auto u = core_ins->queryStoryUnit(ins_ref->unit());
auto frag = core_ins->queryStoryFragment(u[0], ins_ref->fragment());
auto frag_ins = static_cast<NodeStoryFragment*>(frag[0]);
bool isvalid;
double order_value = frag_ins->orderValue(isvalid);
if(temp > order_value)
{
ErrorMessage msg(ins_ref);
msg.CodeRow = ins_ref->refered().first()->row();
msg.CodeCol = ins_ref->refered().first()->column();
msg.FilePath = ins_ref->doc()->filePath();
msg.Text = ins_ref->unit() + ""+ ins_ref->fragment();
msg.Reason = QString("%1指定节点索引顺序颠倒").arg(ins_ref->fragment());
reasons << msg;
return false;
}
temp = order_value;
}
}
}
return true;
}

47
libParse/parsechecks.h Normal file
View File

@ -0,0 +1,47 @@
#ifndef PARSECHECKS_H
#define PARSECHECKS_H
#include "libParse.h"
namespace CheckTools {
/**
* @brief
*/
class FragmentsCheck
{
public:
FragmentsCheck(Parse::Result::ParseCore *const core);
/**
* @brief
* @param reasons
* @return
*/
bool check(QList<Parse::ErrorMessage> &reasons) const;
private:
Parse::Result::ParseCore *const core_ins;
};
}
#endif // PARSECHECKS_H

View File

@ -32,7 +32,7 @@ bool NodeStoryConcept::check(QList<ErrorMessage> &reasons) const
{
auto nodes = doc()->core()->queryStoryConcept(name()[0]);
if(nodes.size() > 1){
ErrorMessage ins;
ErrorMessage ins(this);
ins.CodeRow = refered().first()->row();
ins.CodeCol = refered().first()->column();
ins.FilePath = doc()->filePath();
@ -66,7 +66,7 @@ bool NodeStoryStrongPoint::check(QList<ErrorMessage> &reasons) const
auto concept = parent();
auto nodes = doc()->core()->queryStoryStrongPoint(concept, name()[0]);
if(nodes.size() > 1){
ErrorMessage ins;
ErrorMessage ins(this);
ins.CodeRow = refered().first()->row();
ins.CodeCol = refered().first()->column();
ins.FilePath = doc()->filePath();