00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038 #ifndef TwoHalfDSketch_H_DEFINED
00039 #define TwoHalfDSketch_H_DEFINED
00040
00041 #include "Image/OpenCVUtil.H"
00042 #include "Util/Types.H"
00043 #include "Image/Image.H"
00044 #include "Image/ImageSet.H"
00045 #include "Image/Pixels.H"
00046 #include "Image/Layout.H"
00047 #include "FeatureMatching/OriChamferMatching.H"
00048 #include "plugins/SceneUnderstanding/V2.H"
00049 #include "plugins/SceneUnderstanding/Contours.H"
00050 #include "plugins/SceneUnderstanding/Regions.H"
00051 #include "plugins/SceneUnderstanding/CornersFeatures.H"
00052 #include "plugins/SceneUnderstanding/SMap.H"
00053 #include "Simulation/SimEvents.H"
00054 #include "Simulation/SimModule.H"
00055 #include "GUI/ViewPort3D.H"
00056
00057 #include <vector>
00058 #include <string>
00059
00060 class SimEventTwoHalfDSketchPrior;
00061
00062 #define INVALID_PROB -1e10
00063
00064 class TwoHalfDSketch : public SimModule
00065 {
00066 public:
00067
00068 struct SurfaceState
00069 {
00070 Point2D<float> pos;
00071 Point2D<float> pos2;
00072 float a;
00073 float b;
00074 float e;
00075 float k1;
00076 float k2;
00077 float rot;
00078 float start;
00079 float end;
00080 double prob;
00081 int gibs;
00082 double scale;
00083 Point2D<float> aspect;
00084 Point2D<float> shear;
00085 float matchingScale;
00086 Polygon polygon;
00087
00088
00089 SurfaceState () :
00090 prob(INVALID_PROB)
00091 {}
00092
00093
00094
00095 Line getLine(uint idx)
00096 {
00097 ASSERT(idx < polygon.getNumLines());
00098
00099 Line l = polygon.getLine(idx);
00100 l.trans(pos);
00101 l.scale(1.0/matchingScale);
00102 return l;
00103 }
00104
00105
00106 Point2D<double> getPos()
00107 {
00108 return pos*(1.0/matchingScale);
00109 }
00110
00111
00112 Rectangle getBB()
00113 {
00114 Rectangle bb;
00115
00116 if(polygon.getNumLines() > 1)
00117 {
00118
00119 Line l = getLine(0);
00120 Point2D<int> p1 = (Point2D<int>)l.getP1();
00121 int minX=p1.i;
00122 int minY=p1.j;
00123 int maxX=minX;
00124 int maxY=minY;
00125 for(uint i=0;i<polygon.getNumLines();i++)
00126 {
00127 Line l = getLine(i);
00128 Point2D<int> p1 = (Point2D<int>)l.getP1();
00129 if(p1.i < minX) minX = p1.i;
00130 if(p1.j < minY) minY = p1.j;
00131 if(p1.i > maxX) maxX = p1.i;
00132 if(p1.j > maxY) maxY = p1.j;
00133
00134 Point2D<int> p2 = (Point2D<int>)l.getP2();
00135 if(p2.i < minX) minX = p2.i;
00136 if(p2.j < minY) minY = p2.j;
00137 if(p2.i > maxX) maxX = p2.i;
00138 if(p2.j > maxY) maxY = p2.j;
00139 }
00140
00141 bb = Rectangle::tlbrI(minY,minX,maxY,maxX);
00142 }
00143 return bb;
00144 }
00145 };
00146
00147
00148 void findMax(const Image<SurfaceState>& src, Point2D<int>& p, SurfaceState& maxval)
00149 {
00150 ASSERT(src.initialized());
00151 Image<SurfaceState>::const_iterator aptr = src.begin();
00152 const int w = src.getWidth(), h = src.getHeight();
00153 p.i = 0; p.j = 0; maxval = *aptr;
00154 for (int j = 0; j < h; j ++)
00155 for (int i = 0; i < w; i ++)
00156 {
00157 if (aptr->prob > maxval.prob) { maxval = *aptr; p.i = i; p.j = j; }
00158 aptr++;
00159 }
00160 }
00161
00162 void drawDisk(Image<SurfaceState>& dst, const Point2D<int>& center,
00163 const int radius)
00164 {
00165 if (radius == 1)
00166 {
00167 if (dst.coordsOk(center)) dst.setVal(center.i + dst.getWidth() * center.j, SurfaceState());
00168 return;
00169 }
00170
00171 for (int y = -radius; y <= radius; ++y)
00172 {
00173 int bound = int(sqrtf(float(squareOf(radius) - squareOf(y))));
00174 for (int x = -bound; x <= bound; ++x)
00175 if (dst.coordsOk(x + center.i, y + center.j))
00176 dst.setVal(x + center.i, y + center.j, SurfaceState());
00177 }
00178 }
00179
00180 Image<float> getProbImage(const Image<SurfaceState>& src)
00181 {
00182 Image<float> probImg(src.getDims(), NO_INIT);
00183 ASSERT(src.initialized());
00184
00185 for(uint i=0; i<src.size(); i++)
00186 probImg[i] = src[i].prob;
00187
00188 return probImg;
00189 }
00190
00191
00192
00193 TwoHalfDSketch(OptionManager& mgr, const std::string& descrName = "TwoHalfDSketch",
00194 const std::string& tagName = "TwoHalfDSketch");
00195
00196
00197 ~TwoHalfDSketch();
00198
00199 void evolve(SimEventQueue& q);
00200
00201 Layout<PixRGB<byte> > getDebugImage(SimEventQueue& q);
00202
00203
00204 double calcNFA(Line& line);
00205
00206 void drawSurface(const SurfaceState& surface);
00207
00208
00209 Image<SurfaceState> proposeSurfaces(bool biasMode);
00210 void calcSurfaceLikelihood(SurfaceState& surface);
00211 double calcSurfaceEdgeLikelihood(SurfaceState& surface, Image<float>& edges, Image<float>& surfaceLum);
00212 double getEdgeProb(Point2D<int> loc, float ori);
00213
00214 double calcSurfaceLumLikelihood(SurfaceState& surface, Image<float>& edges, Image<float>& surfaceLum);
00215 double getSurfaceLumProb(Image<float>& data, Image<float>& model);
00216 Image<PixRGB<byte> > getSurfaceImage(const SurfaceState& surface);
00217
00218 double getLineProb(Point2D<int> p1, Point2D<int> p2, float ori, int& pixCount);
00219
00220 double getCost(OriChamferMatching& lm, Polygon& poly,Point2D<float> loc, bool biasMode = false);
00221
00222 Image<float> getSurfaceProbImage(Image<SurfaceState>& surfaceState);
00223
00224
00225 void printResults(float bias);
00226
00227 void optimizePolygon(SurfaceState& surfaceState);
00228
00229 double nfa(int n, int k, double p, double logNT);
00230 int isaligned(Point2D<int> loc, Image<float>& angles, float theta, float prec);
00231 double log_gamma_windschitl(double x);
00232 double log_gamma_lanczos(double x);
00233
00234 typedef struct
00235 {
00236 float vx[4];
00237 float vy[4];
00238 float ys,ye;
00239 int x,y;
00240 } rect_iter;
00241
00242 struct rect
00243 {
00244 float x1,y1,x2,y2;
00245 float width;
00246 float x,y;
00247 float theta;
00248 float dx,dy;
00249 float prec;
00250 double p;
00251 float sum;
00252 };
00253
00254
00255 float inter_low(float x, float x1, float y1, float x2, float y2);
00256 float inter_hi(float x, float x1, float y1, float x2, float y2);
00257 void ri_del(rect_iter * iter);
00258 int ri_end(rect_iter * i);
00259 void ri_inc(rect_iter * i);
00260 rect_iter * ri_ini(struct rect * r);
00261
00262
00263
00264 protected:
00265
00266 SIMCALLBACK_DECLARE(TwoHalfDSketch, SimEventV2Output);
00267
00268 SIMCALLBACK_DECLARE(TwoHalfDSketch, SimEventContoursOutput);
00269
00270
00271 SIMCALLBACK_DECLARE(TwoHalfDSketch, SimEventSaveOutput);
00272
00273
00274 SIMCALLBACK_DECLARE(TwoHalfDSketch, SimEventUserInput);
00275
00276
00277 OModelParam<bool> itsShowDebug;
00278
00279
00280 private:
00281 Image<PixRGB<byte> > itsCurrentFrame;
00282 Image<float> itsLinesMag;
00283 Image<float> itsLinesOri;
00284 Image<float> itsEdgesDT;
00285 ImageSet<float> itsOriEdgesDT;
00286 Image<byte> itsSMap;
00287 std::vector<V2::LineSegment> itsLines;
00288 std::vector<Contours::Contour> itsContours;
00289 std::vector<CornersFeatures::CornerState> itsCorners;
00290 std::vector<SurfaceState> itsSurfaces;
00291 std::vector<SurfaceState> itsProposals;
00292 SurfaceState itsUserProposal;
00293 Polygon itsModel;
00294 OriChamferMatching itsOriChamferMatcher;
00295 double itsProposalThreshold;
00296 double itsAcceptedThreshold;
00297 Image<float> itsProposalsProb;
00298 Image<float> itsProposalsIdxs;
00299 float itsCurrentProb;
00300 uint itsCurrentIdx;
00301 bool itsBiasMode;
00302 float itsBias;
00303 int itsBiasId;
00304
00305 };
00306
00307
00308 class SimEventTwoHalfDSketchOutput : public SimEvent
00309 {
00310 public:
00311 SimEventTwoHalfDSketchOutput(SimModule* src,
00312 std::vector<TwoHalfDSketch::SurfaceState>& surfaces) :
00313 SimEvent(src), itsSurfaces(surfaces)
00314 {}
00315
00316 virtual ~SimEventTwoHalfDSketchOutput(){}
00317 std::vector<TwoHalfDSketch::SurfaceState> getSurfaces() { return itsSurfaces; }
00318
00319 private:
00320 const std::vector<TwoHalfDSketch::SurfaceState>& itsSurfaces;
00321 };
00322
00323
00324
00325
00326
00327
00328
00329
00330
00331 #endif //