summaryrefslogtreecommitdiffstats
path: root/filters/karbon/wmf/wmfexport.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'filters/karbon/wmf/wmfexport.cpp')
-rw-r--r--filters/karbon/wmf/wmfexport.cpp263
1 files changed, 263 insertions, 0 deletions
diff --git a/filters/karbon/wmf/wmfexport.cpp b/filters/karbon/wmf/wmfexport.cpp
new file mode 100644
index 000000000..de929ca88
--- /dev/null
+++ b/filters/karbon/wmf/wmfexport.cpp
@@ -0,0 +1,263 @@
+/* This file is part of the KDE project
+ * Copyright (c) 2003 thierry lorthiois (lorthioist@wanadoo.fr)
+ *
+ * This library is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Library General Public
+ * License version 2 as published by the Free Software Foundation.
+ *
+ * This library is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Library General Public License for more details.
+ *
+ * You should have received a copy of the GNU Library General Public License
+ * along with this library; see the file COPYING.LIB. If not, write to
+ * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
+ * Boston, MA 02110-1301, USA.
+*/
+
+#include <config.h>
+#include <tqdom.h>
+#include <tqcstring.h>
+#include <kdebug.h>
+#include <kgenericfactory.h>
+#include <KoFilterChain.h>
+#include <KoStore.h>
+#include <KoStoreDevice.h>
+#include "vdocument.h"
+#include "vcolor.h"
+#include "vcomposite.h"
+#include "vdashpattern.h"
+#include "vdocument.h"
+#include "vlayer.h"
+#include "vpath.h"
+#include "vsegment.h"
+#include "vfill.h"
+#include "vstroke.h"
+#include "vtext.h"
+#include "vflattencmd.h"
+
+#include "wmfexport.h"
+#include "kowmfwrite.h"
+
+/*
+TODO: bs.wmf stroke in red with MSword and in brown with Kword ??
+*/
+
+typedef KGenericFactory<WmfExport, KoFilter> WmfExportFactory;
+K_EXPORT_COMPONENT_FACTORY( libwmfexport, WmfExportFactory( "kofficefilters" ) )
+
+
+WmfExport::WmfExport( KoFilter *, const char *, const TQStringList&) :
+ KoFilter()
+{
+}
+
+WmfExport::~WmfExport()
+{
+}
+
+KoFilter::ConversionStatus WmfExport::convert( const TQCString& from, const TQCString& to )
+{
+ if( to != "image/x-wmf" || from != "application/x-karbon" ) {
+ return KoFilter::NotImplemented;
+ }
+
+ KoStoreDevice* storeIn = m_chain->storageFile( "root", KoStore::Read );
+
+ if( !storeIn ) {
+ return KoFilter::StupidError;
+ }
+
+ // open Placeable Wmf file
+ mWmf = new KoWmfWrite( m_chain->outputFile() );
+ if( !mWmf->begin() ) {
+ delete mWmf;
+ return KoFilter::WrongFormat;
+ }
+
+ TQDomDocument domIn;
+ domIn.setContent( storeIn );
+ TQDomElement docNode = domIn.documentElement();
+
+ // Load the document.
+ mDoc = new VDocument;
+ mDoc->load( docNode );
+
+ // Process the document.
+ mDoc->accept( *this );
+
+ mWmf->end();
+
+ delete mWmf;
+ delete mDoc;
+
+ return KoFilter::OK;
+}
+
+
+void WmfExport::visitVDocument( VDocument& document ) {
+ int width;
+ int height;
+
+ mDoc = &document;
+ mListPa.setAutoDelete( true );
+
+ // resolution
+ mDpi = 1000;
+ width = (int)(POINT_TO_INCH( document.width() ) * mDpi);
+ height = (int)(POINT_TO_INCH( document.height() ) * mDpi);
+
+ mWmf->setDefaultDpi( mDpi );
+ mWmf->setWindow( 0, 0, width, height );
+
+ if ( (document.width() != 0) && (document.height() != 0) ) {
+ mScaleX = (double)width / document.width();
+ mScaleY = (double)height / document.height();
+ }
+
+ // Export layers.
+ VVisitor::visitVDocument( document );
+
+}
+
+
+void WmfExport::visitVPath( VPath& composite ) {
+ TQPen pen;
+ TQBrush brush;
+
+ getPen( pen, composite.stroke() );
+ getBrush( brush, composite.fill() );
+
+ VVisitor::visitVPath( composite );
+
+ if ( mListPa.count() > 0 ) {
+ mWmf->setPen( pen );
+ if( (brush.style() == TQt::NoBrush)
+ && (mListPa.count() == 1) ) {
+ mWmf->drawPolyline( *mListPa.first() );
+ }
+ else {
+ mWmf->setBrush( brush );
+
+ if ( mListPa.count() == 1 ) {
+ mWmf->drawPolygon( *mListPa.first() );
+ }
+ else {
+ // combined path
+ mWmf->drawPolyPolygon( mListPa );
+ }
+ }
+ }
+ mListPa.clear();
+}
+
+
+// Export segment.
+void WmfExport::visitVSubpath( VSubpath& path ) {
+ VSubpath *newPath;
+ VSubpathIterator itr( path );
+ VFlattenCmd cmd( 0L, INCH_TO_POINT(0.3 / (double)mDpi) );
+ TQPointArray *pa = new TQPointArray( path.count() );
+ int nbrPoint=0; // number of points in the path
+
+ for( ; itr.current(); ++itr ) {
+ VSegment *segment= itr.current();
+ if (segment->isCurve()) {
+ newPath = new VSubpath( mDoc );
+
+ // newPath duplicate the list of curve
+ newPath->moveTo( itr.current()->prev()->knot() );
+ newPath->append( itr.current()->clone() );
+ while( itr.current()->next() ) {
+ if ( itr.current()->next()->isCurve() ) {
+ newPath->append( itr.current()->next()->clone() );
+ }
+ else {
+ break;
+ }
+ ++itr;
+ }
+
+ // flatten the curve
+ cmd.visit( *newPath );
+
+ // adjust the number of points
+ pa->resize( pa->size() + newPath->count() - 2 );
+
+ // Ommit the first segment and insert points
+ newPath->first();
+ while( newPath->next() ) {
+ pa->setPoint( nbrPoint++, coordX( newPath->current()->knot().x() ),
+ coordY( newPath->current()->knot().y() ) );
+ }
+ delete newPath;
+ } else if (segment->isLine()) {
+ pa->setPoint( nbrPoint++, coordX( itr.current()->knot().x() ),
+ coordY( itr.current()->knot().y() ) );
+ } else if (segment->isBegin()) {
+ // start a new polygon
+ pa->setPoint( nbrPoint++, coordX( itr.current()->knot().x() ),
+ coordY( itr.current()->knot().y() ) );
+ }
+ }
+
+ // adjust the number of points
+ if ( nbrPoint > 1 ) {
+ pa->resize( nbrPoint );
+ mListPa.append( pa );
+ }
+ else {
+ delete pa;
+ // TODO: check why we have empty path
+ kdDebug() << "WmfExport::visitVSubpath : Empty path ?" << endl;
+ }
+}
+
+
+void WmfExport::visitVText( VText& text ) {
+ // TODO: export text
+ visitVSubpath( text.basePath() );
+}
+
+
+void WmfExport::getBrush( TQBrush& brush, const VFill *fill ) {
+ if( (fill->type() == VFill::solid) || (fill->type() == VFill::grad)
+ || (fill->type() == VFill::patt) ) {
+ if ( fill->color().opacity() < 0.1 ) {
+ brush.setStyle( Qt::NoBrush );
+ }
+ else {
+ brush.setStyle( Qt::SolidPattern );
+ brush.setColor( fill->color() );
+ }
+ }
+ else {
+ brush.setStyle( Qt::NoBrush );
+ }
+}
+
+
+void WmfExport::getPen( TQPen& pen, const VStroke *stroke ) {
+ if( (stroke->type() == VStroke::solid) || (stroke->type() == VStroke::grad)
+ || (stroke->type() == VStroke::patt) ) {
+ // TODO : Dash pattern.
+
+ if ( stroke->lineCap() == VStroke::capRound ) {
+ pen.setCapStyle( Qt::RoundCap );
+ }
+ else {
+ pen.setCapStyle( Qt::SquareCap );
+ }
+ pen.setStyle( Qt::SolidLine );
+ pen.setColor( stroke->color() );
+ pen.setWidth( coordX( stroke->lineWidth() ) );
+ }
+ else {
+ pen.setStyle( Qt::NoPen );
+ }
+}
+
+
+#include <wmfexport.moc>
+