/*
 *  Copyright (c) 2005 Adrian Page <adrian@pagenet.plus.com>
 *
 *  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.
 *
 *  This program 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 General Public License for more details.
 *
 *  You should have received a copy of the GNU General Public License
 *  along with this program; if not, write to the Free Software
 *  Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
 */

#ifndef KIS_CANVAS_PAINTER_H_
#define KIS_CANVAS_PAINTER_H_

#ifdef HAVE_CONFIG_H
#include <config.h>
#endif

#include <tqpainter.h>

#include "kis_global.h"

class KisCanvas;
class KisCanvasWidget;

class KisCanvasWidgetPainter {
public:
    KisCanvasWidgetPainter();
    virtual ~KisCanvasWidgetPainter();

    virtual bool begin(KisCanvasWidget *canvasWidget, bool unclipped = false) = 0;
    virtual bool end();

    virtual void save();
    virtual void restore();

    virtual TQFontMetrics fontMetrics() const;
    virtual TQFontInfo fontInfo() const;

    virtual const TQFont& font() const;
    virtual void setFont(const TQFont&);
    virtual const TQPen& pen() const;
    virtual void setPen(const TQPen&);
    virtual void setPen(TQt::PenStyle);
    virtual void setPen(const TQColor&);
    virtual const TQBrush&brush() const;
    virtual void setBrush(const TQBrush&);
    virtual void setBrush(TQt::BrushStyle);
    virtual void setBrush(const TQColor&);
    virtual TQPoint pos() const;

    virtual const TQColor&backgroundColor() const;
    virtual void setBackgroundColor(const TQColor&);
    virtual TQt::BGMode backgroundMode() const;
    virtual void setBackgroundMode(TQt::BGMode);
    virtual TQt::RasterOp rasterOp()	const;
    virtual void setRasterOp(TQt::RasterOp);
    virtual const TQPoint&brushOrigin() const;
    virtual void setBrushOrigin(int x, int y);
    virtual void setBrushOrigin(const TQPoint&);

    virtual bool hasViewXForm() const;
    virtual bool hasWorldXForm() const;

    virtual void setViewXForm(bool);
    virtual TQRect window() const;
    virtual void setWindow(const TQRect&);
    virtual void setWindow(int x, int y, int w, int h);
    virtual TQRect viewport() const;
    virtual void setViewport(const TQRect&);
    virtual void setViewport(int x, int y, int w, int h);

    virtual void setWorldXForm(bool);
    virtual const TQWMatrix&worldMatrix() const;
    virtual void setWorldMatrix(const TQWMatrix&, bool combine=false);

    virtual void saveWorldMatrix();
    virtual void restoreWorldMatrix();

    virtual void scale(double sx, double sy);
    virtual void shear(double sh, double sv);
    virtual void rotate(double a);

    virtual void translate(double dx, double dy);
    virtual void resetXForm();
    virtual double translationX() const;
    virtual double translationY() const;

    virtual TQPoint xForm(const TQPoint&) const;
    virtual TQRect xForm(const TQRect&)	const;
    virtual TQPointArray xForm(const TQPointArray&) const;
    virtual TQPointArray xForm(const TQPointArray&, int index, int npoints) const;
    virtual TQPoint xFormDev(const TQPoint&) const;
    virtual TQRect xFormDev(const TQRect&)  const;
    virtual TQPointArray xFormDev(const TQPointArray&) const;
    virtual TQPointArray xFormDev(const TQPointArray&, int index, int npoints) const;

    virtual void setClipping(bool);
    virtual bool hasClipping() const;
    virtual TQRegion clipRegion(TQPainter::CoordinateMode = TQPainter::CoordDevice) const;
    virtual void setClipRect(const TQRect&, TQPainter::CoordinateMode = TQPainter::CoordDevice);
    virtual void setClipRect(int x, int y, int w, int h, TQPainter::CoordinateMode = TQPainter::CoordDevice);
    virtual void setClipRegion(const TQRegion&, TQPainter::CoordinateMode = TQPainter::CoordDevice);

    virtual void drawPoint(int x, int y);
    virtual void drawPoint(const TQPoint&);
    virtual void drawPoints(const TQPointArray& a, int index=0, int npoints=-1);
    virtual void moveTo(int x, int y);
    virtual void moveTo(const TQPoint&);
    virtual void lineTo(int x, int y);
    virtual void lineTo(const TQPoint&);
    virtual void drawLine(int x1, int y1, int x2, int y2);
    virtual void drawLine(const TQPoint&, const TQPoint&);
    virtual void drawRect(int x, int y, int w, int h);
    virtual void drawRect(const TQRect&);
    virtual void drawWinFocusRect(int x, int y, int w, int h);
    virtual void drawWinFocusRect(int x, int y, int w, int h, const TQColor&bgColor);
    virtual void drawWinFocusRect(const TQRect&);
    virtual void drawWinFocusRect(const TQRect&, const TQColor&bgColor);
    virtual void drawRoundRect(int x, int y, int w, int h, int = 25, int = 25);
    virtual void drawRoundRect(const TQRect&, int = 25, int = 25);
    virtual void drawEllipse(int x, int y, int w, int h);
    virtual void drawEllipse(const TQRect&);
    virtual void drawArc(int x, int y, int w, int h, int a, int alen);
    virtual void drawArc(const TQRect&, int a, int alen);
    virtual void drawPie(int x, int y, int w, int h, int a, int alen);
    virtual void drawPie(const TQRect&, int a, int alen);
    virtual void drawChord(int x, int y, int w, int h, int a, int alen);
    virtual void drawChord(const TQRect&, int a, int alen);
    virtual void drawLineSegments(const TQPointArray&, int index=0, int nlines=-1);
    virtual void drawPolyline(const TQPointArray&, int index=0, int npoints=-1);
    virtual void drawPolygon(const TQPointArray&, bool winding=false, int index=0, int npoints=-1);
    virtual void drawConvexPolygon(const TQPointArray&, int index=0, int npoints=-1);
    virtual void drawCubicBezier(const TQPointArray&, int index=0);
    virtual void drawPixmap(int x, int y, const TQPixmap&, int sx=0, int sy=0, int sw=-1, int sh=-1);
    virtual void drawPixmap(const TQPoint&, const TQPixmap&, const TQRect&sr);
    virtual void drawPixmap(const TQPoint&, const TQPixmap&);
    virtual void drawPixmap(const TQRect&, const TQPixmap&);
    virtual void drawImage(int x, int y, const TQImage&, int sx = 0, int sy = 0, int sw = -1, int sh = -1, int conversionFlags = 0);
    virtual void drawImage(const TQPoint&, const TQImage&, const TQRect&sr, int conversionFlags = 0);
    virtual void drawImage(const TQPoint&, const TQImage&, int conversion_flags = 0);
    virtual void drawImage(const TQRect&, const TQImage&);
    virtual void drawTiledPixmap(int x, int y, int w, int h, const TQPixmap&, int sx=0, int sy=0);
    virtual void drawTiledPixmap(const TQRect&, const TQPixmap&, const TQPoint&);
    virtual void drawTiledPixmap(const TQRect&, const TQPixmap&);
    //virtual void drawPicture(const TQPicture&);
    //virtual void drawPicture(int x, int y, const TQPicture&);
    //virtual void drawPicture(const TQPoint&, const TQPicture&);

    virtual void fillRect(int x, int y, int w, int h, const TQBrush&);
    virtual void fillRect(const TQRect&, const TQBrush&);
    virtual void eraseRect(int x, int y, int w, int h);
    virtual void eraseRect(const TQRect&);

    virtual void drawText(int x, int y, const TQString&, int len = -1, TQPainter::TextDirection dir = TQPainter::Auto);
    virtual void drawText(const TQPoint&, const TQString&, int len = -1, TQPainter::TextDirection dir = TQPainter::Auto);

    virtual void drawText(int x, int y, const TQString&, int pos, int len, TQPainter::TextDirection dir = TQPainter::Auto);
    virtual void drawText(const TQPoint&p, const TQString&, int pos, int len, TQPainter::TextDirection dir = TQPainter::Auto);

    virtual void drawText(int x, int y, int w, int h, int flags, const TQString&, int len = -1, TQRect *br=0, TQTextParag **intern=0);
    virtual void drawText(const TQRect&, int flags, const TQString&, int len = -1, TQRect *br=0, TQTextParag **intern=0);

    virtual void drawTextItem(int x, int y, const TQTextItem&ti, int textflags = 0);
    virtual void drawTextItem(const TQPoint& p, const TQTextItem&ti, int textflags = 0);

    virtual TQRect boundingRect(int x, int y, int w, int h, int flags, const TQString&, int len = -1, TQTextParag **intern=0);
    virtual TQRect boundingRect(const TQRect&, int flags, const TQString&, int len = -1, TQTextParag **intern=0);

    virtual int	tabStops() const;
    virtual void setTabStops(int);
    virtual int	*tabArray() const;
    virtual void setTabArray(int *);

protected:
    TQFont m_defaultFont;
    TQPen m_defaultPen;
    TQBrush m_defaultBrush;
    TQColor m_defaultColor;
    TQPoint m_defaultBrushOrigin;
    TQWMatrix m_defaultWorldMatrix;
};

class KisCanvasPainter {
public:
    KisCanvasPainter();
    KisCanvasPainter(KisCanvas *canvas);
    KisCanvasPainter(const TQPaintDevice *paintDevice);

    ~KisCanvasPainter();

    bool begin(KisCanvas *canvas, bool unclipped = false);
    bool begin(const TQPaintDevice *paintDevice, bool unclipped = false);

    bool end();

    void save();
    void restore();

    TQFontMetrics fontMetrics() const;
    TQFontInfo fontInfo() const;

    const TQFont& font() const;
    void setFont(const TQFont&);
    const TQPen& pen() const;
    void setPen(const TQPen&);
    void setPen(TQt::PenStyle);
    void setPen(const TQColor&);
    const TQBrush&brush() const;
    void setBrush(const TQBrush&);
    void setBrush(TQt::BrushStyle);
    void setBrush(const TQColor&);
    TQPoint pos() const;

    const TQColor&backgroundColor() const;
    void setBackgroundColor(const TQColor&);
    TQt::BGMode backgroundMode() const;
    void setBackgroundMode(TQt::BGMode);
    TQt::RasterOp rasterOp()	const;
    void setRasterOp(TQt::RasterOp);
    const TQPoint&brushOrigin() const;
    void setBrushOrigin(int x, int y);
    void setBrushOrigin(const TQPoint&);

    bool hasViewXForm() const;
    bool hasWorldXForm() const;

    void setViewXForm(bool);
    TQRect window() const;
    void setWindow(const TQRect&);
    void setWindow(int x, int y, int w, int h);
    TQRect viewport() const;
    void setViewport(const TQRect&);
    void setViewport(int x, int y, int w, int h);

    void setWorldXForm(bool);
    const TQWMatrix&worldMatrix() const;
    void setWorldMatrix(const TQWMatrix&, bool combine=false);

    void saveWorldMatrix();
    void restoreWorldMatrix();

    void scale(double sx, double sy);
    void shear(double sh, double sv);
    void rotate(double a);

    void translate(double dx, double dy);
    void resetXForm();
    double translationX() const;
    double translationY() const;

    TQPoint xForm(const TQPoint&) const;
    TQRect xForm(const TQRect&)	const;
    TQPointArray xForm(const TQPointArray&) const;
    TQPointArray xForm(const TQPointArray&, int index, int npoints) const;
    TQPoint xFormDev(const TQPoint&) const;
    TQRect xFormDev(const TQRect&)  const;
    TQPointArray xFormDev(const TQPointArray&) const;
    TQPointArray xFormDev(const TQPointArray&, int index, int npoints) const;

    void setClipping(bool);
    bool hasClipping() const;
    TQRegion clipRegion(TQPainter::CoordinateMode = TQPainter::CoordDevice) const;
    void setClipRect(const TQRect&, TQPainter::CoordinateMode = TQPainter::CoordDevice);
    void setClipRect(int x, int y, int w, int h, TQPainter::CoordinateMode = TQPainter::CoordDevice);
    void setClipRegion(const TQRegion&, TQPainter::CoordinateMode = TQPainter::CoordDevice);

    void drawPoint(int x, int y);
    void drawPoint(const TQPoint&);
    void drawPoints(const TQPointArray& a, int index=0, int npoints=-1);
    void moveTo(int x, int y);
    void moveTo(const TQPoint&);
    void lineTo(int x, int y);
    void lineTo(const TQPoint&);
    void drawLine(int x1, int y1, int x2, int y2);
    void drawLine(const TQPoint&, const TQPoint&);
    void drawRect(int x, int y, int w, int h);
    void drawRect(const TQRect&);
    void drawWinFocusRect(int x, int y, int w, int h);
    void drawWinFocusRect(int x, int y, int w, int h, const TQColor&bgColor);
    void drawWinFocusRect(const TQRect&);
    void drawWinFocusRect(const TQRect&, const TQColor&bgColor);
    void drawRoundRect(int x, int y, int w, int h, int = 25, int = 25);
    void drawRoundRect(const TQRect&, int = 25, int = 25);
    void drawEllipse(int x, int y, int w, int h);
    void drawEllipse(const TQRect&);
    void drawArc(int x, int y, int w, int h, int a, int alen);
    void drawArc(const TQRect&, int a, int alen);
    void drawPie(int x, int y, int w, int h, int a, int alen);
    void drawPie(const TQRect&, int a, int alen);
    void drawChord(int x, int y, int w, int h, int a, int alen);
    void drawChord(const TQRect&, int a, int alen);
    void drawLineSegments(const TQPointArray&, int index=0, int nlines=-1);
    void drawPolyline(const TQPointArray&, int index=0, int npoints=-1);
    void drawPolygon(const TQPointArray&, bool winding=false, int index=0, int npoints=-1);
    void drawConvexPolygon(const TQPointArray&, int index=0, int npoints=-1);
    void drawCubicBezier(const TQPointArray&, int index=0);
    void drawPixmap(int x, int y, const TQPixmap&, int sx=0, int sy=0, int sw=-1, int sh=-1);
    void drawPixmap(const TQPoint&, const TQPixmap&, const TQRect&sr);
    void drawPixmap(const TQPoint&, const TQPixmap&);
    void drawPixmap(const TQRect&, const TQPixmap&);
    void drawImage(int x, int y, const TQImage&, int sx = 0, int sy = 0, int sw = -1, int sh = -1, int conversionFlags = 0);
    void drawImage(const TQPoint&, const TQImage&, const TQRect&sr, int conversionFlags = 0);
    void drawImage(const TQPoint&, const TQImage&, int conversion_flags = 0);
    void drawImage(const TQRect&, const TQImage&);
    void drawTiledPixmap(int x, int y, int w, int h, const TQPixmap&, int sx=0, int sy=0);
    void drawTiledPixmap(const TQRect&, const TQPixmap&, const TQPoint&);
    void drawTiledPixmap(const TQRect&, const TQPixmap&);
    //void drawPicture(const TQPicture&);
    //void drawPicture(int x, int y, const TQPicture&);
    //void drawPicture(const TQPoint&, const TQPicture&);

    void fillRect(int x, int y, int w, int h, const TQBrush&);
    void fillRect(const TQRect&, const TQBrush&);
    void eraseRect(int x, int y, int w, int h);
    void eraseRect(const TQRect&);

    void drawText(int x, int y, const TQString&, int len = -1, TQPainter::TextDirection dir = TQPainter::Auto);
    void drawText(const TQPoint&, const TQString&, int len = -1, TQPainter::TextDirection dir = TQPainter::Auto);

    void drawText(int x, int y, const TQString&, int pos, int len, TQPainter::TextDirection dir = TQPainter::Auto);
    void drawText(const TQPoint&p, const TQString&, int pos, int len, TQPainter::TextDirection dir = TQPainter::Auto);

    void drawText(int x, int y, int w, int h, int flags, const TQString&, int len = -1, TQRect *br=0, TQTextParag **intern=0);
    void drawText(const TQRect&, int flags, const TQString&, int len = -1, TQRect *br=0, TQTextParag **intern=0);

    void drawTextItem(int x, int y, const TQTextItem&ti, int textflags = 0);
    void drawTextItem(const TQPoint& p, const TQTextItem&ti, int textflags = 0);

    TQRect boundingRect(int x, int y, int w, int h, int flags, const TQString&, int len = -1, TQTextParag **intern=0);
    TQRect boundingRect(const TQRect&, int flags, const TQString&, int len = -1, TQTextParag **intern=0);

    int	tabStops() const;
    void setTabStops(int);
    int	*tabArray() const;
    void setTabArray(int *);

protected:
    KisCanvasWidgetPainter *m_canvasWidgetPainter;
    TQFont m_defaultFont;
    TQPen m_defaultPen;
    TQBrush m_defaultBrush;
    TQColor m_defaultColor;
    TQPoint m_defaultBrushOrigin;
    TQWMatrix m_defaultWorldMatrix;
};

#endif // KIS_CANVAS_PAINTER_H_

