/****************************************************************************
**
** Copyright (C) 2014 Digia Plc and/or its subsidiary(-ies).
** Contact: http://www.qt-project.org/legal
**
** This file is part of the tools applications of the Qt Toolkit.
**
** $QT_BEGIN_LICENSE:LGPL$
** Commercial License Usage
** Licensees holding valid commercial Qt licenses may use this file in
** accordance with the commercial license agreement provided with the
** Software or, alternatively, in accordance with the terms contained in
** a written agreement between you and Digia. For licensing terms and
** conditions see http://qt.digia.com/licensing. For further information
** use the contact form at http://qt.digia.com/contact-us.
**
** GNU Lesser General Public License Usage
** Alternatively, this file may be used under the terms of the GNU Lesser
** General Public License version 2.1 as published by the Free Software
** Foundation and appearing in the file LICENSE.LGPL included in the
** packaging of this file. Please review the following information to
** ensure the GNU Lesser General Public License version 2.1 requirements
** will be met: http://www.gnu.org/licenses/old-licenses/lgpl-2.1.html.
**
** In addition, as a special exception, Digia gives you certain additional
** rights. These rights are described in the Digia Qt LGPL Exception
** version 1.1, included in the file LGPL_EXCEPTION.txt in this package.
**
** GNU General Public License Usage
** Alternatively, this file may be used under the terms of the GNU
** General Public License version 3.0 as published by the Free Software
** Foundation and appearing in the file LICENSE.GPL included in the
** packaging of this file. Please review the following information to
** ensure the GNU General Public License version 3.0 requirements will be
** met: http://www.gnu.org/copyleft/gpl.html.
**
**
** $QT_END_LICENSE$
**
****************************************************************************/
/*
htmlgenerator.cpp
*/
#include "codemarker.h"
#include "codeparser.h"
#include "helpprojectwriter.h"
#include "htmlgenerator.h"
#include "node.h"
#include "qdocdatabase.h"
#include "separator.h"
#include "tree.h"
#include ";
if (relative->type() == Node::Property ||
relative->type() == Node::Variable) {
QString str;
atom = atom->next();
while (atom != 0 && atom->type() != Atom::BriefRight) {
if (atom->type() == Atom::String ||
atom->type() == Atom::AutoLink)
str += atom->string();
skipAhead++;
atom = atom->next();
}
str[0] = str[0].toLower();
if (str.endsWith(QLatin1Char('.')))
str.truncate(str.length() - 1);
out() << "This ";
if (relative->type() == Node::Property)
out() << "property";
else
out() << "variable";
QStringList words = str.split(QLatin1Char(' '));
if (!(words.first() == "contains" || words.first() == "specifies"
|| words.first() == "describes" || words.first() == "defines"
|| words.first() == "holds" || words.first() == "determines"))
out() << " holds ";
else
out() << ' ';
out() << str << '.';
}
break;
case Atom::BriefRight:
if (!relative->isDocNode())
out() << " ";
in_para = true;
break;
case Atom::CaptionRight:
endLink();
if (in_para) {
out() << " you can rewrite it as For example, if you have code like"
<< trimmedTrailing(highlightedCode(indent(codeIndent,atom->string()),relative))
<< "
\n";
break;
case Atom::Qml:
out() << ""
<< trimmedTrailing(highlightedCode(indent(codeIndent,atom->string()),relative))
<< "
\n";
break;
case Atom::JavaScript:
out() << ""
<< trimmedTrailing(highlightedCode(indent(codeIndent,atom->string()),relative))
<< "
\n";
break;
case Atom::CodeNew:
out() << ""
<< trimmedTrailing(highlightedCode(indent(codeIndent,atom->string()),relative))
<< "
\n";
break;
case Atom::CodeOld:
out() << ""
<< trimmedTrailing(protectEnc(plainCode(indent(codeIndent,atom->string()))))
<< "
\n";
break;
case Atom::DivLeft:
out() << "
Class "; out() << ""; QStringList pieces = pmap.key()->fullName().split("::"); out() << protectEnc(pieces.last()); out() << "" << ":
\n"; generateSection(nlist, 0, marker, CodeMarker::Summary); out() << "";
if (fileName.isEmpty()) {
relative->location().warning(tr("Missing image: %1").arg(protectEnc(atom->string())));
out() << "[Missing image "
<< protectEnc(atom->string()) << "]";
}
else {
QString prefix;
out() << "";
helpProjectWriter->addExtraFile(fileName);
if (relative->isExample()) {
const ExampleNode* cen = static_cast
"; out() << formattingLeftMap()[ATOM_FORMATTING_BOLD]; out() << "Important: "; out() << formattingRightMap()[ATOM_FORMATTING_BOLD]; break; case Atom::ImportantRight: out() << "
"; break; case Atom::NoteLeft: out() << ""; out() << formattingLeftMap()[ATOM_FORMATTING_BOLD]; out() << "Note: "; out() << formattingRightMap()[ATOM_FORMATTING_BOLD]; break; case Atom::NoteRight: out() << "
"; break; case Atom::LegaleseLeft: out() << "Constant | "; // If not in \enum topic, skip the value column if (relative->type() == Node::Enum) out() << "Value | "; out() << "Description |
---|---|---|
Constant | Value | |
" << t << ""; if (relative->type() == Node::Enum) { out() << " | ";
const EnumNode *enume = static_cast | ";
if (matchAhead(atom, Atom::ListItemRight))
out() << " ";
}
}
else {
out() << " |
"; in_para = true; break; case Atom::ParaRight: endLink(); if (in_para) { out() << "
\n"; in_para = false; } //if (!matchAhead(atom, Atom::ListItemRight) && !matchAhead(atom, Atom::TableItemRight)) // out() << "\n"; break; case Atom::QuotationLeft: out() << ""; break; case Atom::QuotationRight: out() << "\n"; break; case Atom::RawString: out() << atom->string(); break; case Atom::SectionLeft: out() << "" << divNavTop << '\n'; break; case Atom::SectionRight: break; case Atom::SectionHeadingLeft: out() << "
"; } if (matchAhead(atom, Atom::ParaLeft)) skipAhead = 1; } break; case Atom::TableItemRight: if (inTableHeader_) out() << "
\\" << protectEnc(atom->string())
<< "
";
break;
case Atom::QmlText:
case Atom::EndQmlText:
// don't do anything with these. They are just tags.
break;
default:
unknownAtom(atom);
}
return skipAhead;
}
/*!
Generate a reference page for a C++ class or a C++ namespace.
*/
void HtmlGenerator::generateClassLikeNode(InnerNode* inner, CodeMarker* marker)
{
QList\n" << navigationLinks << "
\n"; } void HtmlGenerator::generateTitle(const QString& title, const Text &subTitle, SubTitleSize subTitleSize, const Node *relative, CodeMarker *marker) { if (!title.isEmpty()) out() << "\n" << navigationLinks << "
\n"; out() << QString(footer).replace("\\" + COMMAND_VERSION, qdb_->version()) << QString(address).replace("\\" + COMMAND_VERSION, qdb_->version()); out() << "\n"; out() << "\n"; } /*! Lists the required imports and includes in a table. The number of rows is known, so this path is simpler than the generateSection() path. */ void HtmlGenerator::generateRequisites(InnerNode *inner, CodeMarker *marker) { QMap" << *i << ":" << " | "; if (*i == headerText) out() << requisites.value(*i).toString(); else generateText(requisites.value(*i), inner, marker); out() << " |
" << *i << " | ";
if (*i == importText)
out()< |
"; generateText(brief, node, marker); if (!relative || node == relative) out() << " More...
\n"; generateExtractionMark(node, EndMark); } } void HtmlGenerator::generateIncludes(const InnerNode *inner, CodeMarker *marker) { if (!inner->includes().isEmpty()) { out() << "" << trimmedTrailing(highlightedCode(indent(codeIndent, marker->markedUpIncludes(inner->includes())), inner)) << ""; } } /*! Revised for the new doc format. Generates a table of contents beginning at \a node. */ void HtmlGenerator::generateTableOfContents(const Node *node, CodeMarker *marker, QList
This is the complete list of members for "; generateFullName(inner, 0); out() << ", including inherited members.
\n"; Section section = sections.first(); generateSectionList(section, 0, marker, CodeMarker::Subpage); generateFooter(); endSubPage(); return fileName; } /*! This function creates an html page on which are listed all the members of QML class \a qml_cn, including the inherited members. The \a marker is used for formatting stuff. */ QString HtmlGenerator::generateAllQmlMembersFile(QmlClassNode* qml_cn, CodeMarker* marker) { QListThis is the complete list of members for "; generateFullName(qml_cn, 0); out() << ", including inherited members.
\n"; ClassKeysNodesList& cknl = sections.first().classKeysNodesList_; if (!cknl.isEmpty()) { for (int i=0; iThe following members are inherited from "; generateFullName(qcn,0); out() << ".
\n"; } out() << "The following members of class " << "" << protectEnc(inner->name()) << "" << "are part of the " "Qt compatibility layer. We advise against " "using them in new code.
\n"; } else { out() << "The following members of class " << "" << protectEnc(inner->name()) << "" << " are obsolete. " << "They are provided to keep old source code working. " << "We strongly advise against using them in new code.
\n"; } for (i = 0; i < sections.size(); ++i) { out() << ""; generateFullName(node, relative); out() << " | ";
if (!node->isDocNode()) {
Text brief = node->doc().trimmedBriefText(node->name());
if (!brief.isEmpty()) {
out() << ""; generateText(brief, node, marker); out() << " | ";
}
else if (!node->reconstitutedBrief().isEmpty()) {
out() << ""; out() << node->reconstitutedBrief(); out() << " | ";
}
}
else {
out() << ""; if (!node->reconstitutedBrief().isEmpty()) { out() << node->reconstitutedBrief(); } else out() << protectEnc(node->doc().briefText().toString()); out() << " | ";
}
out() << "
"; for (int i = 0; i < 26; i++) { QChar ch('a' + i); out() << QString("%2 ").arg(ch).arg(ch.toUpper()); } out() << "
\n"; char nextLetter = 'a'; char currentLetter; out() << "";
out() << "
";
}
else {
if (twoColumn && i == (int) (nl.count() + 1) / 2)
out() << " |
|
";
out() << "
";
}
else {
if (twoColumn && i == (int) (section.members.count() + 1) / 2)
out() << " |
|
Access functions:
\n"; generateSectionList(section, node, marker, CodeMarker::Accessors); } Section notifiers; notifiers.members += property->notifiers(); if (!notifiers.members.isEmpty()) { out() << "Notifier signal:
\n"; //out() << "This signal is emitted when the property value is changed.
\n"; generateSectionList(notifiers, node, marker, CodeMarker::Accessors); } } else if (node->type() == Node::Enum) { const EnumNode *enume = static_castThe " << protectEnc(enume->flagsType()->name()) << " type is a typedef for " << "QFlags<" << protectEnc(enume->name()) << ">. It stores an OR combination of " << protectEnc(enume->name()) << " values.
\n"; } } generateAlsoList(node, marker); generateExtractionMark(node, EndMark); } int HtmlGenerator::hOffset(const Node *node) { switch (node->type()) { case Node::Namespace: case Node::Class: return 2; case Node::QmlBasicType: case Node::QmlType: case Node::Document: return 1; case Node::Enum: case Node::Typedef: case Node::Function: case Node::Property: default: return 3; } } bool HtmlGenerator::isThreeColumnEnumValueTable(const Atom *atom) { while (atom != 0 && !(atom->type() == Atom::ListRight && atom->string() == ATOM_LIST_VALUE)) { if (atom->type() == Atom::ListItemLeft && !matchAhead(atom, Atom::ListItemRight)) return true; atom = atom->next(); } return false; } const QPair"; out() << ""; generateSynopsis(qsn,relative,marker,CodeMarker::Detailed,false); out() << " |
"; out() << ""; generateSynopsis(qshn,relative,marker,CodeMarker::Detailed,false); out() << " |
"; out() << ""; generateSynopsis(qmn,relative,marker,CodeMarker::Detailed,false); out() << " |