summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--src/qdoc/generator.cpp21
-rw-r--r--src/qdoc/node.cpp75
-rw-r--r--src/qdoc/node.h12
-rw-r--r--src/qdoc/qdocdatabase.cpp4
-rw-r--r--src/qdoc/qdocindexfiles.cpp17
5 files changed, 110 insertions, 19 deletions
diff --git a/src/qdoc/generator.cpp b/src/qdoc/generator.cpp
index 71da36e3c..e80fa5a4c 100644
--- a/src/qdoc/generator.cpp
+++ b/src/qdoc/generator.cpp
@@ -1294,12 +1294,27 @@ void Generator::generateReimplementsClause(const FunctionNode *fn, CodeMarker *m
ClassNode* cn = static_cast<ClassNode*>(fn->parent());
const FunctionNode *overrides = cn->findOverriddenFunction(fn);
if (overrides && !overrides->isPrivate() && !overrides->parent()->isPrivate()) {
+ if (overrides->hasDoc()) {
+ Text text;
+ text << Atom::ParaLeft << "Reimplements: ";
+ QString fullName = overrides->parent()->name() + "::" + overrides->signature(false, true);
+ appendFullName(text, overrides->parent(), fullName, overrides);
+ text << "." << Atom::ParaRight;
+ generateText(text, fn, marker);
+ return;
+ }
+ }
+ const PropertyNode* sameName = cn->findOverriddenProperty(fn);
+ if (sameName && sameName->hasDoc()) {
Text text;
- text << Atom::ParaLeft << "Reimplements: ";
- QString fullName = overrides->parent()->name() + "::" + overrides->signature(false, true);
- appendFullName(text, overrides->parent(), fullName, overrides);
+ text << Atom::ParaLeft << "Reimplements an access function for property: ";
+ QString fullName = sameName->parent()->name() + "::" + sameName->name();
+ appendFullName(text, sameName->parent(), fullName, sameName);
text << "." << Atom::ParaRight;
generateText(text, fn, marker);
+ } else {
+ fn->doc().location().warning(tr("Illegal \\reimp; no documented virtual function for %1")
+ .arg(fn->plainSignature()));
}
}
}
diff --git a/src/qdoc/node.cpp b/src/qdoc/node.cpp
index c664aea63..2ec58dc3a 100644
--- a/src/qdoc/node.cpp
+++ b/src/qdoc/node.cpp
@@ -307,6 +307,7 @@ Node::Node(NodeType type, Aggregate *parent, const QString& name)
status_(Active),
indexNodeFlag_(false),
relatedNonmember_(false),
+ hadDoc_(false),
parent_(parent),
sharedCommentNode_(nullptr),
name_(name)
@@ -1084,7 +1085,7 @@ FunctionNode *Aggregate::findFunctionChild(const QString &name, const Parameters
/*!
Find the function node that is a child of this node, such
that the function described has the same name and signature
- as the function described by the \a clone node.
+ as the function described by the function node \a clone.
*/
FunctionNode *Aggregate::findFunctionChild(const FunctionNode *clone)
{
@@ -1856,7 +1857,7 @@ FunctionNode* ClassNode::findOverriddenFunction(const FunctionNode* fn)
}
if (cn != nullptr) {
FunctionNode *result = cn->findFunctionChild(fn);
- if (result != nullptr && !result->isNonvirtual() && result->hasDoc())
+ if (result != nullptr && !result->isInternal() && !result->isNonvirtual() && result->hasDoc())
return result;
result = cn->findOverriddenFunction(fn);
if (result != nullptr && !result->isNonvirtual())
@@ -1868,6 +1869,44 @@ FunctionNode* ClassNode::findOverriddenFunction(const FunctionNode* fn)
}
/*!
+ \a fn is an overriding function in this class or in a class
+ derived from this class. Find the node for the property that
+ \a fn overrides in this class's children or in one of this
+ class's base classes. Return a pointer to the overridden
+ property or return 0.
+ */
+PropertyNode* ClassNode::findOverriddenProperty(const FunctionNode* fn)
+{
+ QList<RelatedClass>::Iterator bc = bases_.begin();
+ while (bc != bases_.end()) {
+ ClassNode *cn = bc->node_;
+ if (cn == nullptr) {
+ cn = QDocDatabase::qdocDB()->findClassNode(bc->path_);
+ bc->node_ = cn;
+ }
+ if (cn != nullptr) {
+ const NodeList &children = cn->childNodes();
+ NodeList::const_iterator i = children.begin();
+ while (i != children.end()) {
+ if ((*i)->isProperty()) {
+ PropertyNode *pn = static_cast<PropertyNode*>(*i);
+ if (pn->name() == fn->name() || pn->hasAccessFunction(fn->name())) {
+ if (pn->hasDoc())
+ return pn;
+ }
+ }
+ i++;
+ }
+ PropertyNode *result = cn->findOverriddenProperty(fn);
+ if (result != nullptr)
+ return result;
+ }
+ ++bc;
+ }
+ return nullptr;
+}
+
+/*!
Returns true if the class or struct represented by this class
node must be documented. If this function returns true, then
qdoc must find a qdoc comment for this class. If it returns
@@ -2732,6 +2771,38 @@ QString PropertyNode::qualifiedDataType() const
}
}
+/*!
+ Returns true if this property has an access function named \a name.
+ */
+bool PropertyNode::hasAccessFunction(const QString &name) const
+{
+ NodeList::const_iterator i = getters().begin();
+ while (i != getters().end()) {
+ if ((*i)->name() == name)
+ return true;
+ ++i;
+ }
+ i = setters().begin();
+ while (i != setters().end()) {
+ if ((*i)->name() == name)
+ return true;
+ ++i;
+ }
+ i = resetters().begin();
+ while (i != resetters().end()) {
+ if ((*i)->name() == name)
+ return true;
+ ++i;
+ }
+ i = notifiers().begin();
+ while (i != notifiers().end()) {
+ if ((*i)->name() == name)
+ return true;
+ ++i;
+ }
+ return false;
+}
+
bool QmlTypeNode::qmlOnly = false;
QMultiMap<const Node*, Node*> QmlTypeNode::inheritedBy;
diff --git a/src/qdoc/node.h b/src/qdoc/node.h
index 6deb9f8c0..b163541b9 100644
--- a/src/qdoc/node.h
+++ b/src/qdoc/node.h
@@ -258,6 +258,7 @@ public:
void setReconstitutedBrief(const QString &t) { reconstitutedBrief_ = t; }
void setParent(Aggregate* n) { parent_ = n; }
void setIndexNodeFlag(bool isIndexNode = true) { indexNodeFlag_ = isIndexNode; }
+ void setHadDoc() { hadDoc_ = true; }
virtual void setRelatedNonmember(bool b) { relatedNonmember_ = b; }
virtual void setOutputFileName(const QString& ) { }
virtual void addMember(Node* ) { }
@@ -307,7 +308,8 @@ public:
const Location& defLocation() const { return defLocation_; }
const Location& location() const { return (defLocation_.isEmpty() ? declLocation_ : defLocation_); }
const Doc& doc() const { return doc_; }
- bool hasDoc() const { return !doc_.isEmpty(); }
+ bool hasDoc() const { return (hadDoc_ || !doc_.isEmpty()); }
+ bool hadDoc() const { return hadDoc_; }
Status status() const { return status_; }
Status inheritedStatus() const;
ThreadSafeness threadSafeness() const;
@@ -369,6 +371,7 @@ private:
Status status_;
bool indexNodeFlag_ : 1;
bool relatedNonmember_ : 1;
+ bool hadDoc_ : 1;
Aggregate* parent_;
SharedCommentNode *sharedCommentNode_;
@@ -533,7 +536,7 @@ class NamespaceNode : public Aggregate
{
public:
NamespaceNode(Aggregate* parent, const QString& name) : Aggregate(Namespace, parent, name),
- seen_(false), documented_(false), tree_(nullptr), docNode_(nullptr) { }
+ seen_(false), tree_(nullptr), docNode_(nullptr) { }
virtual ~NamespaceNode();
Tree* tree() const override { return (parent() ? parent()->tree() : tree_); }
@@ -551,14 +554,11 @@ public:
bool hasDocumentedChildren() const;
void reportDocumentedChildrenInUndocumentedNamespace() const;
bool docMustBeGenerated() const override;
- void setDocumented() { documented_ = true; }
- bool wasDocumented() const { return documented_; }
void setDocNode(NamespaceNode* ns) { docNode_ = ns; }
NamespaceNode* docNode() const { return docNode_; }
private:
bool seen_;
- bool documented_;
Tree* tree_;
QString whereDocumented_;
NamespaceNode* docNode_;
@@ -633,6 +633,7 @@ public:
PropertyNode* findPropertyNode(const QString& name);
QmlTypeNode* findQmlBaseNode();
FunctionNode* findOverriddenFunction(const FunctionNode* fn);
+ PropertyNode* findOverriddenProperty(const FunctionNode* fn);
bool docMustBeGenerated() const override;
private:
@@ -1130,6 +1131,7 @@ public:
const NodeList &setters() const { return functions(Setter); }
const NodeList &resetters() const { return functions(Resetter); }
const NodeList &notifiers() const { return functions(Notifier); }
+ bool hasAccessFunction(const QString &name) const;
FunctionRole role(const FunctionNode* fn) const;
bool isStored() const { return fromFlagValue(stored_, storedDefault()); }
bool isDesignable() const { return fromFlagValue(designable_, designableDefault()); }
diff --git a/src/qdoc/qdocdatabase.cpp b/src/qdoc/qdocdatabase.cpp
index aefed5615..ef2b5ab33 100644
--- a/src/qdoc/qdocdatabase.cpp
+++ b/src/qdoc/qdocdatabase.cpp
@@ -1185,14 +1185,14 @@ void QDocDatabase::resolveNamespaces()
ns = static_cast<NamespaceNode*>(n);
if (ns->isDocumentedHere())
break;
- else if (ns->wasDocumented())
+ else if (ns->hadDoc())
somewhere = ns;
ns = nullptr;
}
if (ns) {
foreach (Node *n, namespaces) {
NamespaceNode* NS = static_cast<NamespaceNode*>(n);
- if (NS->wasDocumented() && NS != ns) {
+ if (NS->hadDoc() && NS != ns) {
ns->doc().location().warning(tr("Namespace %1 documented more than once")
.arg(NS->name()));
NS->doc().location().warning(tr("...also seen here"));
diff --git a/src/qdoc/qdocindexfiles.cpp b/src/qdoc/qdocindexfiles.cpp
index 617c132f2..efd9adefd 100644
--- a/src/qdoc/qdocindexfiles.cpp
+++ b/src/qdoc/qdocindexfiles.cpp
@@ -204,11 +204,6 @@ void QDocIndexFiles::readIndexSection(QXmlStreamReader& reader,
location = Location(indexUrl + QLatin1Char('/') + name.toLower() + ".html");
else if (!indexUrl.isNull())
location = Location(name.toLower() + ".html");
- if (attributes.hasAttribute(QLatin1String("documented"))) {
- if (attributes.value(QLatin1String("documented")) == QLatin1String("true"))
- ns->setDocumented();
- }
-
} else if (elementName == QLatin1String("class") || elementName == QLatin1String("struct") ||
elementName == QLatin1String("union")) {
Node::NodeType type = Node::Class;
@@ -604,6 +599,11 @@ void QDocIndexFiles::readIndexSection(QXmlStreamReader& reader,
node->setSince(since);
}
+ if (attributes.hasAttribute(QLatin1String("documented"))) {
+ if (attributes.value(QLatin1String("documented")) == QLatin1String("true"))
+ node->setHadDoc();
+ }
+
QString groupsAttr = attributes.value(QLatin1String("groups")).toString();
if (!groupsAttr.isEmpty()) {
QStringList groupNames = groupsAttr.split(QLatin1Char(','));
@@ -936,6 +936,9 @@ bool QDocIndexFiles::generateIndexSection(QXmlStreamWriter &writer, Node *node,
if (!node->since().isEmpty())
writer.writeAttribute("since", node->since());
+ if (node->hasDoc())
+ writer.writeAttribute("documented", "true");
+
QString brief = node->doc().trimmedBriefText(node->name()).toString();
switch (node->nodeType()) {
case Node::Class:
@@ -970,7 +973,6 @@ bool QDocIndexFiles::generateIndexSection(QXmlStreamWriter &writer, Node *node,
case Node::HeaderFile:
{
const HeaderNode* hn = static_cast<const HeaderNode*>(node);
- writer.writeAttribute("documented", hn->hasDoc() ? "true" : "false");
if (!hn->physicalModuleName().isEmpty())
writer.writeAttribute("module", hn->physicalModuleName());
if (!hn->groupNames().isEmpty())
@@ -985,7 +987,6 @@ bool QDocIndexFiles::generateIndexSection(QXmlStreamWriter &writer, Node *node,
case Node::Namespace:
{
const NamespaceNode* ns = static_cast<const NamespaceNode*>(node);
- writer.writeAttribute("documented", ns->hasDoc() ? "true" : "false");
if (!ns->physicalModuleName().isEmpty())
writer.writeAttribute("module", ns->physicalModuleName());
if (!ns->groupNames().isEmpty())
@@ -1333,6 +1334,8 @@ void QDocIndexFiles::generateFunctionSection(QXmlStreamWriter &writer, FunctionN
writer.writeAttribute("lineno", QString("%1").arg(declLocation.lineNo()));
}
+ if (fn->hasDoc())
+ writer.writeAttribute("documented", "true");
if (fn->isRelatedNonmember())
writer.writeAttribute("related", "true");
if (!fn->since().isEmpty())