00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020 #include <config.h>
00021
00022 #ifdef HAVE_UNISTD_H
00023 #include <unistd.h>
00024 #endif
00025
00026 #include <hancomwordimport.h>
00027 #include <hancomwordimport.moc>
00028
00029 #include <qbuffer.h>
00030 #include <qcstring.h>
00031 #include <qfile.h>
00032 #include <qstring.h>
00033 #include <qstringlist.h>
00034 #include <qtextstream.h>
00035
00036 #include <kdebug.h>
00037 #include <KoFilterChain.h>
00038 #include <KoGlobal.h>
00039 #include <KoUnit.h>
00040 #include <kgenericfactory.h>
00041
00042 #include <KoXmlWriter.h>
00043
00044 #include <iostream>
00045 #include "pole.h"
00046
00047 typedef KGenericFactory<HancomWordImport, KoFilter> HancomWordImportFactory;
00048 K_EXPORT_COMPONENT_FACTORY( libhancomwordimport, HancomWordImportFactory( "kofficefilters" ) )
00049
00050 class HancomWordImport::Private
00051 {
00052 public:
00053 QString inputFile;
00054 QString outputFile;
00055
00056 QStringList paragraphs;
00057
00058 QByteArray createStyles();
00059 QByteArray createContent();
00060 QByteArray createManifest();
00061 };
00062
00063 HancomWordImport::HancomWordImport ( QObject*, const char*, const QStringList& )
00064 : KoFilter()
00065 {
00066 d = new Private;
00067 }
00068
00069 HancomWordImport::~HancomWordImport()
00070 {
00071 delete d;
00072 }
00073
00074 namespace
00075 {
00076
00077 static inline unsigned long readU16( const void* p )
00078 {
00079 const unsigned char* ptr = (const unsigned char*) p;
00080 return ptr[0]+(ptr[1]<<8);
00081 }
00082
00083 }
00084
00085 KoFilter::ConversionStatus HancomWordImport::convert( const QCString& from, const QCString& to )
00086 {
00087 if ( from != "application/x-hancomword" )
00088 return KoFilter::NotImplemented;
00089
00090 if ( to != "application/vnd.oasis.opendocument.text" )
00091 return KoFilter::NotImplemented;
00092
00093 d->inputFile = m_chain->inputFile();
00094 d->outputFile = m_chain->outputFile();
00095 d->paragraphs.clear();
00096
00097 POLE::Storage storage( d->inputFile.latin1() );
00098 if( !storage.open() )
00099 return KoFilter::WrongFormat;
00100
00101 POLE::Stream* stream;
00102 stream = new POLE::Stream( &storage, "/PrvText" );
00103 if( stream->fail() || (stream->size() == 0) )
00104 {
00105 delete stream;
00106 return KoFilter::WrongFormat;
00107 }
00108
00109 int len = stream->size() / 2;
00110 QString plaindoc;
00111 plaindoc.reserve( len );
00112
00113 unsigned char* buf = new unsigned char [stream->size()];
00114 stream->read( buf, stream->size());
00115 for(int i = 0; i < len; i++ )
00116 plaindoc.append( QChar((int)readU16(buf + i*2) ) );
00117 delete[] buf;
00118 delete stream;
00119
00120
00121 d->paragraphs = QStringList::split( "\n", plaindoc, true );
00122
00123
00124 KoStore* storeout;
00125 storeout = KoStore::createStore( d->outputFile, KoStore::Write,
00126 "application/vnd.oasis.opendocument.text", KoStore::Zip );
00127
00128 if ( !storeout )
00129 {
00130 kdWarning() << "Couldn't open the requested file." << endl;
00131 return KoFilter::FileNotFound;
00132 }
00133
00134 if ( !storeout->open( "styles.xml" ) )
00135 {
00136 kdWarning() << "Couldn't open the file 'styles.xml'." << endl;
00137 return KoFilter::CreationError;
00138 }
00139 storeout->write( d->createStyles() );
00140 storeout->close();
00141
00142 if ( !storeout->open( "content.xml" ) )
00143 {
00144 kdWarning() << "Couldn't open the file 'content.xml'." << endl;
00145 return KoFilter::CreationError;
00146 }
00147 storeout->write( d->createContent() );
00148 storeout->close();
00149
00150
00151 storeout->enterDirectory( "META-INF" );
00152 if ( !storeout->open( "manifest.xml" ) )
00153 {
00154 kdWarning() << "Couldn't open the file 'META-INF/manifest.xml'." << endl;
00155 return KoFilter::CreationError;
00156 }
00157 storeout->write( d->createManifest() );
00158 storeout->close();
00159
00160
00161 d->inputFile = QString::null;
00162 d->outputFile = QString::null;
00163 delete storeout;
00164
00165 return KoFilter::OK;
00166 }
00167
00168 QByteArray HancomWordImport::Private::createContent()
00169 {
00170 KoXmlWriter* contentWriter;
00171 QByteArray contentData;
00172 QBuffer contentBuffer( contentData );
00173
00174 contentBuffer.open( IO_WriteOnly );
00175 contentWriter = new KoXmlWriter( &contentBuffer );
00176
00177 contentWriter->startDocument( "office:document-content" );
00178 contentWriter->startElement( "office:document-content" );
00179
00180 contentWriter->addAttribute( "xmlns:office", "urn:oasis:names:tc:opendocument:xmlns:office:1.0" );
00181 contentWriter->addAttribute( "xmlns:style", "urn:oasis:names:tc:opendocument:xmlns:style:1.0" );
00182 contentWriter->addAttribute( "xmlns:text", "urn:oasis:names:tc:opendocument:xmlns:text:1.0" );
00183 contentWriter->addAttribute( "xmlns:table", "urn:oasis:names:tc:opendocument:xmlns:table:1.0" );
00184 contentWriter->addAttribute( "xmlns:draw", "urn:oasis:names:tc:opendocument:xmlns:drawing:1.0" );
00185 contentWriter->addAttribute( "xmlns:fo", "urn:oasis:names:tc:opendocument:xmlns:xsl-fo-compatible:1.0" );
00186 contentWriter->addAttribute( "xmlns:svg","urn:oasis:names:tc:opendocument:xmlns:svg-compatible:1.0" );
00187 contentWriter->addAttribute( "office:version","1.0" );
00188
00189 contentWriter->startElement( "office:automatic-styles" );
00190 contentWriter->endElement();
00191
00192
00193 contentWriter->startElement( "office:body" );
00194
00195 contentWriter->startElement( "office:text" );
00196
00197 contentWriter->startElement( "text:sequence-decls" );
00198 contentWriter->endElement();
00199
00200 for( uint i = 0; i < paragraphs.count(); i++ )
00201 {
00202 QString text = paragraphs[i];
00203 text.replace( '\r', ' ' );
00204 contentWriter->startElement( "text:p" );
00205 contentWriter->addTextNode( text );
00206 contentWriter->endElement();
00207 }
00208
00209 contentWriter->endElement();
00210 contentWriter->endElement();
00211
00212 contentWriter->endElement();
00213 contentWriter->endDocument();
00214
00215 delete contentWriter;
00216
00217 return contentData;
00218 }
00219
00220 QByteArray HancomWordImport::Private::createStyles()
00221 {
00222 KoXmlWriter* stylesWriter;
00223 QByteArray stylesData;
00224 QBuffer stylesBuffer( stylesData );
00225
00226 stylesBuffer.open( IO_WriteOnly );
00227 stylesWriter = new KoXmlWriter( &stylesBuffer );
00228
00229 stylesWriter->startDocument( "office:document-styles" );
00230 stylesWriter->startElement( "office:document-styles" );
00231 stylesWriter->addAttribute( "xmlns:office", "urn:oasis:names:tc:opendocument:xmlns:office:1.0" );
00232 stylesWriter->addAttribute( "xmlns:style", "urn:oasis:names:tc:opendocument:xmlns:style:1.0" );
00233 stylesWriter->addAttribute( "xmlns:text", "urn:oasis:names:tc:opendocument:xmlns:text:1.0" );
00234 stylesWriter->addAttribute( "xmlns:table", "urn:oasis:names:tc:opendocument:xmlns:table:1.0" );
00235 stylesWriter->addAttribute( "xmlns:draw", "urn:oasis:names:tc:opendocument:xmlns:drawing:1.0" );
00236 stylesWriter->addAttribute( "xmlns:fo", "urn:oasis:names:tc:opendocument:xmlns:xsl-fo-compatible:1.0" );
00237 stylesWriter->addAttribute( "xmlns:svg","urn:oasis:names:tc:opendocument:xmlns:svg-compatible:1.0" );
00238 stylesWriter->addAttribute( "office:version","1.0" );
00239 stylesWriter->startElement( "office:styles" );
00240
00241
00242 stylesWriter->startElement( "style:default-style" );
00243 stylesWriter->addAttribute( "style:family", "paragraph" );
00244
00245 stylesWriter->startElement( "style:paragraph-properties" );
00246 stylesWriter->addAttribute( "fo:hyphenation-ladder-count", "no-limit" );
00247 stylesWriter->addAttribute( "style:text-autospace", "ideograph-alpha" );
00248 stylesWriter->addAttribute( "style:punctuation-wrap", "hanging" );
00249 stylesWriter->addAttribute( "style:line-break", "strict" );
00250 stylesWriter->addAttribute( "tyle:tab-stop-distance", "0.5in" );
00251 stylesWriter->addAttribute( "style:writing-mode", "page" );
00252 stylesWriter->endElement();
00253
00254 stylesWriter->startElement( "style:text-properties" );
00255 stylesWriter->addAttribute( "style:use-window-font-color", "true" );
00256 stylesWriter->addAttribute( "style:font-name", "Sans Serif" );
00257 stylesWriter->addAttribute( "fo:font-size", "12pt" );
00258 stylesWriter->addAttribute( "fo:hyphenate", "false" );
00259 stylesWriter->endElement();
00260
00261 stylesWriter->endElement();
00262 stylesWriter->endElement();
00263
00264
00265 stylesWriter->startElement( "office:automatic-styles" );
00266 stylesWriter->endElement();
00267
00268 stylesWriter->endElement();
00269 stylesWriter->endDocument();
00270
00271 delete stylesWriter;
00272
00273 return stylesData;
00274 }
00275
00276 QByteArray HancomWordImport::Private::createManifest()
00277 {
00278 KoXmlWriter* manifestWriter;
00279 QByteArray manifestData;
00280 QBuffer manifestBuffer( manifestData );
00281
00282 manifestBuffer.open( IO_WriteOnly );
00283 manifestWriter = new KoXmlWriter( &manifestBuffer );
00284
00285 manifestWriter->startDocument( "manifest:manifest" );
00286 manifestWriter->startElement( "manifest:manifest" );
00287 manifestWriter->addAttribute( "xmlns:manifest", "urn:oasis:names:tc:openoffice:xmlns:manifest:1.0" );
00288 manifestWriter->addManifestEntry( "/", "application/vnd.oasis.opendocument.text" );
00289 manifestWriter->addManifestEntry( "styles.xml", "text/xml" );
00290 manifestWriter->addManifestEntry( "content.xml", "text/xml" );
00291 manifestWriter->endElement();
00292 manifestWriter->endDocument();
00293 delete manifestWriter;
00294
00295 return manifestData;
00296 }