libs/flake

KoPathControlPointMoveCommand.cpp

Go to the documentation of this file.
00001 /* This file is part of the KDE project
00002  * Copyright (C) 2006 Jan Hambrecht <jaham@gmx.net>
00003  * Copyright (C) 2006,2007 Thorsten Zachmann <zachmann@kde.org>
00004  *
00005  * This library is free software; you can redistribute it and/or
00006  * modify it under the terms of the GNU Library General Public
00007  * License as published by the Free Software Foundation; either
00008  * version 2 of the License, or (at your option) any later version.
00009  *
00010  * This library is distributed in the hope that it will be useful,
00011  * but WITHOUT ANY WARRANTY; without even the implied warranty of
00012  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
00013  * Library General Public License for more details.
00014  *
00015  * You should have received a copy of the GNU Library General Public License
00016  * along with this library; see the file COPYING.LIB.  If not, write to
00017  * the Free Software Foundation, Inc., 51 Franklin Street, Fifth Floor,
00018  * Boston, MA 02110-1301, USA.
00019  */
00020 
00021 #include "KoPathControlPointMoveCommand.h"
00022 #include <klocale.h>
00023 #include <math.h>
00024 
00025 KoPathControlPointMoveCommand::KoPathControlPointMoveCommand(
00026     const KoPathPointData &pointData,
00027     const QPointF &offset,
00028     KoPathPoint::KoPointType pointType,
00029     QUndoCommand *parent)
00030         : QUndoCommand(parent)
00031         , m_pointData(pointData)
00032         , m_pointType(pointType)
00033 {
00034     KoPathShape * pathShape = m_pointData.pathShape;
00035     KoPathPoint * point = pathShape->pointByIndex(m_pointData.pointIndex);
00036     if (point) {
00037         m_offset = point->parent()->documentToShape(offset) - point->parent()->documentToShape(QPointF(0, 0));
00038     }
00039 
00040     setText(i18n("Move control point"));
00041 }
00042 
00043 void KoPathControlPointMoveCommand::redo()
00044 {
00045     QUndoCommand::redo();
00046     KoPathShape * pathShape = m_pointData.pathShape;
00047     KoPathPoint * point = pathShape->pointByIndex(m_pointData.pointIndex);
00048     if (point) {
00049         pathShape->update();
00050 
00051         if (m_pointType == KoPathPoint::ControlPoint1) {
00052             point->setControlPoint1(point->controlPoint1() + m_offset);
00053             if (point->properties() & KoPathPoint::IsSymmetric) {
00054                 // set the other control point so that it lies on the line between the moved
00055                 // control point and the point, with the same distance to the point as the moved point
00056                 point->setControlPoint2(2.0 * point->point() - point->controlPoint1());
00057             } else if (point->properties() & KoPathPoint::IsSmooth) {
00058                 // move the other control point so that it lies on the line through point and control point
00059                 // keeping its distance to the point
00060                 QPointF direction = point->point() - point->controlPoint1();
00061                 direction /= sqrt(direction.x() * direction.x() + direction.y() * direction.y());
00062                 QPointF distance = point->point() - point->controlPoint2();
00063                 qreal length = sqrt(distance.x() * distance.x() + distance.y() * distance.y());
00064                 point->setControlPoint2(point->point() + length * direction);
00065             }
00066         } else if (m_pointType == KoPathPoint::ControlPoint2) {
00067             point->setControlPoint2(point->controlPoint2() + m_offset);
00068             if (point->properties() & KoPathPoint::IsSymmetric) {
00069                 // set the other control point so that it lies on the line between the moved
00070                 // control point and the point, with the same distance to the point as the moved point
00071                 point->setControlPoint1(2.0 * point->point() - point->controlPoint2());
00072             } else if (point->properties() & KoPathPoint::IsSmooth) {
00073                 // move the other control point so that it lies on the line through point and control point
00074                 // keeping its distance to the point
00075                 QPointF direction = point->point() - point->controlPoint2();
00076                 direction /= sqrt(direction.x() * direction.x() + direction.y() * direction.y());
00077                 QPointF distance = point->point() - point->controlPoint1();
00078                 qreal length = sqrt(distance.x() * distance.x() + distance.y() * distance.y());
00079                 point->setControlPoint1(point->point() + length * direction);
00080             }
00081         }
00082 
00083         pathShape->normalize();
00084         pathShape->update();
00085     }
00086 }
00087 
00088 void KoPathControlPointMoveCommand::undo()
00089 {
00090     QUndoCommand::undo();
00091     m_offset *= -1.0;
00092     redo();
00093     m_offset *= -1.0;
00094 }
00095