You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
183 lines
6.6 KiB
183 lines
6.6 KiB
15 years ago
|
/*************************************************************************
|
||
|
copyright : (C) 2003-2006 by Robby Stephenson
|
||
|
email : robby@periapsis.org
|
||
|
***************************************************************************/
|
||
|
|
||
|
/***************************************************************************
|
||
|
* *
|
||
|
* This program is free software; you can redistribute it and/or modify *
|
||
|
* it under the terms of version 2 of the GNU General Public License as *
|
||
|
* published by the Free Software Foundation; *
|
||
|
* *
|
||
|
***************************************************************************/
|
||
|
|
||
|
#include <config.h>
|
||
|
|
||
|
#include "bibtexmlexporter.h"
|
||
|
#include "bibtexhandler.h"
|
||
|
#include "../document.h"
|
||
|
#include "../collections/bibtexcollection.h"
|
||
|
#include "../latin1literal.h"
|
||
|
#include "../filehandler.h"
|
||
|
#include "tellico_xml.h"
|
||
|
#include "../stringset.h"
|
||
|
|
||
|
#include <klocale.h>
|
||
|
#include <kdebug.h>
|
||
|
|
||
|
#include <qvbox.h>
|
||
|
#include <qdom.h>
|
||
|
#include <qregexp.h>
|
||
|
#include <qtextcodec.h>
|
||
|
|
||
|
using Tellico::Export::BibtexmlExporter;
|
||
|
|
||
|
QString BibtexmlExporter::formatString() const {
|
||
|
return i18n("Bibtexml");
|
||
|
}
|
||
|
|
||
|
QString BibtexmlExporter::fileFilter() const {
|
||
|
return i18n("*.xml|Bibtexml Files (*.xml)") + QChar('\n') + i18n("*|All Files");
|
||
|
}
|
||
|
|
||
|
bool BibtexmlExporter::exec() {
|
||
|
Data::CollPtr c = collection();
|
||
|
if(!c || c->type() != Data::Collection::Bibtex) {
|
||
|
return false;
|
||
|
}
|
||
|
const Data::BibtexCollection* coll = static_cast<const Data::BibtexCollection*>(c.data());
|
||
|
|
||
|
// there are some special fields
|
||
|
// the entry-type specifies the entry type - book, inproceedings, whatever
|
||
|
QString typeField;
|
||
|
// the key specifies the cite-key
|
||
|
QString keyField;
|
||
|
|
||
|
const QString bibtex = QString::fromLatin1("bibtex");
|
||
|
// keep a list of all the 'ordinary' fields to iterate through later
|
||
|
Data::FieldVec fields;
|
||
|
Data::FieldVec vec = coll->fields();
|
||
|
for(Data::FieldVec::Iterator it = vec.begin(); it != vec.end(); ++it) {
|
||
|
QString bibtexField = it->property(bibtex);
|
||
|
if(bibtexField == Latin1Literal("entry-type")) {
|
||
|
typeField = it->name();
|
||
|
} else if(bibtexField == Latin1Literal("key")) {
|
||
|
keyField = it->name();
|
||
|
} else if(!bibtexField.isEmpty()) {
|
||
|
fields.append(it);
|
||
|
}
|
||
|
}
|
||
|
|
||
|
QDomImplementation impl;
|
||
|
QDomDocumentType doctype = impl.createDocumentType(QString::fromLatin1("file"),
|
||
|
QString::null,
|
||
|
XML::dtdBibtexml);
|
||
|
//default namespace
|
||
|
const QString& ns = XML::nsBibtexml;
|
||
|
|
||
|
QDomDocument dom = impl.createDocument(ns, QString::fromLatin1("file"), doctype);
|
||
|
|
||
|
// root element
|
||
|
QDomElement root = dom.documentElement();
|
||
|
|
||
|
QString encodeStr = QString::fromLatin1("version=\"1.0\" encoding=\"");
|
||
|
if(options() & Export::ExportUTF8) {
|
||
|
encodeStr += QString::fromLatin1("UTF-8");
|
||
|
} else {
|
||
|
encodeStr += QString::fromLatin1(QTextCodec::codecForLocale()->mimeName());
|
||
|
}
|
||
|
encodeStr += '"';
|
||
|
|
||
|
// createDocument creates a root node, insert the processing instruction before it
|
||
|
dom.insertBefore(dom.createProcessingInstruction(QString::fromLatin1("xml"), encodeStr), root);
|
||
|
QString comment = QString::fromLatin1("Generated by Tellico ") + QString::fromLatin1(VERSION);
|
||
|
dom.insertBefore(dom.createComment(comment), root);
|
||
|
|
||
|
Data::ConstFieldPtr field;
|
||
|
Data::FieldVec::ConstIterator fIt, end = fields.constEnd();
|
||
|
bool format = options() & Export::ExportFormatted;
|
||
|
|
||
|
StringSet usedKeys;
|
||
|
QString type, key, newKey, value, elemName, parElemName;
|
||
|
QDomElement btElem, entryElem, parentElem, fieldElem;
|
||
|
for(Data::EntryVec::ConstIterator entryIt = entries().begin(); entryIt != entries().end(); ++entryIt) {
|
||
|
key = entryIt->field(keyField);
|
||
|
if(key.isEmpty()) {
|
||
|
key = BibtexHandler::bibtexKey(entryIt.data());
|
||
|
}
|
||
|
QString newKey = key;
|
||
|
char c = 'a';
|
||
|
while(usedKeys.has(newKey)) {
|
||
|
// duplicate found!
|
||
|
newKey = key + c;
|
||
|
++c;
|
||
|
}
|
||
|
key = newKey;
|
||
|
usedKeys.add(key);
|
||
|
|
||
|
btElem = dom.createElement(QString::fromLatin1("entry"));
|
||
|
btElem.setAttribute(QString::fromLatin1("id"), key);
|
||
|
root.appendChild(btElem);
|
||
|
|
||
|
type = entryIt->field(typeField);
|
||
|
if(type.isEmpty()) {
|
||
|
kdWarning() << "BibtexmlExporter::exec() - the entry for '" << entryIt->title()
|
||
|
<< "' has no entry-type, skipping it!" << endl;
|
||
|
continue;
|
||
|
}
|
||
|
|
||
|
entryElem = dom.createElement(type);
|
||
|
btElem.appendChild(entryElem);
|
||
|
|
||
|
// now iterate over attributes
|
||
|
for(fIt = fields.constBegin(); fIt != end; ++fIt) {
|
||
|
field = fIt.data();
|
||
|
value = entryIt->field(field->name(), format);
|
||
|
if(value.isEmpty()) {
|
||
|
continue;
|
||
|
}
|
||
|
|
||
|
/* Bibtexml has special container elements for titles, authors, editors, and keywords
|
||
|
I'm going to ignore the titlelist element for right now. All authors are contained in
|
||
|
an authorlist element, editors in an editorlist element, and keywords are in a
|
||
|
keywords element, and themselves as a keyword. Also, Bibtexml can format names
|
||
|
similar to docbook, with first, middle, last, etc elements. I'm going to ignore that
|
||
|
for now, too.*/
|
||
|
elemName = field->property(bibtex);
|
||
|
// split text for author, editor, and keywords
|
||
|
if(elemName == Latin1Literal("author") ||
|
||
|
elemName == Latin1Literal("editor") ||
|
||
|
elemName == Latin1Literal("keywords")) {
|
||
|
if(elemName == Latin1Literal("author")) {
|
||
|
parElemName = QString::fromLatin1("authorlist");
|
||
|
} else if(elemName == Latin1Literal("editor")) {
|
||
|
parElemName = QString::fromLatin1("editorlist");
|
||
|
} else { // keywords
|
||
|
parElemName = QString::fromLatin1("keywords");
|
||
|
elemName = QString::fromLatin1("keyword");
|
||
|
}
|
||
|
|
||
|
parentElem = dom.createElement(parElemName);
|
||
|
const QStringList values = entryIt->fields(field->name(), false);
|
||
|
for(QStringList::ConstIterator it = values.begin(); it != values.end(); ++it) {
|
||
|
fieldElem = dom.createElement(elemName);
|
||
|
fieldElem.appendChild(dom.createTextNode(*it));
|
||
|
parentElem.appendChild(fieldElem);
|
||
|
}
|
||
|
if(parentElem.hasChildNodes()) {
|
||
|
entryElem.appendChild(parentElem);
|
||
|
}
|
||
|
} else {
|
||
|
fieldElem = dom.createElement(elemName);
|
||
|
fieldElem.appendChild(dom.createTextNode(value));
|
||
|
entryElem.appendChild(fieldElem);
|
||
|
}
|
||
|
}
|
||
|
}
|
||
|
|
||
|
return FileHandler::writeTextURL(url(), dom.toString(),
|
||
|
options() & ExportUTF8, options() & Export::ExportForce);
|
||
|
}
|
||
|
|
||
|
#include "bibtexmlexporter.moc"
|