Commit a3502e6a authored by Thomas Zander's avatar Thomas Zander

Further work to make the CreateShapesTool be useful and have a nice API.

It now is able to create shapes via the KoShapeFactory::createDefaultShape()
method all via the toolManager (so simple API for the app).

svn path=/trunk/koffice/; revision=550386
parent 808e3562
......@@ -2,7 +2,7 @@
#include "KoShape.h"
#include "KoShapeGroup.h"
#include "KoShapeContainer.h"
#include "KoShapeControllerInterface.h"
#include "KoShapeControllerBase.h"
#include <klocale.h>
......@@ -158,7 +158,7 @@ QString KoUngroupShapesCommand::name () const {
return i18n( "Ungroup shapes" );
}
KoShapeCreateCommand::KoShapeCreateCommand( KoShapeControllerInterface *controller, KoShape *shape )
KoShapeCreateCommand::KoShapeCreateCommand( KoShapeControllerBase *controller, KoShape *shape )
: m_controller( controller )
, m_shape( shape )
, m_deleteShape( true )
......@@ -188,14 +188,14 @@ QString KoShapeCreateCommand::name () const {
return i18n( "Create shape" );
}
KoShapeDeleteCommand::KoShapeDeleteCommand( KoShapeControllerInterface *controller, KoShape *shape )
KoShapeDeleteCommand::KoShapeDeleteCommand( KoShapeControllerBase *controller, KoShape *shape )
: m_controller( controller )
, m_deleteShapes( false )
{
m_shapes.append( shape );
}
KoShapeDeleteCommand::KoShapeDeleteCommand( KoShapeControllerInterface *controller, const KoSelectionSet &shapes )
KoShapeDeleteCommand::KoShapeDeleteCommand( KoShapeControllerBase *controller, const KoSelectionSet &shapes )
: m_controller( controller )
, m_deleteShapes( false )
{
......
......@@ -31,7 +31,7 @@
class KoShape;
class KoShapeGroup;
class KoShapeContainer;
class KoShapeControllerInterface;
class KoShapeControllerBase;
class QString;
/// The undo / redo command for shape moving.
......@@ -134,13 +134,13 @@ public:
/// The undo / redo command for creating shapes
class FLAKE_EXPORT KoShapeCreateCommand : public KCommand {
public:
KoShapeCreateCommand( KoShapeControllerInterface *controller, KoShape *shape );
KoShapeCreateCommand( KoShapeControllerBase *controller, KoShape *shape );
virtual ~KoShapeCreateCommand();
void execute ();
void unexecute ();
virtual QString name () const;
protected:
KoShapeControllerInterface *m_controller;
KoShapeControllerBase *m_controller;
KoShape *m_shape;
bool m_deleteShape;
};
......@@ -153,19 +153,19 @@ public:
* @param controller the controller to used for deleting.
* @param shape a single shape that should be deleted.
*/
KoShapeDeleteCommand( KoShapeControllerInterface *controller, KoShape *shape );
KoShapeDeleteCommand( KoShapeControllerBase *controller, KoShape *shape );
/**
* Command to delete a set of shapes by means of a shape controller.
* @param controller the controller to used for deleting.
* @param shapes a set of all the shapes that should be deleted.
*/
KoShapeDeleteCommand( KoShapeControllerInterface *controller, const KoSelectionSet &shapes );
KoShapeDeleteCommand( KoShapeControllerBase *controller, const KoSelectionSet &shapes );
virtual ~KoShapeDeleteCommand();
void execute ();
void unexecute ();
virtual QString name () const;
protected:
KoShapeControllerInterface *m_controller;
KoShapeControllerBase *m_controller;
QList<KoShape*> m_shapes;
bool m_deleteShapes;
};
......
......@@ -19,7 +19,8 @@
#include "KoCreateShapeStrategy.h"
#include "KoCreateShapesTool.h"
#include "KoShapeControllerInterface.h"
#include "KoShapeControllerBase.h"
#include "KoShapeRegistry.h"
#include "KoCommand.h"
#include "KoCanvasBase.h"
......@@ -30,7 +31,14 @@ KoCreateShapeStrategy::KoCreateShapeStrategy( KoCreateShapesTool *tool, KoCanvas
}
KCommand* KoCreateShapeStrategy::createCommand() {
KoShape *shape = m_tool->controller()->createShape(selectRect());
KoShapeFactory *factory = KoShapeRegistry::instance()->get(
static_cast<KoCreateShapesTool*>(m_parent)->shapeId());
Q_ASSERT(factory);
KoShape *shape = factory->createDefaultShape();
QRectF rect = selectRect();
shape->setPosition(rect.topLeft());
shape->resize(rect.size());
Q_ASSERT(m_tool->controller() /*controller was set on parent tool*/);
KoShapeCreateCommand *cmd = new KoShapeCreateCommand(m_tool->controller(), shape);
cmd->execute();
return cmd;
......
......@@ -28,9 +28,9 @@
#include <kcommand.h>
KoCreateShapesTool::KoCreateShapesTool(KoCanvasBase *canvas, KoShapeControllerInterface *sci )
KoCreateShapesTool::KoCreateShapesTool(KoCanvasBase *canvas)
: KoInteractionTool( canvas )
, m_shapeController( sci )
, m_shapeController( 0 )
{
}
......
......@@ -22,24 +22,37 @@
#define KOCREATESHAPESTOOL_H
#include "KoInteractionTool.h"
#include "KoShapeFactory.h"
#include <koffice_export.h>
#include <QString>
class KoCanvasBase;
class KoShapeControllerInterface;
class KoShapeControllerBase;
/**
* A tool to create shapes with.
*/
class FLAKE_EXPORT KoCreateShapesTool : public KoInteractionTool
{
public:
KoCreateShapesTool( KoCanvasBase *canvas, KoShapeControllerInterface *sci );
KoCreateShapesTool( KoCanvasBase *canvas);
virtual ~KoCreateShapesTool() {};
void paint( QPainter &painter, KoViewConverter &converter );
KoShapeControllerInterface* controller() const { return m_shapeController; }
KoShapeControllerBase* controller() const { return m_shapeController; }
void setShapeController(KoShapeControllerBase *sc) { m_shapeController = sc; }
void setShapeId(QString id) { m_shapeId = id; }
const QString& shapeId() const { return m_shapeId; }
private:
KoShapeControllerInterface *m_shapeController;
KoShapeControllerBase *m_shapeController;
QString m_shapeId;
};
#endif
......@@ -20,7 +20,6 @@
#include "KoCreateShapesToolFactory.h"
#include "KoCreateShapesTool.h"
#include "KoShapeControllerInterface.h"
#include "KoRectangleShape.h"
#include <klocale.h>
......@@ -36,25 +35,11 @@ KoCreateShapesToolFactory::~KoCreateShapesToolFactory() {
}
KoTool* KoCreateShapesToolFactory::createTool(KoCanvasBase *canvas) {
class DummyShapeController : public KoShapeControllerInterface {
public:
DummyShapeController() {};
~DummyShapeController() {};
void addShape(KoShape* shape) {};
void removeShape(KoShape* shape) {};
KoShape* createShape(const QRectF &outline) const {
KoShape *rect = new KoRectangleShape();
rect->setBackground(QColor(Qt::blue));
rect->setPosition(outline.topLeft());
rect->resize(outline.size());
return rect;
}
};
return new KoCreateShapesTool(canvas, new DummyShapeController());
return new KoCreateShapesTool(canvas);
}
KoID KoCreateShapesToolFactory::id() {
return KoID("Create Shapes", i18n("Create Shapes"));
return KoID("createShapesTool", i18n("Create Shapes"));
}
quint32 KoCreateShapesToolFactory::priority() const {
......
......@@ -36,7 +36,7 @@ KoTool* KoInteractionToolFactory::createTool(KoCanvasBase *canvas) {
}
KoID KoInteractionToolFactory::id() {
return KoID("Default", i18n("Default"));
return KoID("defaultTool", i18n("Default"));
}
quint32 KoInteractionToolFactory::priority() const {
......
......@@ -22,13 +22,17 @@
#include <klocale.h>
KoRectangleShapeFactory::KoRectangleShapeFactory() {
setId(KoID("RectangleShape", i18n("A simple square shape")));
setId(KoID("rectangleShape", i18n("A simple square shape")));
setToolTip(i18n("A simple square shape"));
// XXX: Add a nice icon using the KIconLoader
}
KoShape * KoRectangleShapeFactory::createDefaultShape() {
return new KoRectangleShape();
KoRectangleShape *s = new KoRectangleShape();
s->resize(QSizeF(100, 100));
s->setBackground(QBrush(Qt::yellow));
return s;
}
KoShape * KoRectangleShapeFactory::createShape(KoProperties * params) const {
......
/* This file is part of the KDE project
Copyright (C) 2006 Jan Hambrecht <jaham@gmx.net>
Copyright (C) 2006 Thomas Zander <zander@kde.org>
This library is free software; you can redistribute it and/or
modify it under the terms of the GNU Library General Public
......@@ -18,19 +19,20 @@
* Boston, MA 02110-1301, USA.
*/
#ifndef KOSHAPECONTROLLERINTERFACE_H
#define KOSHAPECONTROLLERINTERFACE_H
#ifndef KOSHAPECONTROLLERBASE_H
#define KOSHAPECONTROLLERBASE_H
#include "KoShape.h"
/**
* The shape controller is an abstract interface that the applications class
* that controls the shapes should implement. This tends to be the document.
* @see KoShapeDeleteCommand, KoShapeCreateCommand
*/
class KoShapeControllerInterface
{
class KoShapeControllerBase {
public:
KoShapeControllerInterface() { }
virtual ~KoShapeControllerInterface() { }
KoShapeControllerBase() { }
virtual ~KoShapeControllerBase() { }
/**
* Add a shape to the shape controller, allowing it to be seen and saved.
......@@ -46,15 +48,6 @@ public:
* @param shape the shape to remove
*/
virtual void removeShape( KoShape* shape ) = 0;
/**
* Factory method to create shapes.
* The CreateShapesTool will call this one when the user selected the outline for
* the position and size of the shape.<br>
* The implementor of this interface can choose to create different types of shapes
* based on things like which button was pressed to activate the create tool.
*/
virtual KoShape* createShape(const QRectF &outline) const = 0;
};
#endif // KOSHAPECONTROLLERINTERFACE_H
#endif
......@@ -39,7 +39,7 @@ KoShapeRegistry::KoShapeRegistry()
{
KService::List offers = KServiceTypeTrader::self()->query(QString::fromLatin1("KOffice/Shape"),
QString::fromLatin1("(Type == 'Service') and "
"([X-KOffice-Version] == 1)"));
"([X-Flake-Version] == 1)"));
KService::List::ConstIterator iter;
......
......@@ -9,5 +9,84 @@
* content, and extend KoShapeContainer for objects that can contain others.
* <p>KoShape is the base class for all flake objects. Flake objects extend it
* to allow themselves to be manipulated by the KoTool s. The content of such an
* object is independent and based on the model of the data this object represents.
* object is independent and based on the model of the data this object represents. <br>
* If you want to be a supplier of shape objects; create a library with a KoShapeFactory
* class and install a .desktop service file with the following content:
* <pre>[Desktop Entry]
Encoding=UTF-8
Name=My Flake Shapes Plugin
ServiceTypes=KOffice/Shape
Type=Service
X-KDE-Library=myflakeshapesplugin
X-Flake-Version=1</pre></p>
* <hr><p>To use Flake in your application you need to have a canvas that is ready for usage
* by flake, do this by implementing the KoCanvasBase interface. Redirect mouse/key events
* to the tool and paint events to the shapeManager.<br>
* Then you have to setup the KoToolManager (from KOfficeUI):<br>In your KoDocument instance:<pre>
KoToolManager::instance()->toolBox()->show();</pre>
* And use a KoCanvasView instance with your Canvas.<pre>
class MyCanvas : public QWidget, public KoCanvasBase {
Q_OBJECT
public:
// KoCanvasBase interface methods.
void gridSize(double *horizontal, double *vertical) const;
bool snapToGrid() const;
void addCommand(KCommand *command, bool execute = true);
KoShapeManager *shapeManager() const { return m_shapeManager; }
void updateCanvas(const QRectF& rc) {
QRect clipRect(viewConverter()->normalToView(rc).toRect());
clipRect.adjust(-2, -2, 2, 2); // grow for to anti-aliasing
update(clipRect);
}
KoTool* tool() { return m_tool; }
void setTool(KoTool *tool) { m_tool = tool; }
KoViewConverter *viewConverter() { return view()->viewConverter(); }
QWidget* canvasWidget() { return this; }
// event handlers
void mouseMoveEvent(QMouseEvent *e) {
KoPointerEvent ev(e, QPointF( viewConverter()->viewToNormal(e->pos()) ));
m_tool->mouseMoveEvent( &ev );
}
void mousePressEvent(QMouseEvent *e) {
KoPointerEvent ev(e, QPointF( viewConverter()->viewToNormal(e->pos()) ));
m_tool->mousePressEvent( &ev );
}
void mouseReleaseEvent(QMouseEvent *e) {
KoPointerEvent ev(e, QPointF( viewConverter()->viewToNormal(e->pos()) ));
m_tool->mouseReleaseEvent( &ev );
}
void keyReleaseEvent (QKeyEvent *e) {
m_tool->keyReleaseEvent(e);
}
void KWCanvas::keyPressEvent( QKeyEvent *e ) {
m_tool->keyPressEvent(e);
}
void paintEvent(QPaintEvent * ev) {
QPainter painter( this );
painter.setRenderHint(QPainter::Antialiasing);
painter.setClipRect(ev->rect());
m_shapeManager->paint( painter, *(viewConverter()), false );
m_tool->paint( painter, *m_doc );
painter.end();
}
private:
KoTool *m_tool;
KoShapeManager *m_shapeManager;
}; </pre>
And then: <pre>
KoCanvasView *canvasController = new KoCanvasView(parentWidget);
MyCanvas *canvas = new MyCanvas();
canvasController->setCanvas(canvas);
KoToolManager::instance()->addControllers(canvasView, m_document);
parentLayout.addWidget(canvasController);</pre>
*/
......@@ -22,7 +22,9 @@
#include <KoToolFactory.h>
#include <KoCreateShapesToolFactory.h>
#include <KoCreateShapesTool.h>
#include <KoInteractionToolFactory.h>
#include <KoShapeControllerBase.h>
#include <KoCanvasView.h>
#include "kactioncollection.h"
......@@ -111,15 +113,14 @@ void KoToolManager::registerTools(KActionCollection *ac) {
m_mutex.unlock();
}
void KoToolManager::addCanvasView(KoCanvasView *view) {
void KoToolManager::addControllers(KoCanvasView *view, KoShapeControllerBase *sc) {
if(m_canvases.contains(view))
return;
setup();
m_mutex.lock();
kDebug(30004) << "KoToolManager::addCanvasView called, setting up..." << endl;
kDebug(30004) << "KoToolManager::addControllers called, setting up..." << endl;
m_canvases.append(view);
//QMap<KoID, KoTool*> toolsMap;
//m_allTools.insert(view, toolsMap);
m_shapeControllers.insert(view, sc);
if(m_activeCanvas == 0)
m_activeCanvas = view;
if(view->canvas())
......@@ -132,6 +133,7 @@ void KoToolManager::addCanvasView(KoCanvasView *view) {
void KoToolManager::removeCanvasView(KoCanvasView *view) {
m_mutex.lock();
m_canvases.removeAll(view);
m_shapeControllers.remove(view);
QMap<QString, KoTool*> toolsMap = m_allTools.value(view);
foreach(KoTool *tool, toolsMap.values())
delete tool;
......@@ -208,6 +210,10 @@ kDebug(30004) << "KoToolManager::attachCanvas\n";
QMap<QString, KoTool*> toolsMap;
foreach(ToolHelper *tool, m_tools)
toolsMap.insert(tool->id().id(), tool->m_toolFactory->createTool(view->canvas()));
KoCreateShapesTool *createTool = dynamic_cast<KoCreateShapesTool*>(toolsMap["createShapesTool"]);
Q_ASSERT(createTool); // if this fails; check the ID didn't change
createTool->setShapeController(m_shapeControllers[view]);
m_mutex.lock();
m_allTools.remove(view);
m_allTools.insert(view, toolsMap);
......@@ -250,12 +256,27 @@ void KoToolManager::switchToolTemporaryRequested(const QString &id) {
void KoToolManager::switchBackRequested() {
if(m_stack.isEmpty()) {
kWarning(30004) << "Tool emits a done while it is not temporary, ignoring";
// default to changing to the interactionTool
switchTool("defaultTool", false);
return;
}
switchTool(m_stack.pop(), false);
}
KoCreateShapesTool *KoToolManager::shapeCreatorTool(KoCanvasBase *canvas) const {
foreach(KoCanvasView *controller, m_canvases) {
if(controller->canvas() == canvas) {
QMap<QString, KoTool*> tools = m_allTools.value(controller);
KoCreateShapesTool *tool =
dynamic_cast<KoCreateShapesTool*>(tools.value("createShapesTool"));
Q_ASSERT(tool /* ID changed? */);
return tool;
}
}
kWarning(30004) << "KoToolManager: can't find the canvas, did you register it?" << endl;
return 0;
}
// ************ ToolHelper **********
QAbstractButton* ToolHelper::createButton(QWidget *parent) {
QToolButton *but = new QToolButton(parent);
......
......@@ -23,6 +23,7 @@
#include <KoID.h>
#include <KoTool.h>
#include <KoCreateShapesTool.h>
#include <koffice_export.h>
#include <QMap>
......@@ -36,6 +37,7 @@ class QAbstractButton;
class KoToolFactory;
class KoCanvasView;
class KoCanvasBase;
class KoShapeControllerBase;
class KoTool;
/**
......@@ -62,9 +64,11 @@ public:
QWidget *toolBox(); // TODO alter from QWidget to KoToolBox
void registerTools(KActionCollection *ac);
void addCanvasView(KoCanvasView *view);
void addControllers(KoCanvasView *view, KoShapeControllerBase *sc);
void removeCanvasView(KoCanvasView *view);
KoCreateShapesTool *shapeCreatorTool(KoCanvasBase *canvas) const;
private:
KoToolManager();
KoToolManager(const KoToolManager&);
......@@ -89,6 +93,7 @@ private:
QWidget *m_toolBox;
QList<ToolHelper*> m_tools;
QMap<KoCanvasView*, KoShapeControllerBase*> m_shapeControllers;
QList<KoCanvasView*> m_canvases;
KoCanvasView *m_activeCanvas;
KoTool *m_activeTool, *m_dummyTool;
......
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment