import org.kde.qt.*;
import org.kde.koala.*;

/** The KScribbleView class provides the view widget for the KScribble instance.
 * The View instance inherits QWidget as a base class and represents the view object of a KMainWindow. As KScribbleView is part of the
 * docuement-view model, it needs a reference to the document object connected with it by the KScribble class to manipulate and display
 * the document structure provided by the KScribbleDoc class.
 *
 * @author Source Framework Automatically Generated by KDevelop, (c) The KDevelop Team.
 * @version KDevelop version 0.4 code generation
 */
public class KScribbleView extends QScrollView {

   private QClipboard cb;
   private KScribbleDoc doc;
   private static final int IDLE = 0;
   private static final int DRAW = 1;
   private static final int SELECT = 2;
   private static final int PASTE = 3;
   private static final int DRAG = 4;

   private QPixmap tmp = new QPixmap();

   private int action = IDLE;
   private QRect select = new QRect();

   private KIconLoader k = new KIconLoader();
   private QImageDrag qid;

   public KScribbleView(KScribbleDoc pDoc, QWidget parent, String name, int wflags) {
      super(parent, name,wflags | WPaintClever | WNorthWestGravity | WRepaintNoErase);
      setBackgroundMode(PaletteBase);
      cb = QApplication.clipboard();
      viewport().setAcceptDrops(true);
      setDragAutoScroll(true);
      doc=pDoc;
      action=IDLE;
      viewport().setCursor( Qt.crossCursor() );

      QSize size=doc.docSize();
      resizeContents(size.width(), size.height());
      resize(size);

   }

   void update(KScribbleView pSender){
	if(pSender != this)
         viewport().repaint(0,0,visibleWidth(), visibleHeight(), false);
   }

   public KScribbleDoc getDocument() {
      return doc;
   }

   void keyPressEvent( QKeyEvent e )  {
      switch (e.key()) {
      case Key_Right:
         scrollBy( 10, 0 );
         break;
      case Key_Left:
         scrollBy( -10,0);
         break;
      case Key_Up:
         scrollBy( 0, -10 );
         break;
      case Key_Down:
         scrollBy( 0, 10 );
         break;
      case Key_Home:
         setContentsPos(0,0);
         break;
      case Key_End:
         setContentsPos(0,viewport().height()-viewport().height());
         break;
      case Key_PageUp:
         scrollBy( 0, -viewport().height() );
         break;
      case Key_PageDown:
         scrollBy( 0, viewport().height() );
         break;
      }

   }

   /** cuts out a selection */
   void cutSelection() {
      select=select.normalize();
      QPixmap cb_pix = new QPixmap();
      cb_pix.resize(select.size());
      // copy selection to cb_pix and copy to clipboard
      QPaintDevice.bitBlt(cb_pix,0, 0, doc.buffer, select.x()+contentsX(), select.y()+contentsY(), cb_pix.width(),cb_pix.height());
      cb.setPixmap(cb_pix);
      // fill cb_pix with white and copy to selection area
      cb_pix.fill(Qt.white());
      QPaintDevice.bitBlt(doc.buffer, select.x()+contentsX(), select.y()+contentsY(),cb_pix, 0, 0, cb_pix.width(), cb_pix.height());
      action = IDLE;
      doc.setModified();
      doc.updateAllViews(this);
      viewport().repaint(0,0,visibleWidth(), visibleHeight(), false);
   }

   /** pastes the clipboard contents to a selection that can be inserted into the picture */
   void pasteSelection(){
      select=cb.pixmap().rect();
      action = PASTE;
      viewport().setCursor( Qt.sizeAllCursor() );
   }

   /** copies a selection to the clipboard */
   void copySelection(){
      select=select.normalize();
      QPixmap cb_pix = new QPixmap();
      cb_pix.resize(select.size());
      // copy selection to cb_pix and copy to clipboard
      QPaintDevice.bitBlt(cb_pix, 0, 0,doc.buffer, select.x()+contentsX(), select.y()+contentsY(), cb_pix.width(),cb_pix.height());
      cb.setPixmap(cb_pix);
      action = IDLE;
      viewport().repaint(0,0,visibleWidth(), visibleHeight(), false);
   }

