Qucs-GUI  0.0.19
/home/travis/build/Qucs/qucs/qucs/qucs/paintings/rectangle.cpp
Go to the documentation of this file.
00001 /***************************************************************************
00002                               rectangle.cpp
00003                              ---------------
00004     begin                : Sat Nov 22 2003
00005     copyright            : (C) 2003 by Michael Margraf
00006     email                : michael.margraf@alumni.tu-berlin.de
00007  ***************************************************************************/
00008 
00009 /***************************************************************************
00010  *                                                                         *
00011  *   This program is free software; you can redistribute it and/or modify  *
00012  *   it under the terms of the GNU General Public License as published by  *
00013  *   the Free Software Foundation; either version 2 of the License, or     *
00014  *   (at your option) any later version.                                   *
00015  *                                                                         *
00016  ***************************************************************************/
00017 #include "rectangle.h"
00018 #include "filldialog.h"
00019 #include "schematic.h"
00020 
00021 #include <QPainter>
00022 #include <QPushButton>
00023 #include <QLineEdit>
00024 #include <QComboBox>
00025 #include <QCheckBox>
00026 
00027 Rectangle::Rectangle(bool _filled)
00028 {
00029   Name = "Rectangle ";
00030   isSelected = false;
00031   Pen = QPen(QColor());
00032   Brush = QBrush(Qt::lightGray);
00033   filled = _filled;
00034   cx = cy = 0;
00035   x1 = x2 = 0;
00036   y1 = y2 = 0;
00037 }
00038 
00039 Rectangle::~Rectangle()
00040 {
00041 }
00042 
00043 // --------------------------------------------------------------------------
00044 void Rectangle::paint(ViewPainter *p)
00045 {
00046   if(isSelected) {
00047     p->Painter->setPen(QPen(Qt::darkGray,Pen.width()+5));
00048     if(filled)  p->Painter->setBrush(Brush);
00049     p->drawRect(cx, cy, x2, y2);
00050     p->Painter->setPen(QPen(Qt::white, Pen.width(), Pen.style()));
00051     p->Painter->setBrush(Qt::NoBrush);
00052     p->drawRect(cx, cy, x2, y2);
00053 
00054     p->Painter->setPen(QPen(Qt::darkRed,2));
00055     p->drawResizeRect(cx, cy+y2);  // markers for changing the size
00056     p->drawResizeRect(cx, cy);
00057     p->drawResizeRect(cx+x2, cy+y2);
00058     p->drawResizeRect(cx+x2, cy);
00059     return;
00060   }
00061   p->Painter->setPen(Pen);
00062   if(filled)  p->Painter->setBrush(Brush);
00063   p->drawRect(cx, cy, x2, y2);
00064   p->Painter->setBrush(Qt::NoBrush); // no filling for the next paintings
00065 }
00066 
00067 // --------------------------------------------------------------------------
00068 void Rectangle::paintScheme(Schematic *p)
00069 {
00070   p->PostPaintEvent(_Rect, cx, cy, x2, y2);
00071 }
00072 
00073 // --------------------------------------------------------------------------
00074 void Rectangle::getCenter(int& x, int &y)
00075 {
00076   x = cx+(x2>>1);
00077   y = cy+(y2>>1);
00078 }
00079 
00080 // --------------------------------------------------------------------------
00081 // Sets the center of the painting to x/y.
00082 void Rectangle::setCenter(int x, int y, bool relative)
00083 {
00084   if(relative) { cx += x;  cy += y; }
00085   else { cx = x-(x2>>1);  cy = y-(y2>>1); }
00086 }
00087 
00088 // --------------------------------------------------------------------------
00089 Painting* Rectangle::newOne()
00090 {
00091   return new Rectangle();
00092 }
00093 
00094 // --------------------------------------------------------------------------
00095 Element* Rectangle::info(QString& Name, char* &BitmapFile, bool getNewOne)
00096 {
00097   Name = QObject::tr("Rectangle");
00098   BitmapFile = (char *) "rectangle";
00099 
00100   if(getNewOne)  return new Rectangle();
00101   return 0;
00102 }
00103 
00104 // --------------------------------------------------------------------------
00105 Element* Rectangle::info_filled(QString& Name, char* &BitmapFile, bool getNewOne)
00106 {
00107   Name = QObject::tr("filled Rectangle");
00108   BitmapFile = (char *) "filledrect";
00109 
00110   if(getNewOne)  return new Rectangle(true);
00111   return 0;
00112 }
00113 
00114 // --------------------------------------------------------------------------
00115 bool Rectangle::load(const QString& s)
00116 {
00117   bool ok;
00118 
00119   QString n;
00120   n  = s.section(' ',1,1);    // cx
00121   cx = n.toInt(&ok);
00122   if(!ok) return false;
00123 
00124   n  = s.section(' ',2,2);    // cy
00125   cy = n.toInt(&ok);
00126   if(!ok) return false;
00127 
00128   n  = s.section(' ',3,3);    // x2
00129   x2 = n.toInt(&ok);
00130   if(!ok) return false;
00131 
00132   n  = s.section(' ',4,4);    // y2
00133   y2 = n.toInt(&ok);
00134   if(!ok) return false;
00135 
00136   n  = s.section(' ',5,5);    // color
00137   QColor co;
00138   co.setNamedColor(n);
00139   Pen.setColor(co);
00140   if(!Pen.color().isValid()) return false;
00141 
00142   n  = s.section(' ',6,6);    // thickness
00143   Pen.setWidth(n.toInt(&ok));
00144   if(!ok) return false;
00145 
00146   n  = s.section(' ',7,7);    // line style
00147   Pen.setStyle((Qt::PenStyle)n.toInt(&ok));
00148   if(!ok) return false;
00149 
00150   n  = s.section(' ',8,8);    // fill color
00151   co.setNamedColor(n);
00152   Brush.setColor(co);
00153   if(!Brush.color().isValid()) return false;
00154 
00155   n  = s.section(' ',9,9);    // fill style
00156   Brush.setStyle((Qt::BrushStyle)n.toInt(&ok));
00157   if(!ok) return false;
00158 
00159   n  = s.section(' ',10,10);    // filled
00160   if(n.toInt(&ok) == 0) filled = false;
00161   else filled = true;
00162   if(!ok) return false;
00163 
00164   return true;
00165 }
00166 
00167 // --------------------------------------------------------------------------
00168 QString Rectangle::save()
00169 {
00170   QString s = Name +
00171   QString::number(cx) + " " + QString::number(cy) + " " +
00172   QString::number(x2) + " " + QString::number(y2) + " " +
00173   Pen.color().name() + " " + QString::number(Pen.width()) + " " +
00174   QString::number(Pen.style()) + " " +
00175   Brush.color().name() + " " + QString::number(Brush.style());
00176   if(filled) s += " 1";
00177   else s += " 0";
00178   return s;
00179 }
00180 
00181 // --------------------------------------------------------------------------
00182 QString Rectangle::saveCpp()
00183 {
00184   QString b = filled ?
00185     QString (", QBrush (QColor (\"%1\"), %2)").
00186     arg(Brush.color().name()).arg(toBrushString(Brush.style())) : "";
00187   QString s =
00188     QString ("new Area (%1, %2, %3, %4, "
00189        "QPen (QColor (\"%5\"), %6, %7)%8)").
00190     arg(cx).arg(cy).arg(x2).arg(y2).
00191     arg(Pen.color().name()).arg(Pen.width()).arg(toPenString(Pen.style())).
00192     arg(b);
00193   s = "Rects.append (" + s + ");";
00194   return s;
00195 }
00196 
00197 QString Rectangle::saveJSON()
00198 {
00199   QString b = filled ?
00200     QString ("\"colorfill\" : \"%1\", \"stylefill\" : \"%2\"").
00201     arg(Brush.color().name()).arg(toBrushString(Brush.style())) : "";
00202 
00203   QString s =
00204     QString("{\"type\" : \"rectangle\", "
00205       "\"x\" : %1, \"y\" : %2, \"w\" : %3, \"h\" : %4, "
00206       "\"color\" : \"%5\", \"thick\" : %6, \"style\" : \"%7\", %8},").
00207       arg(cx).arg(cy).arg(x2).arg(y2).
00208       arg(Pen.color().name()).arg(Pen.width()).arg(toPenString(Pen.style())).
00209       arg(b);
00210   return s;
00211 }
00212 
00213 // --------------------------------------------------------------------------
00214 // Checks if the resize area was clicked.
00215 bool Rectangle::resizeTouched(float fX, float fY, float len)
00216 {
00217   float fCX = float(cx), fCY = float(cy);
00218   float fX2 = float(cx+x2), fY2 = float(cy+y2);
00219 
00220   State = -1;
00221   if(fX < fCX-len) return false;
00222   if(fY < fCY-len) return false;
00223   if(fX > fX2+len) return false;
00224   if(fY > fY2+len) return false;
00225 
00226   State = 0;
00227   if(fX < fCX+len)  State = 1;
00228   else if(fX < fX2-len) { State = -1; return false; }
00229   if(fY < fCY+len)  State |= 2;
00230   else if(fY < fY2-len) { State = -1; return false; }
00231 
00232   return true;
00233 }
00234 
00235 // --------------------------------------------------------------------------
00236 // Mouse move action during resize.
00237 void Rectangle::MouseResizeMoving(int x, int y, Schematic *p)
00238 {
00239   paintScheme(p);  // erase old painting
00240   switch(State) {
00241     case 0: x2 = x-cx; y2 = y-cy; // lower right corner
00242       break;
00243     case 1: x2 -= x-cx; cx = x; y2 = y-cy; // lower left corner
00244       break;
00245     case 2: x2 = x-cx; y2 -= y-cy; cy = y; // upper right corner
00246       break;
00247     case 3: x2 -= x-cx; cx = x; y2 -= y-cy; cy = y; // upper left corner
00248       break;
00249   }
00250   if(x2 < 0) { State ^= 1; x2 *= -1; cx -= x2; }
00251   if(y2 < 0) { State ^= 2; y2 *= -1; cy -= y2; }
00252 
00253   paintScheme(p);  // paint new painting
00254 }
00255 
00256 // --------------------------------------------------------------------------
00257 // fx/fy are the precise coordinates, gx/gy are the coordinates set on grid.
00258 // x/y are coordinates without scaling.
00259 void Rectangle::MouseMoving(
00260   Schematic *paintScale, int, int, int gx, int gy,
00261   Schematic *p, int x, int y, bool drawn)
00262 {
00263   if(State > 0) {
00264     if(State > 1)
00265       paintScale->PostPaintEvent(_Rect,x1, y1, x2-x1, y2-y1);  // erase old painting
00266     State++;
00267     x2 = gx;
00268     y2 = gy;
00269     paintScale->PostPaintEvent(_Rect,x1, y1, x2-x1, y2-y1);  // paint new rectangle
00270   }
00271   else { x2 = gx; y2 = gy; }
00272 
00273 
00274   // FIXME #warning p->setPen(Qt::SolidLine);
00275   if(drawn) {
00276     p->PostPaintEvent(_Rect, cx+13, cy, 18, 12,0,0,true);  // erase old cursor symbol
00277     if(filled) {   // hatched ?
00278       p->PostPaintEvent(_Line, cx+14, cy+6, cx+19, cy+1,0,0,true);
00279       p->PostPaintEvent(_Line, cx+26, cy+1, cx+17, cy+10,0,0,true);
00280       p->PostPaintEvent(_Line, cx+29, cy+5, cx+24, cy+10,0,0,true);
00281     }
00282   }
00283   cx = x;
00284   cy = y;
00285   p->PostPaintEvent(_Rect,cx+13, cy, 18, 12,0,0,true);  // paint new cursor symbol
00286   if(filled) {   // hatched ?
00287     p->PostPaintEvent(_Line, cx+14, cy+6, cx+19, cy+1,0,0,true);
00288     p->PostPaintEvent(_Line, cx+26, cy+1, cx+17, cy+10,0,0,true);
00289     p->PostPaintEvent(_Line, cx+29, cy+5, cx+24, cy+10,0,0,true);
00290   }
00291 }
00292 
00293 // --------------------------------------------------------------------------
00294 bool Rectangle::MousePressing()
00295 {
00296   State++;
00297   if(State == 1) {
00298     x1 = x2;
00299     y1 = y2;    // first corner is determined
00300   }
00301   else {
00302     if(x1 < x2) { cx = x1; x2 = x2-x1; } // cx/cy to upper left corner
00303     else { cx = x2; x2 = x1-x2; }
00304     if(y1 < y2) { cy = y1; y2 = y2-y1; }
00305     else { cy = y2; y2 = y1-y2; }
00306     x1 = y1 = 0;
00307     State = 0;
00308     return true;    // rectangle is ready
00309   }
00310   return false;
00311 }
00312 
00313 // --------------------------------------------------------------------------
00314 // Checks if the coordinates x/y point to the painting.
00315 bool Rectangle::getSelected(float fX, float fY, float w)
00316 {
00317   if(filled) {
00318     if(int(fX) > cx+x2) return false;   // coordinates outside the rectangle ?
00319     if(int(fY) > cy+y2) return false;
00320     if(int(fX) < cx) return false;
00321     if(int(fY) < cy) return false;
00322   }
00323   else {
00324     fX -= float(cx);
00325     fY -= float(cy);
00326     float fX2 = float(x2);
00327     float fY2 = float(y2);
00328 
00329     if(fX > fX2+w) return false;   // coordinates outside the rectangle ?
00330     if(fY > fY2+w) return false;
00331     if(fX < -w) return false;
00332     if(fY < -w) return false;
00333 
00334     // coordinates inside the rectangle ?
00335     if(fX < fX2-w) if(fX > w) if(fY < fY2-w) if(fY > w)
00336       return false;
00337   }
00338 
00339   return true;
00340 }
00341 
00342 // --------------------------------------------------------------------------
00343 // Rotates around the center.
00344 void Rectangle::rotate()
00345 {
00346   cy += (y2-x2) >> 1;
00347   cx += (x2-y2) >> 1;
00348   int tmp = x2;
00349   x2 = y2;
00350   y2 = tmp;
00351 }
00352 
00353 // --------------------------------------------------------------------------
00354 // Mirrors about center line.
00355 void Rectangle::mirrorX()
00356 {
00357   // nothing to do
00358 }
00359 
00360 // --------------------------------------------------------------------------
00361 // Mirrors about center line.
00362 void Rectangle::mirrorY()
00363 {
00364   // nothing to do
00365 }
00366 
00367 // --------------------------------------------------------------------------
00368 // Calls the property dialog for the painting and changes them accordingly.
00369 // If there were changes, it returns 'true'.
00370 bool Rectangle::Dialog()
00371 {
00372   bool changed = false;
00373 
00374   FillDialog *d = new FillDialog(QObject::tr("Edit Rectangle Properties"));
00375   d->ColorButt->setPaletteBackgroundColor(Pen.color());
00376   d->LineWidth->setText(QString::number(Pen.width()));
00377   d->StyleBox->setCurrentItem(Pen.style()-1);
00378   d->FillColorButt->setPaletteBackgroundColor(Brush.color());
00379   d->FillStyleBox->setCurrentItem(Brush.style());
00380   d->CheckFilled->setChecked(filled);
00381   d->slotCheckFilled(filled);
00382 
00383   if(d->exec() == QDialog::Rejected) {
00384     delete d;
00385     return false;
00386   }
00387 
00388   if(Pen.color() != d->ColorButt->paletteBackgroundColor()) {
00389     Pen.setColor(d->ColorButt->paletteBackgroundColor());
00390     changed = true;
00391   }
00392   if(Pen.width()  != d->LineWidth->text().toInt()) {
00393     Pen.setWidth(d->LineWidth->text().toInt());
00394     changed = true;
00395   }
00396   if(Pen.style()  != (Qt::PenStyle)(d->StyleBox->currentItem()+1)) {
00397     Pen.setStyle((Qt::PenStyle)(d->StyleBox->currentItem()+1));
00398     changed = true;
00399   }
00400   if(filled != d->CheckFilled->isChecked()) {
00401     filled = d->CheckFilled->isChecked();
00402     changed = true;
00403   }
00404   if(Brush.color() != d->FillColorButt->paletteBackgroundColor()) {
00405     Brush.setColor(d->FillColorButt->paletteBackgroundColor());
00406     changed = true;
00407   }
00408   if(Brush.style() != d->FillStyleBox->currentItem()) {
00409     Brush.setStyle((Qt::BrushStyle)d->FillStyleBox->currentItem());
00410     changed = true;
00411   }
00412 
00413   delete d;
00414   return changed;
00415 }
 All Data Structures Namespaces Files Functions Variables Typedefs Enumerations Enumerator Friends Defines