My Project
 All Classes Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Macros Groups Pages
Classes | Macros | Functions
searchindex.h File Reference
#include <qintdict.h>
#include <qlist.h>
#include <qdict.h>
#include <qvector.h>
#include "sortdict.h"
#include "definition.h"
#include "util.h"

Go to the source code of this file.

Classes

struct  URL
 
struct  URLInfo
 
class  IndexWord
 
class  SearchIndexIntf
 
class  SearchIndex
 
class  SearchIndexExternal
 
class  SearchDefinitionList
 
class  SearchIndexList
 
struct  SearchIndexInfo
 

Macros

#define SEARCH_INDEX_ALL   0
 
#define SEARCH_INDEX_CLASSES   1
 
#define SEARCH_INDEX_NAMESPACES   2
 
#define SEARCH_INDEX_FILES   3
 
#define SEARCH_INDEX_FUNCTIONS   4
 
#define SEARCH_INDEX_VARIABLES   5
 
#define SEARCH_INDEX_TYPEDEFS   6
 
#define SEARCH_INDEX_ENUMS   7
 
#define SEARCH_INDEX_ENUMVALUES   8
 
#define SEARCH_INDEX_PROPERTIES   9
 
#define SEARCH_INDEX_EVENTS   10
 
#define SEARCH_INDEX_RELATED   11
 
#define SEARCH_INDEX_DEFINES   12
 
#define SEARCH_INDEX_GROUPS   13
 
#define SEARCH_INDEX_PAGES   14
 
#define NUM_SEARCH_INDICES   15
 

Functions

void initSearchIndexer ()
 
void finializeSearchIndexer ()
 
void createJavascriptSearchIndex ()
 
void writeJavascriptSearchIndex ()
 
const SearchIndexInfogetSearchIndices ()
 

Macro Definition Documentation

#define NUM_SEARCH_INDICES   15
#define SEARCH_INDEX_ALL   0

Definition at line 115 of file searchindex.h.

Referenced by addMemberToSearchIndex(), and createJavascriptSearchIndex().

#define SEARCH_INDEX_CLASSES   1

Definition at line 116 of file searchindex.h.

Referenced by createJavascriptSearchIndex().

#define SEARCH_INDEX_DEFINES   12

Definition at line 127 of file searchindex.h.

Referenced by addMemberToSearchIndex(), and createJavascriptSearchIndex().

#define SEARCH_INDEX_ENUMS   7

Definition at line 122 of file searchindex.h.

Referenced by addMemberToSearchIndex(), and createJavascriptSearchIndex().

#define SEARCH_INDEX_ENUMVALUES   8

Definition at line 123 of file searchindex.h.

Referenced by addMemberToSearchIndex(), and createJavascriptSearchIndex().

#define SEARCH_INDEX_EVENTS   10

Definition at line 125 of file searchindex.h.

Referenced by addMemberToSearchIndex(), and createJavascriptSearchIndex().

#define SEARCH_INDEX_FILES   3

Definition at line 118 of file searchindex.h.

Referenced by createJavascriptSearchIndex().

#define SEARCH_INDEX_FUNCTIONS   4

Definition at line 119 of file searchindex.h.

Referenced by addMemberToSearchIndex(), and createJavascriptSearchIndex().

#define SEARCH_INDEX_GROUPS   13

Definition at line 128 of file searchindex.h.

Referenced by createJavascriptSearchIndex().

#define SEARCH_INDEX_NAMESPACES   2

Definition at line 117 of file searchindex.h.

Referenced by createJavascriptSearchIndex().

#define SEARCH_INDEX_PAGES   14

Definition at line 129 of file searchindex.h.

Referenced by createJavascriptSearchIndex().

#define SEARCH_INDEX_PROPERTIES   9

Definition at line 124 of file searchindex.h.

Referenced by addMemberToSearchIndex(), and createJavascriptSearchIndex().

#define SEARCH_INDEX_RELATED   11

Definition at line 126 of file searchindex.h.

Referenced by addMemberToSearchIndex(), and createJavascriptSearchIndex().

#define SEARCH_INDEX_TYPEDEFS   6

Definition at line 121 of file searchindex.h.

Referenced by addMemberToSearchIndex(), and createJavascriptSearchIndex().

#define SEARCH_INDEX_VARIABLES   5

Definition at line 120 of file searchindex.h.

