/*************************************************************************** kimearea.cpp - description ------------------- begin : Thu Jun 14 2001 copyright : (C) 2001 by Jan Schaefer email : janschaefer@users.sourceforge.net ***************************************************************************/ /*************************************************************************** * * * 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 #include #include #include #include #include #include #include #include #include #include #include "kimearea.h" #include "kimecommon.h" #define SELSIZE 7 bool Area::highlightArea; bool Area::showAlt; Area::Area() { _coords=new TQPointArray(); _selectionPoints= new SelectionPointList(); _selectionPoints->setAutoDelete(true); _finished=false; _isSelected=false; _name=i18n("noname"); _listViewItem=0L; currentHighlighted=-1; _type=Area::None; _highlightedPixmap=0L; } Area* Area::clone() const { Area* areaClone = new Area(); areaClone->setArea( *this ); return areaClone; } TQPointArray* Area::coords() const { return _coords; } TQString Area::getHTMLAttributes() const { TQString retStr=""; for (AttributeIterator it = firstAttribute();it!=lastAttribute();++it) { retStr+=it.key()+"=\""+it.data()+"\" "; } return retStr; } Area::~Area() { delete _coords; delete _selectionPoints; delete _highlightedPixmap; } bool Area::contains(const TQPoint &) const { return false; } TQString Area::getHTMLCode() const { return ""; } TQString Area::attribute(const TQString & name) const { return _attributes[name.lower()]; } void Area::setAttribute(const TQString & name, const TQString & value) { _attributes.replace(name.lower(),value); if (value.isEmpty()) _attributes.remove(name.lower()); } AttributeIterator Area::firstAttribute() const { return _attributes.begin(); } AttributeIterator Area::lastAttribute() const { return _attributes.end(); } bool Area::setCoords(const TQString &) { return true; } void Area::moveSelectionPoint(TQRect*, const TQPoint &) {} // Default implementation; is specified by subclasses TQString Area::coordsToString() const { return ""; } Area::ShapeType Area::type() const { return _type; } void Area::setArea(const Area & copy) { delete _coords; delete _selectionPoints; _coords=new TQPointArray(copy.coords()->copy()); _selectionPoints= new SelectionPointList(); currentHighlighted=-1; // Need a deep copy of the list for (TQRect *r=copy.selectionPoints()->first();r!=0L;r=copy.selectionPoints()->next()) _selectionPoints->append(new TQRect( r->topLeft(),r->bottomRight() ) ); _finished=copy.finished(); _isSelected=copy.isSelected(); _rect = copy.rect(); for (AttributeIterator it = copy.firstAttribute();it!=copy.lastAttribute();++it) { setAttribute(it.key(),it.data()); } setMoving(copy.isMoving()); // _listViewItem=0L; } void Area::setListViewItem(TQListViewItem* item) { _listViewItem=item; } void Area::deleteListViewItem() { delete _listViewItem; _listViewItem = 0L; } void Area::setRect(const TQRect & r) { _rect=r; updateSelectionPoints(); } TQRect Area::rect() const { return _rect; } void Area::setMoving(bool b) { _isMoving=b; } void Area::moveBy(int dx, int dy) { _rect.moveBy(dx,dy); for (uint i=0;i<_coords->size();i++) { int newX=_coords->point(i).x()+dx; int newY=_coords->point(i).y()+dy; _coords->setPoint(i,newX,newY); } for (TQRect *r=_selectionPoints->first();r!=0L;r=_selectionPoints->next()) { r->moveBy(dx,dy); } } void Area::moveTo(int x, int y) { int dx=x-rect().left(); int dy=y-rect().top(); moveBy(dx,dy); } uint Area::countSelectionPoints() const { return (uint) selectionPoints()->count(); } int Area::addCoord(const TQPoint & p) { _coords->resize(_coords->size()+1); _coords->setPoint(_coords->size()-1,p); TQRect *r= new TQRect(0,0,SELSIZE,SELSIZE); r->moveCenter(p); _selectionPoints->append(r); setRect(_coords->boundingRect()); return _coords->size()-1; } void Area::insertCoord(int pos, const TQPoint & p) { /* kdDebug() << p.x() << "," << p.y() << endl; if ( _coords->size()>0 ) { for (int i=0; i<_coords->size(); i++) { if (p==_coords->point(i)) { kdDebug() << "same Point already exists" << endl; return; } } } */ _coords->resize(_coords->size()+1); for (int i=_coords->size()-1;i>pos;i--) { _coords->setPoint(i,_coords->point(i-1)); } _coords->setPoint(pos, p); TQRect *r= new TQRect(0,0,SELSIZE,SELSIZE); r->moveCenter(p); _selectionPoints->insert(pos,r); setRect(_coords->boundingRect()); } void Area::removeCoord(int pos) { int count=_coords->size(); if (count<4) { kdDebug() << "Danger : trying to remove coordinate from Area with less then 4 coordinates !" << endl; return; } for (int i=pos;i<(count-1);i++) _coords->setPoint(i, _coords->point(i+1)); _coords->resize(count-1); _selectionPoints->remove(pos); setRect(_coords->boundingRect()); } bool Area::removeSelectionPoint(TQRect * r) { if (_selectionPoints->contains(r)) { removeCoord(_selectionPoints->find(r)); return true; } return false; } void Area::moveCoord(int pos, const TQPoint & p) { _coords->setPoint(pos,p); _selectionPoints->at(pos)->moveCenter(p); setRect(_coords->boundingRect()); } void Area::setSelected(bool b) { _isSelected=b; if (_listViewItem) { _listViewItem->setSelected(b); } } void Area::highlightSelectionPoint(int number){ currentHighlighted=number; } TQRect Area::selectionRect() const { TQRect r = rect(); r.moveBy(-SELSIZE*2,-SELSIZE*2); r.setSize(r.size()+TQSize(SELSIZE*4,SELSIZE*4)); return r; } void Area::drawHighlighting(TQPainter & p) { if (Area::highlightArea && !isMoving() && _highlightedPixmap) { p.setRasterOp(TQt::CopyROP); TQPoint point = TQPoint(rect().x(),rect().y()); if (point.x()<0) point.setX(0); if (point.y()<0) point.setY(0); p.drawPixmap( point, *_highlightedPixmap); } } void Area::drawAlt(TQPainter & p) { double x,y; double scalex = p.worldMatrix().m11(); // double scaley = p.worldMatrix().m12(); TQWMatrix oldMatrix = p.worldMatrix(); p.setWorldMatrix(TQWMatrix(1,oldMatrix.m12(), oldMatrix.m21(), 1, oldMatrix.dx(), oldMatrix.dy() )); x = (rect().x()+rect().width()/2)*scalex; y = (rect().y()+rect().height()/2)*scalex; TQFontMetrics metrics = p.fontMetrics(); int w = metrics.width(attribute("alt")); x -= w/2; y += metrics.height()/4; if (highlightArea) { p.setRasterOp(TQt::CopyROP); p.setPen(TQt::black); } else { p.setRasterOp(TQt::XorROP); p.setPen(TQPen(TQColor("white"),1)); } p.drawText(myround(x),myround(y),attribute("alt")); p.setWorldMatrix(oldMatrix); } void Area::draw(TQPainter & p) { // Only draw the selection points at base class // the rest is done in the derived classes if (_isSelected) { int i=0; double scalex = p.worldMatrix().m11(); // double scaley = p.worldMatrix().m12(); TQWMatrix oldMatrix = p.worldMatrix(); p.setWorldMatrix(TQWMatrix(1,oldMatrix.m12(), oldMatrix.m21(), 1, oldMatrix.dx(), oldMatrix.dy() )); for (TQRect *r=_selectionPoints->first();r!=0L;r=_selectionPoints->next()) { // Draw a green circle around the selected point ( only when editing a polygon ) if (i==currentHighlighted) { TQRect r2(0,0,15,15); r2.moveCenter(r->center()*scalex); p.setRasterOp(TQt::CopyROP); p.setPen(TQPen(TQColor("lightgreen"),2)); p.drawEllipse(r2); p.setRasterOp(TQt::XorROP); p.setPen(TQPen(TQColor("white"),1)); } // Draw the selection point p.setRasterOp(TQt::XorROP); TQRect r3(*r); int d = 1; if (scalex > 2) d=0; r3.moveCenter( TQPoint((int)(r3.center().x()*scalex),(int)(r3.center().y()*scalex)) ); p.fillRect(r3,TQBrush("white")); /* TQRect r3(*r); r3.moveTopLeft( TQPoint(r3.left()*scalex+2*(scalex-1), r3.top()*scalex+2*(scalex-1)) ); r3.setSize(r3.size()+TQSize(2,2)); //+ r3.moveBy(-1,-1); p.setRasterOp(TQt::CopyROP); p.setPen(TQPen(TQColor("lightgreen"),1)); p.setBrush(TQColor("lightgreen")); p.drawPie(r3,0,5760); p.setPen(TQPen(TQColor("black"),1)); r3.setSize(r3.size()+TQSize(2,2)); r3.moveBy(-1,-1); p.drawEllipse(r3); */ i++; } p.setWorldMatrix(oldMatrix); } if (showAlt) { drawAlt(p); } p.setRasterOp(TQt::XorROP); } TQRect* Area::onSelectionPoint(const TQPoint & p, double zoom) const { for (TQRect *r=_selectionPoints->first();r!=0L;r=_selectionPoints->next()) { TQRect r2(r->topLeft(),r->bottomRight()); r2.moveCenter(r2.center()*zoom); if (r2.contains(p)) { return r; } } return 0L; } /** * returns only the part of the image which is * covered by the area */ TQPixmap Area::cutOut(const TQImage & image) { if ( 0>=rect().width() || 0>=rect().height() || !rect().intersects(image.rect()) ) { TQPixmap dummyPix(10,10); dummyPix.fill(); delete _highlightedPixmap; _highlightedPixmap = 0L; return dummyPix; } // Get the mask from the subclasses TQBitmap mask=getMask(); // The rectangle which is part of the image TQRect partOfImage=rect(); TQRect partOfMask(0,0,mask.width(),mask.height()); // If the area is outside of the image make the // preview smaller if ( (rect().x()+rect().width()) > image.width() ) { partOfImage.setWidth( image.width()-rect().x() ); partOfMask.setWidth( image.width()-rect().x() ); } if ( (rect().x() < 0) ) { partOfImage.setX(0); partOfMask.setX(myabs(rect().x())); } if ( (rect().y()+rect().height()) > image.height() ) { partOfImage.setHeight( image.height()-rect().y() ); partOfMask.setHeight ( image.height()-rect().y() ); } if ( (rect().y() < 0) ) { partOfImage.setY(0); partOfMask.setY(myabs(rect().y())); } TQImage tempImage=mask.convertToImage().copy(partOfMask); mask.convertFromImage(tempImage); // partOfImage = partOfImage.normalize(); TQImage cut=image.copy(partOfImage); TQPixmap pix; // partOfMask = partOfMask.normalize(); if (!partOfMask.isValid()) kdDebug() << "PartofMask not valid : " << partOfMask.x() << "," << partOfMask.y() << "," << partOfMask.width() << "," << partOfMask.height() << "," << endl; /* TQBitmap mask2(partOfMask.width(), partOfMask.height()); TQPainter p4(&mask2); p4.drawPixmap( TQPoint(0,0) ,mask,partOfMask); p4.flush(); p4.end(); */ pix.convertFromImage(cut); setHighlightedPixmap(cut, mask); TQPixmap retPix(pix.width(),pix.height()); TQPainter p3(&retPix); // if transparent image fill the background // with gimp-like rectangles if (pix.mask()) { TQPixmap backPix(32,32); // Gimp like transparent rectangle TQPainter p2(&backPix); p2.fillRect(0,0,32,32,TQColor(156,149,156)); p2.fillRect(0,16,16,16,TQColor(98,105,98)); p2.fillRect(16,0,16,16,TQColor(98,105,98)); p2.flush(); p3.setPen(TQPen()); p3.fillRect(0,0,pix.width(),pix.height(),TQBrush(TQColor("black"),backPix)); } p3.drawPixmap(TQPoint(0,0),pix); p3.flush(); p3.end(); retPix.setMask(mask); return retPix; } TQBitmap Area::getMask() const { TQBitmap b; return b; } void Area::setHighlightedPixmap( TQImage & im, TQBitmap & mask ) { if (!Area::highlightArea) return; delete _highlightedPixmap; TQImage image = im.convertDepth( 32 ); TQSize size = image.size(); TQColor pixel; double r,g,b; // highlight every pixel for (int y=0; y < size.height(); y++) { for (int x=0; x < size.width(); x++) { r = tqRed(image.pixel(x,y)); g = tqGreen(image.pixel(x,y)); b = tqBlue(image.pixel(x,y)); r = (r *123 / 255)+132; g = (g *123 / 255)+132; b = (b *123 / 255)+132; pixel.setRgb( (int) r, (int) g, (int) b); image.setPixel(x,y, pixel.rgb()); } } _highlightedPixmap = new TQPixmap(); _highlightedPixmap->convertFromImage( image ); _highlightedPixmap->setMask( mask ); if (_highlightedPixmap->isNull()) kdDebug() << "HighlightedPixmap is null" << endl; } /******************************************************************** * RECTANGLE *******************************************************************/ RectArea::RectArea() : Area() { TQRect *p = new TQRect(0,0,SELSIZE,SELSIZE); _selectionPoints->append(p); p = new TQRect(0,0,SELSIZE,SELSIZE); _selectionPoints->append(p); p = new TQRect(0,0,SELSIZE,SELSIZE); _selectionPoints->append(p); p = new TQRect(0,0,SELSIZE,SELSIZE); _selectionPoints->append(p); _type=Area::Rectangle; } RectArea::~RectArea() { } Area* RectArea::clone() const { Area* areaClone = new RectArea(); areaClone->setArea( *this ); return areaClone; } void RectArea::draw(TQPainter & p) { drawHighlighting(p); // p.setRasterOp(TQt::CopyROP); // p.setRasterOp(TQt:: OrROP); // TQBrush b(TQBrush::SolidPattern); // TQBrush b(TQBrush::Dense4Pattern); // TQBrush b(TQBrush::BDiagPattern); // b.setColor(TQColor(32,32,32)); // p.fillRect(rect(), b); p.setRasterOp(TQt::XorROP); p.setPen(TQPen(TQColor("white"),1)); TQRect r(rect()); r.setWidth(r.width()+1); r.setHeight(r.height()+1); p.drawRect(r); Area::draw(p); } TQBitmap RectArea::getMask() const { TQBitmap mask(rect().width(),rect().height()); mask.fill(TQt::color0); TQPainter p(&mask); p.setBackgroundColor(TQt::color0); p.setPen(TQt::color1); p.setBrush(TQt::color1); mask.fill(TQt::color1); p.end(); return mask; } TQString RectArea::coordsToString() const { TQString retStr=TQString("%1,%2,%3,%4") .tqarg(rect().left()) .tqarg(rect().top()) .tqarg(rect().right()) .tqarg(rect().bottom()); return retStr; } bool RectArea::contains(const TQPoint & p) const{ return rect().contains(p); } void RectArea::moveSelectionPoint(TQRect* selectionPoint, const TQPoint & p) { selectionPoint->moveCenter(p); int i=0; for (TQRect *r=_selectionPoints->first();r!=0L;r=_selectionPoints->next()) { if (r==selectionPoint) break; i++; } TQRect r2(_rect); switch (i) { case 0 : _rect.setLeft(p.x()); _rect.setTop(p.y()); break; case 1 : _rect.setRight(p.x()); _rect.setTop(p.y()); break; case 2 : _rect.setLeft(p.x()); _rect.setBottom(p.y()); break; case 3 : _rect.setRight(p.x()); _rect.setBottom(p.y()); break; } if ( ! _rect.isValid()) _rect=r2; updateSelectionPoints(); } void RectArea::updateSelectionPoints() { _selectionPoints->first()->moveCenter(_rect.topLeft()); _selectionPoints->next()->moveCenter(_rect.topRight()+TQPoint(1,0)); _selectionPoints->next()->moveCenter(_rect.bottomLeft()+TQPoint(0,1)); _selectionPoints->next()->moveCenter(_rect.bottomRight()+TQPoint(1,1)); } bool RectArea::setCoords(const TQString & s) { _finished=true; TQStringList list=TQStringList::split(",",s); TQRect r; bool ok=true; TQStringList::Iterator it = list.begin(); r.setLeft((*it).toInt(&ok,10));it++; r.setTop((*it).toInt(&ok,10));it++; r.setRight((*it).toInt(&ok,10));it++; r.setBottom((*it).toInt(&ok,10)); if (ok) { setRect(r); return true; } else return false; } TQString RectArea::getHTMLCode() const { TQString retStr; retStr+="append(p); p = new TQRect(0,0,SELSIZE,SELSIZE); _selectionPoints->append(p); p = new TQRect(0,0,SELSIZE,SELSIZE); _selectionPoints->append(p); p = new TQRect(0,0,SELSIZE,SELSIZE); _selectionPoints->append(p); } CircleArea::~CircleArea() { } Area* CircleArea::clone() const { Area* areaClone = new CircleArea(); areaClone->setArea( *this ); return areaClone; } void CircleArea::draw(TQPainter & p) { drawHighlighting(p); /* p.setRasterOp(TQt::CopyROP); TQBrush bold = p.brush(); TQBrush b(TQBrush::Dense5Pattern); b.setColor(TQColor("green")); p.setBrush(b); TQRect r = _rect; r.moveBy(1,1); r.setSize( r.size()-TQSize(2,2) ); p.drawChord(r,0,5760); p.setBrush(bold); */ p.setRasterOp(TQt::XorROP); p.setPen(TQPen(TQColor("white"),1)); TQRect r(_rect); r.setWidth(r.width()+1); r.setHeight(r.height()+1); p.drawEllipse(r); Area::draw(p); } TQBitmap CircleArea::getMask() const { TQBitmap mask(_rect.width(),_rect.height()); mask.fill(TQt::color0); TQPainter p(&mask); p.setBackgroundColor(TQt::color0); p.setPen(TQt::color1); p.setBrush(TQt::color1); p.drawPie(TQRect(0,0,_rect.width(),_rect.height()),0,5760); p.flush(); p.end(); return mask; } TQString CircleArea::coordsToString() const { TQString retStr=TQString("%1,%2,%3") .tqarg(_rect.center().x()) .tqarg(_rect.center().y()) .tqarg(_rect.width()/2); return retStr; } bool CircleArea::contains(const TQPoint & p) const { TQRegion r(_rect,TQRegion::Ellipse); return r.contains(p); } void CircleArea::moveSelectionPoint(TQRect* selectionPoint, const TQPoint & p) { selectionPoint->moveCenter(p); int i=0; for (TQRect *r=_selectionPoints->first();r!=0L;r=_selectionPoints->next()) { if (r==selectionPoint) break; i++; } // The code below really sucks, but I have no better idea. // it only makes sure that the circle is perfektly round TQPoint newPoint; int diff=myabs(p.x()-_rect.center().x()); if (myabs(p.y()-_rect.center().y())>diff) diff=myabs(p.y()-_rect.center().y()); newPoint.setX( p.x()-_rect.center().x()<0 ? _rect.center().x()-diff : _rect.center().x()+diff); newPoint.setY( p.y()-_rect.center().y()<0 ? _rect.center().y()-diff : _rect.center().y()+diff); switch (i) { case 0 : if (newPoint.x() < _rect.center().x() && newPoint.y() < _rect.center().y()) { _rect.setLeft(newPoint.x()); _rect.setTop(newPoint.y()); } break; case 1 : if (newPoint.x() > _rect.center().x() && newPoint.y() < _rect.center().y()) { _rect.setRight(newPoint.x()); _rect.setTop(newPoint.y()); } break; case 2 : if (newPoint.x() < _rect.center().x() && newPoint.y() > _rect.center().y()) { _rect.setLeft(newPoint.x()); _rect.setBottom(newPoint.y()); } break; case 3 : if (newPoint.x() > _rect.center().x() && newPoint.y() > _rect.center().y()) { _rect.setRight(newPoint.x()); _rect.setBottom(newPoint.y()); } break; } updateSelectionPoints(); } void CircleArea::setRect(const TQRect & r) { TQRect r2 = r; if ( r2.height() != r2.width() ) r2.setHeight( r2.width() ); Area::setRect(r2); } void CircleArea::updateSelectionPoints() { _selectionPoints->first()->moveCenter(_rect.topLeft()); _selectionPoints->next()->moveCenter(_rect.topRight()); _selectionPoints->next()->moveCenter(_rect.bottomLeft()); _selectionPoints->next()->moveCenter(_rect.bottomRight()); } bool CircleArea::setCoords(const TQString & s) { _finished=true; TQStringList list=TQStringList::split(",",s); bool ok=true; TQStringList::Iterator it = list.begin(); int x=(*it).toInt(&ok,10);it++; int y=(*it).toInt(&ok,10);it++; int rad=(*it).toInt(&ok,10); if (!ok) return false; TQRect r; r.setWidth(rad*2); r.setHeight(rad*2); r.moveCenter(TQPoint(x,y)); setRect(r); return true; } TQString CircleArea::getHTMLCode() const { TQString retStr; retStr+="setArea( *this ); return areaClone; } void PolyArea::draw(TQPainter & p) { drawHighlighting(p); p.setRasterOp(TQt::XorROP); p.setPen(TQPen(TQColor("white"),1)); if (_coords->count()==0) return; if (_finished) p.drawPolygon ( *_coords,false,0,_coords->count()); else p.drawPolyline ( *_coords,0,_coords->count()); /* p.moveTo(_coords->point(0)); for (int i=1;i<_coords->count();i++) p.lineTo(_coords->point(i)); if (_finished) p.lineTo(_coords->point(0)); */ Area::draw(p); } TQBitmap PolyArea::getMask() const { TQBitmap mask(_rect.width(),_rect.height()); mask.fill(TQt::color0); TQPainter p(&mask); p.setBackgroundColor(TQt::color0); p.setPen(TQt::color1); p.setBrush(TQt::color1); p.setClipping(true); TQRegion r(*_coords); r.translate(-_rect.left(),-_rect.top()); p.setClipRegion(r); p.fillRect(TQRect(0,0,_rect.width(),_rect.height()),TQt::color1); p.flush(); p.end(); return mask; } TQString PolyArea::coordsToString() const { TQString retStr; for (uint i=0;i<_coords->count();i++) { retStr.append(TQString("%1,%2,") .tqarg(_coords->point(i).x()) .tqarg(_coords->point(i).y())); } retStr.remove(retStr.length()-1,1); return retStr; } int PolyArea::distance(const TQPoint &p1, const TQPoint &p2) { TQPoint temp = p1-p2; return temp.manhattanLength(); } bool PolyArea::isBetween(const TQPoint &p, const TQPoint &p1, const TQPoint &p2) { int dist = distance(p,p1)+distance(p,p2)-distance(p1,p2); if (myabs(dist)<1) return true; else return false; } void PolyArea::simplifyCoords() { if (_coords->size()<4) return; TQPoint p = _coords->point(0) - _coords->point(1); uint i = 1; while( (i<_coords->size()) && (_coords->size() > 3) ) { p = _coords->point(i-1) - _coords->point(i); if (p.manhattanLength() < 3) removeCoord(i); else i++; } p = _coords->point(0) - _coords->point(1); double angle2; double angle1; if (p.y()==0) angle1 = 1000000000; else angle1 = (double) p.x() / (double) p.y(); i=2; while( (i<_coords->size()) && (_coords->size() > 3) ) { p = _coords->point(i-1) - _coords->point(i); if (p.y()==0) angle2 = 1000000000; else angle2 = (double) p.x() / (double) p.y(); if ( angle2==angle1 ) { kdDebug() << "removing " << i-1 << endl; removeCoord(i-1); } else { i++; kdDebug() << "skipping " << i-1 << " cause " << angle1 << "!= " << angle2 << endl; angle1 = angle2; } } } int PolyArea::addCoord(const TQPoint & p) { if (_coords->size()<3) { return Area::addCoord(p); } if (_coords->point(_coords->size()-1) == p) { kdDebug() << "equal Point added" << endl; return -1; } int n=_coords->size(); // TQPoint temp = p-_coords->point(0); int nearest = 0; int olddist = distance(p,_coords->point(0)); int mindiff = 999999999; // find the two points, which are the nearest one to the new point for (int i=1; i <= n; i++) { int dist = distance(p,_coords->point(i%n)); int dist2 = distance(_coords->point(i-1),_coords->point(i%n)); int diff = myabs(dist+olddist-dist2); if ( diffcount() >2 ) { TQRegion r(*_coords); return r.contains(p); } else return false; } void PolyArea::moveSelectionPoint(TQRect* selectionPoint, const TQPoint & p) { selectionPoint->moveCenter(p); int i=0; for (TQRect *r=_selectionPoints->first();r!=0L;r=_selectionPoints->next()) { if (r==selectionPoint) break; i++; } _coords->setPoint(i,p); _rect=_coords->boundingRect(); } void PolyArea::updateSelectionPoints() { TQRect *r; r=_selectionPoints->first(); for (uint i=0;i<_coords->size();i++) { r->moveCenter(_coords->point(i)); r=_selectionPoints->next(); } } bool PolyArea::setCoords(const TQString & s) { _finished=true; TQStringList list=TQStringList::split(",",s); _coords=new TQPointArray(); _selectionPoints= new SelectionPointList(); for (TQStringList::Iterator it = list.begin(); it !=list.end(); ++it) { bool ok=true; int newXCoord=(*it).toInt(&ok,10); if (!ok) return false; it++; if (it==list.end()) break; int newYCoord=(*it).toInt(&ok,10); if (!ok) return false; insertCoord(_coords->size(), TQPoint(newXCoord,newYCoord)); } return true; } TQString PolyArea::getHTMLCode() const { TQString retStr; retStr+="resize(_coords->size()-1); _selectionPoints->removeLast(); _finished=b; } TQRect PolyArea::selectionRect() const { TQRect r = _rect; r.moveBy(-10,-10); r.setSize(r.size()+TQSize(21,21)); return r; } /******************************************************************** * DEFAULT *******************************************************************/ DefaultArea::DefaultArea() : Area() { _type=Area::Default; } DefaultArea::~DefaultArea() { } Area* DefaultArea::clone() const { Area* areaClone = new DefaultArea(); areaClone->setArea( *this ); return areaClone; } void DefaultArea::draw(TQPainter &) {} TQString DefaultArea::getHTMLCode() const { TQString retStr; retStr+="add( it.current()->clone() ); } // areaClone->setArea( *this ); return areaClone; } void AreaSelection::add(Area *a) { // if a selection of areas was added get the areas of it AreaSelection *selection=0L; if ( (selection = dynamic_cast ( a ) ) ) { AreaList list = selection->getAreaList(); for (Area* area = list.first(); area != 0L; area = list.next() ) { if ( _areas->find( area ) == -1 ) { _areas->append( area ); // Must come before area->setSelected area->setSelected( true ); } } } else { if ( _areas->find( a ) == -1 ) { _areas->append( a ); // Must come before a->setSelected a->setSelected( true ); } } tqinvalidate(); } void AreaSelection::remove(Area *a) { if (_areas->find(a) == -1) return; a->setSelected( false ); _areas->remove( a ); tqinvalidate(); } void AreaSelection::reset() { AreaListIterator it=getAreaListIterator(); for ( ; it.current() != 0L; ++it ) { it.current()->setSelected( false ); } _areas->clear(); tqinvalidate(); } bool AreaSelection::contains(const TQPoint & p) const { bool b=false; AreaListIterator it=getAreaListIterator(); for ( ; it.current() != 0L; ++it ) { if ( it.current()->contains( p ) ) { b=true; break; } } return b; } TQRect* AreaSelection::onSelectionPoint(const TQPoint & p, double zoom) const { AreaListIterator it=getAreaListIterator(); if (it.count() != 1) return 0L; TQRect* retRect=0L; for ( ; it.current() != 0L; ++it ) { if ( (retRect = it.current()->onSelectionPoint( p , zoom) ) ) { break; } } return retRect; } void AreaSelection::moveSelectionPoint(TQRect* selectionPoint, const TQPoint & p) { // It's only possible to move a SelectionPoint if only one Area is selected if (_areas->count() != 1) return; _areas->getFirst()->moveSelectionPoint(selectionPoint,p); tqinvalidate(); } void AreaSelection::moveBy(int dx, int dy) { AreaListIterator it=getAreaListIterator(); for ( ; it.current() != 0L; ++it ) it.current()->moveBy(dx,dy); Area::moveBy( dx, dy ); tqinvalidate(); } TQString AreaSelection::typeString() const { // if there is only one Area selected // show the name of that Area if ( _areas->count()==0 ) return ""; else if ( _areas->count()==1 ) return _areas->getFirst()->typeString(); else return i18n("Number of Areas"); } Area::ShapeType AreaSelection::type() const { // if there is only one Area selected // take the type of that Area if ( _areas->count()==0 ) return Area::None; else if ( _areas->count()==1 ) return _areas->getFirst()->type(); else return Area::Selection; } void AreaSelection::updateSelectionPoints() { AreaListIterator it=getAreaListIterator(); for ( ; it.current() != 0L; ++it ) { it.current()->updateSelectionPoints(); } tqinvalidate(); } TQRect AreaSelection::selectionRect() const { if (!_selectionCacheValid) { _selectionCacheValid=true; TQRect r; AreaListIterator it=getAreaListIterator(); for ( ; it.current() != 0L; ++it ) r = r | it.current()->selectionRect(); _cachedSelectionRect=r; } return _cachedSelectionRect; } uint AreaSelection::count() const { return _areas->count(); } bool AreaSelection::isEmpty() const { return _areas->isEmpty(); } AreaList AreaSelection::getAreaList() const { AreaList list(*_areas); return list; } AreaListIterator AreaSelection::getAreaListIterator() const { AreaListIterator it(*_areas); return it; } void AreaSelection::setArea(const Area & copy) { Area *area = copy.clone(); AreaSelection *selection = dynamic_cast(area); if (selection) setAreaSelection(*selection); else { Area::setArea(copy); tqinvalidate(); } } void AreaSelection::setAreaSelection(const AreaSelection & copy) { AreaListIterator it=getAreaListIterator(); AreaListIterator it2=copy.getAreaListIterator(); if (it.count() != it2.count()) return; for ( ; it.current() != 0L; ++it, ++it2 ) it.current()->setArea(*it2.current()); Area::setArea(copy); tqinvalidate(); } void AreaSelection::setAreaList( const AreaList & areas ) { delete _areas; _areas = new AreaList(areas); tqinvalidate(); } void AreaSelection::setRect(const TQRect & r) { if ( _areas->count()==1 ) { _areas->getFirst()->setRect(r); } tqinvalidate(); _rect=rect(); updateSelectionPoints(); } TQRect AreaSelection::rect() const { if (!_rectCacheValid) { _rectCacheValid=true; TQRect r; AreaListIterator it=getAreaListIterator(); for ( ; it.current() != 0L; ++it ) r = r | it.current()->rect(); _cachedRect=r; } return _cachedRect; } int AreaSelection::addCoord(const TQPoint & p) { if ( _areas->count()==1 ) { return _areas->getFirst()->addCoord(p); tqinvalidate(); } return 0; } void AreaSelection::insertCoord(int pos, const TQPoint & p) { if ( _areas->count()==1 ) { _areas->getFirst()->insertCoord(pos, p); tqinvalidate(); } } void AreaSelection::removeCoord(int pos) { if ( _areas->count()==1 ) { _areas->getFirst()->removeCoord(pos); tqinvalidate(); } } bool AreaSelection::removeSelectionPoint(TQRect * r) { bool result=false; if ( _areas->count()==1 ) { result = _areas->getFirst()->removeSelectionPoint(r); tqinvalidate(); } return result; } SelectionPointList* AreaSelection::selectionPoints() const { if ( _areas->count()==1 ) { return _areas->getFirst()->selectionPoints(); } return _selectionPoints; } void AreaSelection::moveCoord(int pos,const TQPoint & p) { if ( _areas->count()==1 ) { _areas->getFirst()->moveCoord(pos,p); tqinvalidate(); } } void AreaSelection::highlightSelectionPoint(int i) { if ( _areas->count()==1 ) { _areas->getFirst()->highlightSelectionPoint(i); tqinvalidate(); } } TQPointArray* AreaSelection::coords() const { if ( _areas->count()==1 ) { return _areas->getFirst()->coords(); } return Area::coords(); } TQString AreaSelection::attribute(const TQString & name) const { if ( _areas->count()==1 ) { return _areas->getFirst()->attribute(name); } return Area::attribute(name); } void AreaSelection::setAttribute(const TQString & name, const TQString & value) { AreaListIterator it=getAreaListIterator(); for ( ; it.current() != 0L; ++it ) it.current()->setAttribute(name,value); Area::setAttribute(name,value); } AttributeIterator AreaSelection::firstAttribute() const { if ( _areas->count()==1 ) { return _areas->getFirst()->firstAttribute(); } return _attributes.begin(); } AttributeIterator AreaSelection::lastAttribute() const { if ( _areas->count()==1 ) { return _areas->getFirst()->lastAttribute(); } return _attributes.end(); } void AreaSelection::setMoving(bool b) { AreaListIterator it=getAreaListIterator(); for ( ; it.current() != 0L; ++it ) it.current()->setMoving(b); Area::setMoving(b); } bool AreaSelection::isMoving() const { if ( _areas->count()==1 ) { return _areas->getFirst()->isMoving(); } return Area::isMoving(); } /** * Checks if an area is outside the rectangle parameter * returns false if an area has no pixel in common with the rectangle parameter **/ bool AreaSelection::allAreasWithin(const TQRect & r) const { if ( ! r.contains(rect()) ) { AreaListIterator it=getAreaListIterator(); for ( ; it.current() != 0L; ++it ) if (!it.current()->rect().intersects(r)) return false; } return true; } void AreaSelection::draw(TQPainter &) {}