CenterHorizontally.cpp

Go to the documentation of this file.
00001 // -*- c-basic-offset: 4 -*-
00026 #include "CenterHorizontally.h"
00027 
00028 #include <vigra/impex.hxx>
00029 #include <panodata/PanoramaData.h>
00030 #include <nona/RemappedPanoImage.h>
00031 
00032 
00033 
00034 namespace HuginBase {
00035 
00036 
00037 void CenterHorizontally::centerHorizontically(PanoramaData& panorama)
00038 {
00039     vigra::Size2D panoSize(360,180);
00040     
00041     // remap into minature pano.
00042     PanoramaOptions opts;
00043     opts.setHFOV(360);
00044     opts.setProjection(PanoramaOptions::EQUIRECTANGULAR);
00045     opts.setWidth(360);
00046     opts.setHeight(180);
00047     
00048     // remap image
00049     vigra::BImage panoAlpha(panoSize);
00050     Nona::RemappedPanoImage<vigra::BImage, vigra::BImage> remapped;
00051     
00052     // use selected images.
00053     UIntSet allActiveImgs = panorama.getActiveImages();
00054 
00055     if (allActiveImgs.size() == 0) {
00056         // do nothing if there are no images
00057         return;
00058     }
00059     
00060     //only check unlinked images
00061     UIntSet activeImgs;
00062     for (UIntSet::const_iterator it = allActiveImgs.begin(); it!= allActiveImgs.end(); it++)
00063     {
00064         const SrcPanoImage & img=panorama.getImage(*it);
00065         bool consider=true;
00066         if(img.YawisLinked())
00067         {
00068             for(UIntSet::const_iterator it2=activeImgs.begin(); it2!=activeImgs.end(); it2++)
00069             {
00070                 if(img.YawisLinkedWith(panorama.getSrcImage(*it2)))
00071                 {
00072                     consider=false;
00073                     break;
00074                 };
00075             };
00076         };
00077         if(img.getX()!=0 || img.getY()!=0 || img.getZ()!=0)
00078         {
00079             //if translation parameters are non-zero break, 
00080             //because centering by modifying yaw does not work in this case
00081             return;
00082         };
00083         if(consider)
00084             activeImgs.insert(*it);
00085     };
00086 
00087     for (UIntSet::iterator it = activeImgs.begin(); it != activeImgs.end(); ++it) {
00088         //    for (unsigned int imgNr=0; imgNr < getNrOfImages(); imgNr++) {
00089         //        const PanoImage & img = getImage(*it);
00090         //        Size2D sz(img.getWidth(), img.getHeight());
00091         //        remapped.setPanoImage(*this, *it, sz, opts);
00092         remapped.setPanoImage(panorama.getSrcImage(*it), opts, vigra::Rect2D(0,0,360,180));
00093         // calculate alpha channel
00094         remapped.calcAlpha();
00095         // copy into global alpha channel.
00096         vigra::copyImageIf(vigra_ext::applyRect(remapped.boundingBox(),
00097                                                 vigra_ext::srcMaskRange(remapped)),
00098                            vigra_ext::applyRect(remapped.boundingBox(),
00099                                                 vigra_ext::srcMask(remapped)),
00100                            vigra_ext::applyRect(remapped.boundingBox(),
00101                                                 destImage(panoAlpha)));
00102         }
00103     //    vigra::ImageExportInfo imge("c:/hugin_calcfov_alpha.png");
00104     //    exportImage(vigra::srcImageRange(panoAlpha), imge);
00105     
00106     // get field of view
00107     std::vector<int> borders;
00108     bool colOccupied = false;
00109     for (int h=0; h < 360; h++) {
00110         bool curColOccupied = false;
00111         for (int v=0; v< 180; v++) {
00112             if (panoAlpha(h,v)) {
00113                 // pixel is valid
00114                 curColOccupied = true;
00115             }
00116         }
00117         if (colOccupied && (! curColOccupied) ||
00118             (!colOccupied) && curColOccupied )
00119         {
00120             // change in position, save point.
00121             borders.push_back(h-180);
00122             colOccupied = curColOccupied;
00123         }
00124     }
00125     
00126     
00127     int lastidx = borders.size() -1;
00128     if (lastidx == -1) {
00129         // empty pano
00130         return;
00131     }
00132     
00133     if (colOccupied) {
00134         // we have reached the right border, and the pano is still valid
00135         // shift right fragments by 360 deg
00136         // |11    2222|  -> |      222211     |
00137         std::vector<int> newBorders;
00138         newBorders.push_back(borders[lastidx]);
00139         for (int i = 0; i < lastidx; i++) {
00140             newBorders.push_back(borders[i]+360);
00141         }
00142         borders = newBorders;
00143     }
00144     
00145     double dYaw=(borders[0] + borders[lastidx])/2;
00146     
00147     // apply yaw shift
00148     unsigned int nImg = panorama.getNrOfImages();
00149     for (unsigned int i=0; i < nImg; i++) {
00150         const SrcPanoImage & image = panorama.getImage(i);
00151         // only adjust yaw if we haven't already done so because of linking.
00152         bool update=true;
00153         if(image.YawisLinked())
00154         {
00155             for(unsigned int j=0; j<i; j++)
00156             {
00157                 if(image.YawisLinkedWith(panorama.getImage(j)))
00158                 {
00159                     update=false;
00160                     break;
00161                 };
00162             };
00163         };
00164         if (update)
00165         {
00166             double yaw = image.getYaw();
00167             yaw = yaw - dYaw;
00168             while (yaw < 180) {
00169                 yaw += 360;
00170             }
00171             while (yaw > 180) {
00172                 yaw -= 360;
00173             }
00174             SrcPanoImage newImage = image;
00175             newImage.setYaw(yaw);
00176             panorama.setImage(i, newImage);
00177             panorama.imageChanged(i);
00178         }
00179     }
00180 }
00181 
00182 } 

Generated on Thu Aug 21 01:25:39 2014 for Hugintrunk by  doxygen 1.3.9.1