stdr_map_loader.cpp
Go to the documentation of this file.
00001 /******************************************************************************
00002    STDR Simulator - Simple Two DImensional Robot Simulator
00003    Copyright (C) 2013 STDR Simulator
00004    This program is free software; you can redistribute it and/or modify
00005    it under the terms of the GNU General Public License as published by
00006    the Free Software Foundation; either version 3 of the License, or
00007    (at your option) any later version.
00008    This program is distributed in the hope that it will be useful,
00009    but WITHOUT ANY WARRANTY; without even the implied warranty of
00010    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00011    GNU General Public License for more details.
00012    You should have received a copy of the GNU General Public License
00013    along with this program; if not, write to the Free Software Foundation,
00014    Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301  USA
00015    
00016    Authors : 
00017    * Manos Tsardoulias, etsardou@gmail.com
00018    * Aris Thallas, aris.thallas@gmail.com
00019    * Chris Zalidis, zalidis@gmail.com 
00020 ******************************************************************************/
00021 
00022 #include "stdr_gui/stdr_map_loader.h"
00023 
00024 namespace stdr_gui
00025 {
00032   CMapLoader::CMapLoader(int argc, char **argv):
00033     argc_(argc),
00034     argv_(argv)
00035   {
00036     setupUi(this);
00037     internal_img_ = new QImage(100,100,QImage::Format_RGB32);
00038     map_min_ = QPoint(0,0);
00039     map_max_ = QPoint(0,0);
00040     zoom_ = 0;
00041   }
00042   
00048   void CMapLoader::resizeEvent(QResizeEvent *e)
00049   {
00050     updateImage(internal_img_);
00051   }
00052   
00059   std::pair<int,int> CMapLoader::checkDimensions(int w,int h)
00060   {
00061     float containerWidth = this->width();
00062     float containerHeight = this->height();
00063     float aspectRatio = (float)w / (float)h;
00064     float finalW,finalH;
00065     if(containerHeight * aspectRatio > containerWidth)
00066     {
00067       finalW = containerWidth;
00068       finalH = containerWidth / aspectRatio;
00069     }
00070     else
00071     {
00072       finalW = containerHeight * aspectRatio;
00073       finalH = containerHeight;
00074     }
00075     return std::pair<int,int>(finalW,finalH);
00076   }
00077   
00083   void CMapLoader::updateImage(QImage *img)
00084   {
00085     internal_img_ = img;
00086     std::pair<int,int> newDims = checkDimensions(img->width(),img->height());
00087     
00088     map->setPixmap(
00089       QPixmap().fromImage(
00090         (*img).
00091           copy(map_min_.x(),
00092               map_min_.y(),
00093               map_max_.x() - map_min_.x(),
00094               map_max_.y() - map_min_.y()).
00095           scaled(newDims.first,newDims.second,
00096               Qt::IgnoreAspectRatio,
00097               Qt::SmoothTransformation)));
00098           
00099     map->resize(newDims.first,newDims.second);
00100   }
00101   
00108   void CMapLoader::drawGrid(QImage *img,float resolution)
00109   {
00110     QPainter painter(img);
00111     painter.setPen(QColor(100,100,100,150));
00112     int pix = 1.0 / resolution;
00113     for(unsigned int i = 1 ; i <= img->width() / pix + 1 ; i++)
00114     {
00115       painter.drawLine(0, i * pix, img->width() - 1, i * pix);
00116     }
00117     for(unsigned int i = 1 ; i <= img->height() / pix + 1 ; i++)
00118     {
00119       painter.drawLine(i * pix, 0, i * pix, img->height() - 1);
00120     }
00121   }
00122   
00129   void CMapLoader::updateZoom(QPoint p,bool zoomIn)
00130   {
00131     QPoint np = getGlobalPoint(p);
00132     np.setY(internal_img_->height() - np.y());
00133     int prevZoom = zoom_;
00134     if(zoomIn)
00135     {
00136       zoom_++;
00137     }
00138     else 
00139     {
00140       zoom_--;
00141     }
00142     if(zoom_ < 0)
00143     {
00144       zoom_ = 0;
00145       return;
00146     }
00147     float intW = internal_img_->width();
00148     float intH = internal_img_->height();
00149     float newWidth = internal_img_->width() / pow(ZOOM_RATIO,zoom_);
00150     float newHeight = internal_img_->height() / pow(ZOOM_RATIO,zoom_);
00151     QPoint evOriginal = np;
00152     
00153     float xmin,xmax,ymin,ymax;
00154     float prevxmin, prevymin, prevWidth, prevHeight;
00155     prevxmin = map_min_.x();
00156     prevymin = map_min_.y();
00157     prevWidth = map_max_.x() - map_min_.x();
00158     prevHeight = map_max_.y() - map_min_.y();
00159     float xhit = evOriginal.x();
00160     float yhit = evOriginal.y();
00161 
00162     xmin = xhit - (xhit - prevxmin) * newWidth / prevWidth;
00163     xmax = xmin + newWidth ;
00164     ymin = yhit - (yhit - prevymin) * newHeight / prevHeight;
00165     ymax = ymin + newHeight;
00166     
00167     if(xmin < 0)
00168     {
00169       xmax += - xmin;
00170       xmin = 0;
00171     }
00172     else if(xmax > internal_img_->width() - 1)
00173     {
00174       xmin -= xmax - internal_img_->width() + 1;
00175       xmax = internal_img_->width() - 1;
00176     }
00177     if(ymin < 0)
00178     {
00179       ymax += - ymin;
00180       ymin = 0;
00181     }
00182     else if(ymax > internal_img_->height() - 1)
00183     {
00184       ymin -= ymax - internal_img_->height() + 1;
00185       ymax = internal_img_->height() - 1;
00186     }
00187     map_min_ = QPoint(xmin,ymin);
00188     map_max_ = QPoint(xmax,ymax);
00189   }
00190   
00196   void CMapLoader::moveDirectionally(int key)
00197   {
00198     int xcenter = (map_max_.x() + map_min_.x()) / 2; 
00199     int ycenter = (map_max_.y() + map_min_.y()) / 2; 
00200     QPoint p(xcenter, ycenter);
00201     //~ float move_by = (map_max_.x() - map_min_.x()) / 10.0;
00202     float move_by = 50;
00203     
00204     switch(key)
00205     {
00206       case Qt::Key_Right:
00207         p.setX(p.x() + move_by);
00208         break;
00209       case Qt::Key_Left:
00210         p.setX(p.x() - move_by);
00211         break;
00212       case Qt::Key_Up:
00213         p.setY(p.y() - move_by);
00214         break;
00215       case Qt::Key_Down:
00216         p.setY(p.y() + move_by);
00217         break;
00218       default:
00219         return;
00220     }
00221     updateCenter(p);
00222   }
00223   
00224   
00230   void CMapLoader::updateCenter(QPoint p)
00231   {
00232     
00233     float intW = internal_img_->width();
00234     float intH = internal_img_->height();
00235     float newWidth = internal_img_->width() / pow(ZOOM_RATIO,zoom_);
00236     float newHeight = internal_img_->height() / pow(ZOOM_RATIO,zoom_);
00237     QPoint evOriginal = p;
00238     //~ evOriginal.setY(internal_img_->height() - evOriginal.y());
00239     
00240     float xmin,xmax,ymin,ymax;
00241     xmin = evOriginal.x() - newWidth / 2;
00242     xmax = evOriginal.x() + newWidth / 2;
00243     ymin = evOriginal.y() - newHeight / 2;
00244     ymax = evOriginal.y() + newHeight / 2;
00245     if(xmin < 0)
00246     {
00247       xmax += - xmin;
00248       xmin = 0;
00249     }
00250     else if(xmax > internal_img_->width() - 1)
00251     {
00252       xmin -= xmax - internal_img_->width() + 1;
00253       xmax = internal_img_->width() - 1;
00254     }
00255     if(ymin < 0)
00256     {
00257       ymax += - ymin;
00258       ymin = 0;
00259     }
00260     else if(ymax > internal_img_->height() - 1)
00261     {
00262       ymin -= ymax - internal_img_->height() + 1;
00263       ymax = internal_img_->height() - 1;
00264     }
00265     map_min_ = QPoint(xmin,ymin);
00266     map_max_ = QPoint(xmax,ymax);
00267   }
00268   
00274   QPoint CMapLoader::pointUnscaled(QPoint p)
00275   {
00276     QPoint newPoint;
00277     float x = p.x();
00278     float y = p.y();
00279     float initialWidth = internal_img_->width();
00280     float currentWidth = map->width();
00281     //~ ROS_ERROR("InitialW, CurrW : %f %f",initialWidth,currentWidth);
00282     float climax = initialWidth / currentWidth;
00283     newPoint.setX(x * climax);
00284     newPoint.setY(y * climax);
00285     return newPoint;
00286   }
00287   
00292   void CMapLoader::resetZoom(void)
00293   {
00294     zoom_ = 0;
00295     map_min_ = QPoint(0,0);
00296     map_max_ = QPoint(internal_img_->width() - 1,internal_img_->height() - 1);
00297   }
00298     
00304   QPoint CMapLoader::getGlobalPoint(QPoint p){
00305     //~ ROS_ERROR("Robot place set (loader) : %d %d",p.x(),p.y());
00306     QPoint np = pointUnscaled(p);
00307     //~ ROS_ERROR("Robot place set (unscaled): %d %d",np.x(),np.y());
00308     int xev = np.x() / pow(ZOOM_RATIO,zoom_) + map_min_.x();
00309     int yev = np.y() / pow(ZOOM_RATIO,zoom_) + map_min_.y();
00310     //~ ROS_ERROR("Robot place set (unzoomed): %d %d",xev,yev);
00311     return QPoint(xev,internal_img_->height() - yev);
00312   }
00313   
00319   void CMapLoader::setInitialImageSize(QSize s)
00320   {
00321     initial_image_size_ = s;
00322     map_min_ = QPoint(0, 0);
00323     map_max_ = QPoint(s.width(), s.height());
00324   }
00325 }


stdr_gui
Author(s): Manos Tsardoulias
autogenerated on Thu Jun 6 2019 18:57:38