Referenced by addMemberToSearchIndex(), and createJavascriptSearchIndex().

Function Documentation

void createJavascriptSearchIndex ( )

Definition at line 718 of file searchindex.cpp.

References addMemberToSearchIndex(), LetterToIndexMap< T >::append(), Doxygen::classSDict, Doxygen::functionNameSDict, getUtf8CodeToLower(), Doxygen::groupSDict, GroupDef::groupTitle(), Doxygen::inputNameList, isId(), PageDef::isLinkable(), GroupDef::isLinkable(), NamespaceDef::isLinkable(), FileDef::isLinkable(), ClassDef::isLinkable(), SDict< ClassDef >::Iterator, SDict< NamespaceDef >::Iterator, SDict< MemberName >::Iterator, SDict< GroupDef >::Iterator, SDict< PageDef >::Iterator, Definition::localName(), Doxygen::mainPage, Doxygen::memberNameSDict, FileDef::name(), Definition::name(), SearchIndexInfo::name, Doxygen::namespaceSDict, NUM_SEARCH_INDICES, Doxygen::pageSDict, SEARCH_INDEX_ALL, SEARCH_INDEX_CLASSES, SEARCH_INDEX_DEFINES, SEARCH_INDEX_ENUMS, SEARCH_INDEX_ENUMVALUES, SEARCH_INDEX_EVENTS, SEARCH_INDEX_FILES, SEARCH_INDEX_FUNCTIONS, SEARCH_INDEX_GROUPS, SEARCH_INDEX_NAMESPACES, SEARCH_INDEX_PAGES, SEARCH_INDEX_PROPERTIES, SEARCH_INDEX_RELATED, SEARCH_INDEX_TYPEDEFS, SEARCH_INDEX_VARIABLES, SDict< T >::sort(), SearchIndexInfo::symbolList, SearchIndexInfo::text, theTranslator, PageDef::title(), Translator::trAll(), Translator::trClasses(), Translator::trDefines(), Translator::trEnumerations(), Translator::trEnumerationValues(), Translator::trEvents(), Translator::trFile(), Translator::trFriends(), Translator::trFunctions(), Translator::trGroup(), Translator::trNamespace(), Translator::trPage(), Translator::trProperties(), Translator::trTypedefs(), and Translator::trVariables().

Referenced by generateOutput().

{
// set index names
// set index texts
// add symbols to letter -> symbol list map
// index classes
ClassDef *cd;
for (;(cd=cli.current());++cli)
{
uint letter = getUtf8CodeToLower(cd->localName(),0);
if (cd->isLinkable() && isId(letter))
{
}
}
// index namespaces
for (;(nd=nli.current());++nli)
{
uint letter = getUtf8CodeToLower(nd->name(),0);
if (nd->isLinkable() && isId(letter))
{
}
}
// index files
FileName *fn;
for (;(fn=fnli.current());++fnli)
{
FileNameIterator fni(*fn);
FileDef *fd;
for (;(fd=fni.current());++fni)
{
uint letter = getUtf8CodeToLower(fd->name(),0);
if (fd->isLinkable() && isId(letter))
{
}
}
}
// index class members
{
// for each member name
for (mnli.toFirst();(mn=mnli.current());++mnli)
{
MemberDef *md;
// for each member definition
for (mni.toFirst();(md=mni.current());++mni)
{
}
}
}
// index file/namespace members
{
// for each member name
for (fnli.toFirst();(mn=fnli.current());++fnli)
{
MemberDef *md;
// for each member definition
for (mni.toFirst();(md=mni.current());++mni)
{
}
}
}
// index groups
GroupDef *gd;
for (gli.toFirst();(gd=gli.current());++gli)
{
if (gd->isLinkable())
{
QCString title = gd->groupTitle();
if (!title.isEmpty()) // TODO: able searching for all word in the title
{
uchar charCode = title.at(0);
uint letter = charCode<128 ? tolower(charCode) : charCode;
if (isId(letter))
{
}
}
}
}
// index pages
PageDef *pd=0;
for (pdi.toFirst();(pd=pdi.current());++pdi)
{
if (pd->isLinkable())
{
QCString title = pd->title();
if (!title.isEmpty())
{
uchar charCode = title.at(0);
uint letter = charCode<128 ? tolower(charCode) : charCode;
if (isId(letter))
{
}
}
}
}
{
QCString title = Doxygen::mainPage->title();
if (!title.isEmpty())
{
uchar charCode = title.at(0);
uint letter = charCode<128 ? tolower(charCode) : charCode;
if (isId(letter))
{
}
}
}
// sort all lists
int i;
for (i=0;i<NUM_SEARCH_INDICES;i++)
{
for (it.toFirst();(sl=it.current());++it)
{
sl->sort();
}
}
}
void finializeSearchIndexer ( )

