summaryrefslogtreecommitdiffstats
path: root/src/drawparts/dpline.cpp
diff options
context:
space:
mode:
Diffstat (limited to 'src/drawparts/dpline.cpp')
-rw-r--r--src/drawparts/dpline.cpp227
1 files changed, 227 insertions, 0 deletions
diff --git a/src/drawparts/dpline.cpp b/src/drawparts/dpline.cpp
new file mode 100644
index 0000000..59fa789
--- /dev/null
+++ b/src/drawparts/dpline.cpp
@@ -0,0 +1,227 @@
+/***************************************************************************
+ * Copyright (C) 2005 by David Saxton *
+ * david@bluehaze.org *
+ * *
+ * This program is free software; you can redistribute it and/or modify *
+ * it under the terms of the GNU General Public License as published by *
+ * the Free Software Foundation; either version 2 of the License, or *
+ * (at your option) any later version. *
+ ***************************************************************************/
+
+#include "dpline.h"
+#include "libraryitem.h"
+#include "resizeoverlay.h"
+#include "variant.h"
+
+#include <cmath>
+#include <kiconloader.h>
+#include <klocale.h>
+#include <qpainter.h>
+
+
+//BEGIN class DPLine
+Item* DPLine::construct( ItemDocument *itemDocument, bool newItem, const char *id )
+{
+ return new DPLine( itemDocument, newItem, id );
+}
+
+LibraryItem* DPLine::libraryItem()
+{
+ return new LibraryItem(
+ QString("dp/line"),
+ i18n("Line"),
+ i18n("Other"),
+ KGlobal::iconLoader()->loadIcon( "text", KIcon::Small ),
+ LibraryItem::lit_drawpart,
+ DPLine::construct );
+}
+
+DPLine::DPLine( ItemDocument *itemDocument, bool newItem, const char *id )
+ : DrawPart( itemDocument, newItem, id ? id : "line" )
+{
+ m_pLineOverlay = new LineOverlay(this);
+ m_name = i18n("Line");
+ m_desc = i18n("Select the line to position the end points");
+
+ createProperty( "line-color", Variant::Type::Color );
+ property("line-color")->setCaption( i18n("Line Color") );
+ property("line-color")->setValue(Qt::black);
+
+ createProperty( "line-width", Variant::Type::Int );
+ property("line-width")->setCaption( i18n("Line Width") );
+ property("line-width")->setMinValue(1);
+ property("line-width")->setMaxValue(1000);
+ property("line-width")->setValue(1);
+
+ createProperty( "line-style", Variant::Type::PenStyle );
+ property("line-style")->setCaption( i18n("Line Style") );
+ property("line-style")->setAdvanced(true);
+ setDataPenStyle( "line-style", Qt::SolidLine );
+
+ createProperty( "cap-style", Variant::Type::PenCapStyle );
+ property("cap-style")->setCaption( i18n("Cap Style") );
+ property("cap-style")->setAdvanced(true);
+ setDataPenCapStyle( "cap-style", Qt::FlatCap );
+}
+
+DPLine::~DPLine()
+{
+}
+
+void DPLine::setSelected( bool yes )
+{
+ if ( yes == isSelected() )
+ return;
+
+ DrawPart::setSelected(yes);
+ m_pLineOverlay->showResizeHandles(yes);
+}
+
+
+void DPLine::dataChanged()
+{
+ setPen( QPen( dataColor("line-color"),
+ unsigned( dataInt("line-width") ),
+ getDataPenStyle("line-style"),
+ getDataPenCapStyle("cap-style"),
+ Qt::MiterJoin ) );
+
+ postResize(); // in case the pen width has changed
+ update();
+}
+
+
+void DPLine::postResize()
+{
+ int x1 = offsetX();
+ int y1 = offsetY();
+ int x2 = x1+width();
+ int y2 = y1+height();
+
+ QPointArray p(4);
+ int pw = pen().width();
+ int dx = QABS(x1-x2);
+ int dy = QABS(y1-y2);
+ pw = pw*4/3+2; // approx pw*sqrt(2)
+ int px = x1<x2 ? -pw : pw ;
+ int py = y1<y2 ? -pw : pw ;
+ if ( dx && dy && (dx > dy ? (dx*2/dy <= 2) : (dy*2/dx <= 2)) ) {
+ // steep
+ if ( px == py ) {
+ p[0] = QPoint(x1 ,y1+py);
+ p[1] = QPoint(x2-px,y2 );
+ p[2] = QPoint(x2 ,y2-py);
+ p[3] = QPoint(x1+px,y1 );
+ } else {
+ p[0] = QPoint(x1+px,y1 );
+ p[1] = QPoint(x2 ,y2-py);
+ p[2] = QPoint(x2-px,y2 );
+ p[3] = QPoint(x1 ,y1+py);
+ }
+ } else if ( dx > dy ) {
+ // horizontal
+ p[0] = QPoint(x1+px,y1+py);
+ p[1] = QPoint(x2-px,y2+py);
+ p[2] = QPoint(x2-px,y2-py);
+ p[3] = QPoint(x1+px,y1-py);
+ } else {
+ // vertical
+ p[0] = QPoint(x1+px,y1+py);
+ p[1] = QPoint(x2+px,y2-py);
+ p[2] = QPoint(x2-px,y2-py);
+ p[3] = QPoint(x1-px,y1+py);
+ }
+ setItemPoints( p, false );
+}
+
+
+void DPLine::drawShape( QPainter & p )
+{
+ int x1 = int(x()+offsetX());
+ int y1 = int(y()+offsetY());
+ int x2 = x1+width();
+ int y2 = y1+height();
+
+ p.drawLine( x1, y1, x2, y2 );
+}
+//END class DPLine
+
+
+//BEGIN class DPArrow
+Item* DPArrow::construct( ItemDocument *itemDocument, bool newItem, const char *id )
+{
+ return new DPArrow( itemDocument, newItem, id );
+}
+
+LibraryItem* DPArrow::libraryItem()
+{
+ return new LibraryItem(
+ QString("dp/arrow"),
+ i18n("Arrow"),
+ i18n("Other"),
+ KGlobal::iconLoader()->loadIcon( "text", KIcon::Small ),
+ LibraryItem::lit_drawpart,
+ DPArrow::construct );
+}
+
+DPArrow::DPArrow( ItemDocument *itemDocument, bool newItem, const char *id )
+ : DPLine( itemDocument, newItem, id ? id : "arrow" )
+{
+ m_name = i18n("Arrow");
+
+ // We don't want to use the square cap style as it screws up drawing our arrow head
+ QStringList allowed = property("cap-style")->allowed();
+ allowed.remove( DrawPart::penCapStyleToName( Qt::SquareCap ) );
+ property("cap-style")->setAllowed(allowed);
+}
+
+DPArrow::~DPArrow()
+{
+}
+
+
+void DPArrow::drawShape( QPainter & p )
+{
+ int x1 = int(x()+offsetX());
+ int y1 = int(y()+offsetY());
+ int x2 = x1+width();
+ int y2 = y1+height();
+
+ p.drawLine( x1, y1, x2, y2 );
+
+ double dx = x2-x1;
+ double dy = y2-y1;
+
+ if ( dx == 0. && dy == 0. )
+ return;
+
+ double pi = 3.14159265358979323846264;
+ double arrow_angle = ( dx == 0 ? (dy>0?(pi/2.):(-pi/2.)) : std::atan(dy/dx) );
+ if ( dx < 0 )
+ arrow_angle += pi;
+
+ double head_angle = 0.6; // Angle of arrowhead
+ double head_length = 10.;
+
+ // Position of arrowhead
+ int x3 = int( x2 + head_length*std::cos( pi + arrow_angle - head_angle ) );
+ int y3 = int( y2 + head_length*std::sin( pi + arrow_angle - head_angle ) );
+ int x4 = int( x2 + head_length*std::cos( pi + arrow_angle + head_angle ) );
+ int y4 = int( y2 + head_length*std::sin( pi + arrow_angle + head_angle ) );
+
+ // Draw arrowhead
+ QPen pen = p.pen();
+ pen.setCapStyle( Qt::RoundCap );
+ p.setPen(pen);
+ p.setBrush(pen.color());
+ QPointArray pa(3);
+ pa[0] = QPoint( x2, y2 );
+ pa[1] = QPoint( x3, y3 );
+ pa[2] = QPoint( x4, y4 );
+ p.drawPolygon(pa);
+ p.drawPolyline(pa);
+// p.drawLine( x2, y2, x3, y3 );
+// p.drawLine( x2, y2, x4, y4 );
+}
+//END class DPLine
+