   public void print(QPrinter pPrinter) {
      if (pPrinter.setup(this)) {
         QPainter p = new QPainter();
         p.begin(pPrinter);

         ///////////////////////////////
         // TODO: add your printing code here
         p.drawPixmap(0,0,doc.buffer);
         ///////////////////////////////
         p.end();
      }
   }

   void viewportMousePressEvent( QMouseEvent e ) {
      if ( e.button() == LeftButton && action == IDLE) {
       action=DRAW;
       doc.polyline.setPoint(0,viewportToContents(e.pos()));
       doc.polyline.setPoint(1,viewportToContents(e.pos()));
       doc.polyline.setPoint(2,viewportToContents(e.pos()));
       doc.updateAllViews(this);
      }
      else if ( e.button() == RightButton && action == IDLE) {
         action = SELECT;
         QPoint pt=e.pos();
         int x = pt.x() > contentsWidth() ? contentsWidth() : pt.x();
         int y = pt.y() > contentsHeight() ? contentsHeight() : pt.y();
         select.setLeft(x-1);
         select.setTop(y-1);
         select.setRight(x-1);
         select.setBottom(y-1);
         }
         else if( action == SELECT ) {
            action = IDLE;

            select=select.normalize();
            // drag
            if(select.contains(e.pos(), true)) { // point inside the selection
               tmp.resize(select.size());
               QPaintDevice.bitBlt(tmp, 0, 0, doc.buffer, select.x()+contentsX(), select.y()+contentsY(), tmp.width(),tmp.height());
               QImage img =tmp.convertToImage();
               QDragObject d = new QImageDrag( img, viewport(), "" );
               d.setPixmap(KIconLoader.BarIcon("filenew"));
               d.drag();
            }
            // remove selection
            else
               viewport().repaint(0,0,visibleWidth(), visibleHeight(), false);
            }
         else if( action == PASTE ) {
            if ( e.button() == RightButton ) {
               action = IDLE;
               viewport().setCursor( Qt.crossCursor() );
            }
            QPoint mv_pt = new QPoint(viewport().height(), viewport().width());
            if(new QRect(0,0,mv_pt.x(),mv_pt.y()).contains(e.pos()))
               select.moveCenter(e.pos());
            else {
               select.moveBottomRight(mv_pt);
            }
            viewport().repaint(0,0,visibleWidth(), visibleHeight(), false);
         }
   }

   void viewportMouseReleaseEvent( QMouseEvent e ) {
     if ( action == DRAW )      {
        action = IDLE;
        doc.updateAllViews(this);
     }
     if ( action == SELECT) {
        QPoint pt=e.pos();
        int x = pt.x() > 0 ? pt.x() : 0;
        int y = pt.y() > 0 ? pt.y() : 0;
        select.setRight(x);
        select.setBottom(y);
        QSize size=doc.docSize();
        select = select.intersect(new QRect(0,0,size.width(), size.height()));
     }
   }

   /** On paste actions inserts the pasted clipboard contents
    */
   void viewportMouseDoubleClickEvent(QMouseEvent e) {
     if( action == PASTE ) {
         action = IDLE;
         select.moveCenter(e.pos());
         viewport().setCursor( Qt.crossCursor() );
         QPixmap cb_pix = new QPixmap();
         cb_pix.resize(cb.pixmap().size());
         cb_pix=cb.pixmap();
         QPaintDevice.bitBlt( doc.buffer,contentsX()+select.x(), contentsY()+select.y(),cb_pix, 0, 0, select.width(), select.height());
         viewport().repaint(0,0,visibleWidth(), visibleHeight(), false);
         doc.setModified();
         doc.updateAllViews(this);
      }

   }