Cleanup the search indexer

Definition at line 1320 of file searchindex.cpp.

References Doxygen::searchIndex.

Referenced by generateOutput().

const SearchIndexInfo* getSearchIndices ( )

Definition at line 1247 of file searchindex.cpp.

References g_searchIndexInfo.

Referenced by SearchIndicesContext::Private::Private().

{
}
void initSearchIndexer ( )

Initialize the search indexer

Definition at line 1298 of file searchindex.cpp.

References Config_getBool, and Doxygen::searchIndex.

Referenced by generateOutput().

{
static bool searchEngine = Config_getBool(SEARCHENGINE);
static bool serverBasedSearch = Config_getBool(SERVER_BASED_SEARCH);
static bool externalSearch = Config_getBool(EXTERNAL_SEARCH);
if (searchEngine && serverBasedSearch)
{
if (externalSearch) // external tools produce search index and engine
{
}
else // doxygen produces search index and engine
{
}
}
else // no search engine or pure javascript based search function
{
}
}
void writeJavascriptSearchIndex ( )

Definition at line 903 of file searchindex.cpp.

References IndexList::addStyleSheetFile(), Definition::anchor(), MemberDef::argsString(), Config_getBool, Config_getString, convertToXML(), ResourceMgr::copyResource(), DefinitionIntf::definitionType(), endl(), err(), externalRef(), Definition::getBodyDef(), MemberDef::getClassDef(), MemberDef::getFileDef(), Definition::getLanguage(), getLanguageSpecificSeparator(), MemberDef::getNamespaceDef(), Definition::getOuterScope(), Definition::getOutputFileBase(), Definition::getReference(), Doxygen::globalScope, Doxygen::htmlFileExtension, SearchDefinitionList::id(), Doxygen::indexList, ResourceMgr::instance(), MemberDef::isFunction(), MemberDef::isSlot(), SearchIndexList::letter(), Definition::localName(), Definition::name(), SearchDefinitionList::name(), SearchIndexInfo::name, NUM_SEARCH_INDICES, Definition::qualifiedName(), theTranslator, Translator::trGlobalNamespace(), Translator::trLoading(), Translator::trNoMatches(), Translator::trSearching(), DefinitionIntf::TypeClass, DefinitionIntf::TypeMember, DefinitionIntf::TypeNamespace, and versionString.

Referenced by generateOutput().

