KDocTools
docbookl10nhelper.cpp
Go to the documentation of this file.
00001 /* This file is part of the KDE project 00002 Copyright (C) 2010 Luigi Toscano <luigi.toscano@tiscali.it> 00003 00004 This library is free software; you can redistribute it and/or 00005 modify it under the terms of the GNU Lesser General Public 00006 License as published by the Free Software Foundation; either 00007 version 2.1 of the License, or (at your option) version 3, or any 00008 later version accepted by the membership of KDE e.V. (or its 00009 successor approved by the membership of KDE e.V.), which shall 00010 act as a proxy defined in Section 6 of version 3 of the license. 00011 00012 This library is distributed in the hope that it will be useful, 00013 but WITHOUT ANY WARRANTY; without even the implied warranty of 00014 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU 00015 Lesser General Public License for more details. 00016 00017 You should have received a copy of the GNU Lesser General Public 00018 License along with this library. If not, see <http://www.gnu.org/licenses/>. 00019 */ 00020 00021 #include <QCoreApplication> 00022 #include <QDebug> 00023 #include <QDir> 00024 #include <QFile> 00025 #include <QIODevice> 00026 #include <QList> 00027 #include <QPair> 00028 #include <QRegExp> 00029 #include <QStringList> 00030 #include <QTextStream> 00031 00032 00033 class LangListType: public QList<QPair<QString,QString> > 00034 { 00035 public: 00036 int searchLang( QString el ) { 00037 00038 for ( int i = 0; i < size(); ++i ) { 00039 if ( at( i ).first == el ) 00040 return i; 00041 } 00042 return -1; 00043 } 00044 }; 00045 00046 int writeLangFile( const QString &fname, const QString &dtdPath, 00047 const LangListType &langMap ) { 00048 00049 QFile outFile( fname ); 00050 if ( ! outFile.open( QIODevice::WriteOnly ) ) { 00051 qCritical() << QString( "Could not write %1" ) 00052 .arg( outFile.fileName() ); 00053 return( 1 ); 00054 } 00055 00056 QTextStream outStream( &outFile ); 00057 outStream << "<?xml version='1.0'?>" << endl; 00058 outStream << QString( "<!DOCTYPE l:i18n SYSTEM \"%1\" [" ) 00059 .arg( dtdPath ) << endl; 00060 00061 LangListType::const_iterator i = langMap.constBegin(); 00062 while ( i != langMap.constEnd() ) { 00063 //qDebug() << (*i).first << ": " << (*i).second; 00064 outStream << QString( "<!ENTITY %1 SYSTEM \"%2\">" ) 00065 .arg( (*i).first ).arg( (*i).second ) << endl; 00066 ++i; 00067 } 00068 outStream << "]>" << endl; 00069 00070 if ( langMap.size() > 0 ) { 00071 outStream 00072 << "<l:i18n xmlns:l=\"http://docbook.sourceforge.net/xmlns/l10n/1.0\">" 00073 << endl; 00074 i = langMap.constBegin(); 00075 while ( i != langMap.constEnd() ) { 00076 outStream << QString( "&%1;" ) 00077 .arg( (*i).first ) << endl; 00078 ++i; 00079 } 00080 outStream << "</l:i18n>" << endl; 00081 } 00082 00083 outFile.close(); 00084 00085 return( 0 ); 00086 } 00087 00088 int writeLangFileNew( const QString &fname, const QString &dtdPath, 00089 const LangListType &langMap ) { 00090 00091 QFile outFile( fname ); 00092 if ( ! outFile.open( QIODevice::WriteOnly ) ) { 00093 qCritical() << QString( "Could not write %1" ) 00094 .arg( outFile.fileName() ); 00095 return( 1 ); 00096 } 00097 00098 QTextStream outStream( &outFile ); 00099 outStream << "<?xml version='1.0'?>" << endl; 00100 outStream << QString( "<!DOCTYPE l:i18n SYSTEM \"%1\">" ) 00101 .arg( dtdPath ) << endl; 00102 00103 if ( langMap.size() > 0 ) { 00104 outStream 00105 << "<l:i18n xmlns:l=\"http://docbook.sourceforge.net/xmlns/l10n/1.0\">" 00106 << endl; 00107 LangListType::const_iterator i = langMap.constBegin(); 00108 while ( i != langMap.constEnd() ) { 00109 outStream << QString( "<l:l10n language=\"%1\" href=\"%2\"/>" ) 00110 .arg( (*i).first ).arg( (*i).second ) << endl; 00111 ++i; 00112 } 00113 outStream << "</l:i18n>" << endl; 00114 } 00115 00116 outFile.close(); 00117 00118 return( 0 ); 00119 } 00120 00121 inline const QString addTrailingSlash( const QString &p ) { 00122 return p.endsWith( "/" ) ? p : p + "/"; 00123 } 00124 00125 int main( int argc, char **argv ) { 00126 QCoreApplication app( argc, argv ); 00127 00128 const QStringList arguments = app.arguments(); 00129 if ( arguments.count() != 4 ) { 00130 qCritical() << "wrong argument count"; 00131 return ( 1 ); 00132 } 00133 00134 const QString l10nDir = addTrailingSlash( arguments[1] ); 00135 const QString l10nCustomDir = addTrailingSlash( arguments[2] ); 00136 const QString destDir = addTrailingSlash( arguments[3] ); 00137 00138 QFile i18nFile( l10nDir + "common/l10n.xml" ); 00139 00140 if ( ! i18nFile.open( QIODevice::ReadOnly ) ) { 00141 qCritical() << i18nFile.fileName() << " not found"; 00142 return( 1 ); 00143 } 00144 00145 const QString all10nFName = destDir + "all-l10n.xml"; 00146 const QString customl10nFName = destDir + "kde-custom-l10n.xml"; 00147 00148 /* 00149 * for each language defined in the original l10n.xml, copy 00150 * it into all-l10n.xml and store it in a list; 00151 **/ 00152 QRegExp rxEntity, rxEntity2, rxDocType, rxDocType2; 00153 rxDocType.setPattern("^\\s*<!DOCTYPE\\s+l:i18n\\s+SYSTEM\\s+\"l10n\\.dtd\"\\s+\\[\\s*$"); 00154 rxDocType2.setPattern("^\\s*<!DOCTYPE\\s+l:i18n\\s+SYSTEM\\s+\"l10n\\.dtd\"\\s*>$"); 00155 rxEntity.setPattern("^\\s*<!ENTITY\\s+([^\\s]+)\\s+SYSTEM\\s+\"([^\\s]+)\">\\s*$"); 00156 rxEntity2.setPattern("^\\s*<l:l10n language=\"([^\\s]+)\"\\s+href=\"([^\\s]+)\"/>\\s*$"); 00157 QTextStream inStream( &i18nFile ); 00158 int parsingState = 0; 00159 00160 LangListType allLangs, customLangs; 00161 00162 bool foundRxEntity = false; 00163 bool foundRxEntity2 = false; 00164 while ( ! inStream.atEnd() ) { 00165 QString line = inStream.readLine(); 00166 00167 switch ( parsingState ) { 00168 case 0: 00169 if ( rxDocType.indexIn( line ) != -1 ) { 00170 parsingState = 1; 00171 //qDebug() << "DTD found"; 00172 } else if ( rxDocType2.indexIn( line ) != -1 ) { 00173 parsingState = 1; 00174 //qDebug() << "DTD found"; 00175 } 00176 break; 00177 case 1: 00178 QString langCode, langFile; 00179 if ( rxEntity.indexIn( line ) != -1 && !foundRxEntity2 ) { 00180 foundRxEntity = true; 00181 langCode = rxEntity.cap( 1 ); 00182 langFile = l10nDir + "common/" + rxEntity.cap( 2 ); 00183 allLangs += qMakePair( langCode, langFile ); 00184 //qDebug() << langCode << " - " << langFile; 00185 } else if ( rxEntity2.indexIn( line ) != -1 && !foundRxEntity ) { 00186 foundRxEntity2 = true; 00187 langCode = rxEntity2.cap( 1 ); 00188 langFile = l10nDir + "common/" + rxEntity2.cap( 2 ); 00189 allLangs += qMakePair( langCode, langFile ); 00190 //qDebug() << langCode << " - " << langFile; 00191 } 00192 break; 00193 } 00194 00195 } 00196 i18nFile.close(); 00197 00198 /* read the list of locally-available custom languages */ 00199 QDir outDir( l10nCustomDir ); 00200 00201 QStringList dirFileFilters; 00202 dirFileFilters << "*.xml"; 00203 QStringList customLangFiles = outDir.entryList( dirFileFilters, 00204 QDir::Files|QDir::NoSymLinks, QDir::Name ); 00205 /* the following two calls to removeOne should not be needed, as 00206 * the customization directory from the sources should not contain 00207 * those files 00208 */ 00209 customLangFiles.removeOne( "all-l10n.xml" ); 00210 customLangFiles.removeOne( "kde-custom-l10n.xml" ); 00211 //qDebug() << "customLangFiles:" << customLangFiles; 00212 00213 /* 00214 * for each custom language (from directory listing), if it is not 00215 * in the list of upstream languages, add it to all-l10n.xml, 00216 * otherwise add it to kde-custom-l10n.xml 00217 */ 00218 QStringList::const_iterator i = customLangFiles.constBegin(); 00219 while ( i != customLangFiles.constEnd() ) { 00220 QString langFile = (*i); 00221 /* remove trailing .xml */ 00222 QString langCode = langFile.left( langFile.length() - 4 ); 00223 00224 QPair<QString,QString> cl = qMakePair( langCode, langFile ); 00225 if ( ( allLangs.searchLang( langCode ) ) > 0 ) { 00226 /* custom language found in upstream list */ 00227 customLangs += cl; 00228 } else { 00229 /* custom language not found in upstream list */ 00230 allLangs += cl; 00231 } 00232 ++i; 00233 } 00234 00235 int res = 0; 00236 00237 if ( foundRxEntity ) { 00238 /* old style (docbook-xsl<=1.75) */ 00239 res = writeLangFile( all10nFName, l10nDir + "common/l10n.dtd", 00240 allLangs ); 00241 } else { 00242 res = writeLangFileNew( all10nFName, l10nDir + "common/l10n.dtd", 00243 allLangs ); 00244 } 00245 00246 return( res ); 00247 }
KDE 4.7 API Reference