   void viewportMouseMoveEvent( QMouseEvent e ) {
      if ( action == DRAW ) {
         QPainter painter = new QPainter();
         painter.begin( doc.buffer );
         painter.setPen( doc.currentPen() );
         doc.polyline.setPoint(2, doc.polyline.at(1));
         doc.polyline.setPoint(1, doc.polyline.at(0));
         doc.polyline.setPoint(0, viewportToContents(e.pos()));
         painter.drawPolyline( doc.polyline );
         painter.end();

         QRect r = doc.polyline.boundingRect();
         r = r.normalize();
         r.setLeft( r.left() - doc.penWidth() );
         r.setTop( r.top() - doc.penWidth() );
         r.setRight( r.right() + doc.penWidth() );
         r.setBottom( r.bottom() + doc.penWidth() );
         
		 QPaintDevice.bitBlt(viewport(), r.x()-contentsX(), r.y()-contentsY(), doc.buffer, r.x(), r.y(), r.width(),r.height());
         doc.setModified();
         doc.updateAllViews(this);
      }
      if ( action == SELECT ) {
         QPoint pt=e.pos();
         select.setWidth(select.x()+pt.x());
         select.setHeight(select.y()+pt.y());
         select.setRight(pt.x());
         select.setBottom(pt.y());
         QSize size=doc.docSize();
         select = select.intersect(new QRect(0,0,size.width(), size.height()));
         viewport().repaint(0,0,visibleWidth(), visibleHeight(), false);
      }
      if( action == PASTE ) {
         QPoint mv_pt = new QPoint(viewport().height(), viewport().width());
         if(new QRect(0,0,mv_pt.x(),mv_pt.y()).contains(e.pos()))
            select.moveCenter(e.pos());
         else {
            select.moveBottomRight(mv_pt);
         }
         QRect pm_rect=cb.pixmap().rect();
         select.setWidth(pm_rect.width());
         select.setHeight(pm_rect.height());
         QSize size=doc.docSize();
         select = select.intersect(new QRect(0,0,size.width(), size.height()));
         viewport().repaint(0,0,visibleWidth(), visibleHeight(), false);
         doc.setModified();
         doc.updateAllViews(this);
      }
   }

   //void KScribbleView::viewportResizeEvent( QResizeEvent *e )
   //{
   //}

   void viewportPaintEvent( QPaintEvent e ) {
     QPaintDevice.bitBlt( viewport(),0, 0, doc.buffer, contentsX(), contentsY(), doc.buffer.width(),doc.buffer.width());

     if( action == PASTE )
     {
       tmp.resize(cb.pixmap().size());
       tmp=cb.pixmap();
     }
     if( action == PASTE || action == DRAG )
     {
       QSize size=doc.docSize();
       select = select.intersect(new QRect(0,0,size.width(), size.height()));
       if(select.intersects(e.rect()))
        QPaintDevice.bitBlt(viewport(), select.x(), select.y(), tmp, 0, 0, select.width(), select.height());
     }
      if( action == PASTE || action == DRAG || action == SELECT ) {
         if(select.intersects(e.rect())) {
            QPainter paint_area = new QPainter();
            paint_area.begin(viewport());
            paint_area.setPen(new QPen(Qt.black(), 0, DashLine));
            paint_area.drawRect( select );
            paint_area.end();
         }
     }

      // not implemented for QScrollView yet
//      super.viewportPaintEvent(e);
   }

   void  viewportDragEnterEvent ( QDragEnterEvent e) {
      e.accept(QImageDrag.canDecode(e));
      action = DRAG;
   }

   void  viewportDragMoveEvent ( QDragMoveEvent e) {
      QImage img = new QImage();

      if ( QImageDrag.canDecode(e) ){
      	 QImageDrag.decode(e, img);
         tmp.resize(img.size());
         tmp.convertFromImage(img);
         select.setWidth(tmp.width());
         select.setHeight(tmp.height());
         select.moveCenter(e.pos());
         viewport().repaint(0,0,visibleWidth(), visibleHeight(), false);
      }
   }

   void  viewportDragLeaveEvent ( QDragLeaveEvent e ) {
      action = IDLE;
      viewport().repaint(0,0,visibleWidth(), visibleHeight(), false);
   }

   void  viewportDropEvent ( QDropEvent e) {
     QImage img = new QImage();
      if ( QImageDrag.canDecode(e) ) {
         QImageDrag.decode(e, img);
         tmp.resize(img.size());
         tmp.convertFromImage(img);
         select.setWidth(tmp.width());
         select.setHeight(tmp.height());
         select.moveCenter(e.pos());
         QPaintDevice.bitBlt(doc.buffer, select.x()+contentsX(), select.y()+contentsY(), tmp,0,0,tmp.width(), tmp.height());
         doc.setModified();
         doc.updateAllViews(this);
      }
      action = IDLE;
      viewport().repaint(0,0,visibleWidth(), visibleHeight(), false);
   }

}