{
int i;
// write index files
QCString searchDirName = Config_getString(HTML_OUTPUT)+"/search";
for (i=0;i<NUM_SEARCH_INDICES;i++) // for each index
{
int p=0;
for (it.toFirst();(sl=it.current());++it,++p) // for each letter
{
QCString baseName;
baseName.sprintf("%s_%x",g_searchIndexInfo[i].name.data(),p);
QCString fileName = searchDirName + "/"+baseName+".html";
QCString dataFileName = searchDirName + "/"+baseName+".js";
QFile outFile(fileName);
QFile dataOutFile(dataFileName);
if (outFile.open(IO_WriteOnly) && dataOutFile.open(IO_WriteOnly))
{
{
FTextStream t(&outFile);
t << "<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\""
" \"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">" << endl;
t << "<html><head><title></title>" << endl;
t << "<meta http-equiv=\"Content-Type\" content=\"text/xhtml;charset=UTF-8\"/>" << endl;
t << "<meta name=\"generator\" content=\"Doxygen " << versionString << "\"/>" << endl;
t << "<link rel=\"stylesheet\" type=\"text/css\" href=\"search.css\"/>" << endl;
t << "<script type=\"text/javascript\" src=\"" << baseName << ".js\"></script>" << endl;
t << "<script type=\"text/javascript\" src=\"search.js\"></script>" << endl;
t << "</head>" << endl;
t << "<body class=\"SRPage\">" << endl;
t << "<div id=\"SRIndex\">" << endl;
t << "<div class=\"SRStatus\" id=\"Loading\">" << theTranslator->trLoading() << "</div>" << endl;
t << "<div id=\"SRResults\"></div>" << endl; // here the results will be inserted
t << "<script type=\"text/javascript\"><!--" << endl;
t << "createResults();" << endl; // this function will insert the results
t << "--></script>" << endl;
t << "<div class=\"SRStatus\" id=\"Searching\">"
<< theTranslator->trSearching() << "</div>" << endl;
t << "<div class=\"SRStatus\" id=\"NoMatches\">"
<< theTranslator->trNoMatches() << "</div>" << endl;
t << "<script type=\"text/javascript\"><!--" << endl;
t << "document.getElementById(\"Loading\").style.display=\"none\";" << endl;
t << "document.getElementById(\"NoMatches\").style.display=\"none\";" << endl;
t << "var searchResults = new SearchResults(\"searchResults\");" << endl;
t << "searchResults.Search();" << endl;
t << "--></script>" << endl;
t << "</div>" << endl; // SRIndex
t << "</body>" << endl;
t << "</html>" << endl;
}
FTextStream ti(&dataOutFile);
ti << "var searchData=" << endl;
// format
// searchData[] = array of items
// searchData[x][0] = id
// searchData[x][1] = [ name + child1 + child2 + .. ]
// searchData[x][1][0] = name as shown
// searchData[x][1][y+1] = info for child y
// searchData[x][1][y+1][0] = url
// searchData[x][1][y+1][1] = 1 => target="_parent"
// searchData[x][1][y+1][2] = scope
ti << "[" << endl;
bool firstEntry=TRUE;
int itemCount=0;
for (li.toFirst();(dl=li.current());++li)
{
Definition *d = dl->getFirst();
if (!firstEntry)
{
ti << "," << endl;
}
firstEntry=FALSE;
ti << " ['" << dl->id() << "',['" << convertToXML(dl->name()) << "',[";
if (dl->count()==1) // item with a unique name
{
MemberDef *md = 0;
bool isMemberDef = d->definitionType()==Definition::TypeMember;
if (isMemberDef) md = (MemberDef*)d;
QCString anchor = d->anchor();
ti << "'" << externalRef("../",d->getReference(),TRUE)
if (!anchor.isEmpty())
{
ti << "#" << anchor;
}
ti << "',";
static bool extLinksInWindow = Config_getBool(EXT_LINKS_IN_WINDOW);
if (!extLinksInWindow || d->getReference().isEmpty())
{
ti << "1,";
}
else
{
ti << "0,";
}
{
ti << "'" << convertToXML(d->getOuterScope()->name()) << "'";
}
else if (md)
{
FileDef *fd = md->getBodyDef();
if (fd==0) fd = md->getFileDef();
if (fd)
{
ti << "'" << convertToXML(fd->localName()) << "'";
}
}
else
{
ti << "''";
}
ti << "]]";
}
else // multiple items with the same name
{
QListIterator<Definition> di(*dl);
bool overloadedFunction = FALSE;
Definition *prevScope = 0;
int childCount=0;
for (di.toFirst();(d=di.current());)
{
++di;
Definition *scope = d->getOuterScope();
Definition *next = di.current();
Definition *nextScope = 0;
MemberDef *md = 0;
bool isMemberDef = d->definitionType()==Definition::TypeMember;
if (isMemberDef) md = (MemberDef*)d;
if (next) nextScope = next->getOuterScope();
QCString anchor = d->anchor();
if (childCount>0)
{
ti << "],[";
}
ti << "'" << externalRef("../",d->getReference(),TRUE)
if (!anchor.isEmpty())
{
ti << "#" << anchor;
}
ti << "',";
static bool extLinksInWindow = Config_getBool(EXT_LINKS_IN_WINDOW);
if (!extLinksInWindow || d->getReference().isEmpty())
{
ti << "1,";
}
else
{
ti << "0,";
}
bool found=FALSE;
overloadedFunction = ((prevScope!=0 && scope==prevScope) ||
(scope && scope==nextScope)
) && md &&
(md->isFunction() || md->isSlot());
QCString prefix;
if (md) prefix=convertToXML(md->localName());
if (overloadedFunction) // overloaded member function
{
prefix+=convertToXML(md->argsString());
// show argument list to disambiguate overloaded functions
}
else if (md) // unique member function
{
prefix+="()"; // only to show it is a function
}
QCString name;
{
name = convertToXML(((ClassDef*)d)->displayName());
found = TRUE;
}
{
name = convertToXML(((NamespaceDef*)d)->displayName());
found = TRUE;
}
else if (scope==0 || scope==Doxygen::globalScope) // in global scope
{
if (md)
{
FileDef *fd = md->getBodyDef();
if (fd==0) fd = md->getFileDef();
if (fd)
{
if (!prefix.isEmpty()) prefix+=":&#160;";
name = prefix + convertToXML(fd->localName());
found = TRUE;
}
}
}
else if (md && (md->getClassDef() || md->getNamespaceDef()))
// member in class or namespace scope
{
SrcLangExt lang = md->getLanguage();
+ getLanguageSpecificSeparator(lang) + prefix;
found = TRUE;
}
else if (scope) // some thing else? -> show scope
{
name = prefix + convertToXML(scope->name());
found = TRUE;
}
if (!found) // fallback
{
name = prefix + "("+theTranslator->trGlobalNamespace()+")";
}
ti << "'" << name << "'";
prevScope = scope;
childCount++;
}
ti << "]]";
}
ti << "]";
itemCount++;
}
if (!firstEntry)
{
ti << endl;
}
ti << "];" << endl;
}
else
{
err("Failed to open file '%s' for writing...\n",fileName.data());
}
}
}
{
QFile f(searchDirName+"/searchdata.js");
if (f.open(IO_WriteOnly))
{
FTextStream t(&f);
t << "var indexSectionsWithContent =" << endl;
t << "{" << endl;
bool first=TRUE;
int j=0;
for (i=0;i<NUM_SEARCH_INDICES;i++)
{
if (g_searchIndexInfo[i].symbolList.count()>0)
{
if (!first) t << "," << endl;
t << " " << j << ": \"";
for (it.toFirst();(sl=it.current());++it) // for each letter
{
t << QString( QChar( sl->letter() ) ).utf8();
}
t << "\"";
first=FALSE;
j++;
}
}
if (!first) t << "\n";
t << "};" << endl << endl;
t << "var indexSectionNames =" << endl;
t << "{" << endl;
first=TRUE;
j=0;
for (i=0;i<NUM_SEARCH_INDICES;i++)
{
if (g_searchIndexInfo[i].symbolList.count()>0)
{
if (!first) t << "," << endl;
t << " " << j << ": \"" << g_searchIndexInfo[i].name << "\"";
first=FALSE;
j++;
}
}
if (!first) t << "\n";
t << "};" << endl << endl;
t << "var indexSectionLabels =" << endl;
t << "{" << endl;
first=TRUE;
j=0;
for (i=0;i<NUM_SEARCH_INDICES;i++)
{
if (g_searchIndexInfo[i].symbolList.count()>0)
{
if (!first) t << "," << endl;
t << " " << j << ": \"" << convertToXML(g_searchIndexInfo[i].text) << "\"";
first=FALSE;
j++;
}
}
if (!first) t << "\n";
t << "};" << endl << endl;
}
ResourceMgr::instance().copyResource("search.js",searchDirName);
}
{
QFile f(searchDirName+"/nomatches.html");
if (f.open(IO_WriteOnly))
{
FTextStream t(&f);
t << "<!DOCTYPE html PUBLIC \"-//W3C//DTD XHTML 1.0 Transitional//EN\" "
"\"http://www.w3.org/TR/xhtml1/DTD/xhtml1-transitional.dtd\">" << endl;
t << "<html><head><title></title>" << endl;
t << "<meta http-equiv=\"Content-Type\" content=\"text/xhtml;charset=UTF-8\"/>" << endl;
t << "<link rel=\"stylesheet\" type=\"text/css\" href=\"search.css\"/>" << endl;
t << "<script type=\"text/javascript\" src=\"search.js\"></script>" << endl;
t << "</head>" << endl;
t << "<body class=\"SRPage\">" << endl;
t << "<div id=\"SRIndex\">" << endl;
t << "<div class=\"SRStatus\" id=\"NoMatches\">"
<< theTranslator->trNoMatches() << "</div>" << endl;
t << "</div>" << endl;
t << "</body>" << endl;
t << "</html>" << endl;
}
}
Doxygen::indexList->addStyleSheetFile("search/search.js");
}