Home || Architecture || Video Search || Visual Search || Scripts || Applications || Important Messages || OGL || Src

ShotDetailSidebar.h

Go to the documentation of this file.
00001 #ifndef Impala_Visualization_GUI_ShotDetailSidebar_h
00002 #define Impala_Visualization_GUI_ShotDetailSidebar_h
00003 
00004 /*
00005  * This defines a small shot detail pane, as used in the MN6
00006  * GoldenDemo Investigator's Dashboard application.
00007  *
00008  * Author: Ork de Rooij
00009  * Code cleanup: R. van Balen
00010  */
00011 #include "Core/VideoSet/SegmentationDocument.h"
00012 #include "Core/VideoSet/Stills.h"
00013 #include "Core/Trec/VisualQueryEngine.h"
00014 #include "Core/Trec/ThreadSet.h"
00015 
00016 #include "OglGui/Button.h"
00017 #include "OglGui/Strut.h"
00018 #include "OglGui/TextEdit.h"
00019 
00020 #include "Visualization/GUI/KeyframeResultBar.h"
00021 
00022 namespace Impala {
00023 namespace Visualization {
00024 namespace GUI {
00025 
00026 using namespace Impala::Core::Trec;
00027 
00028 class ShotDetailSidebarListener
00029 {
00030 public:
00031     virtual void
00032     QueryVisualEvent(String visname, int keyframe)
00033     {
00034     }
00035 };
00036 
00037 
00038 class ShotDetailSidebar : public OglGui::Window, 
00039                           public KeyframeResultBarListener
00040 {
00041 public:
00042     typedef Visualization::View                     View;
00043     typedef Core::Array::Array2dVec3UInt8           Array2dVec3UInt8;
00044     typedef Core::Array::Array2dScalarUInt8         Array2dScalarUInt8;
00045     typedef Core::VideoSet::SegmentationDocument    SegmentationDocument;
00046     typedef Core::VideoSet::Segmentation            Segmentation;
00047     typedef std::list<Thread*>                      ThreadList;
00048 
00049     ShotDetailSidebar(OglGui::Window *parent, int w, int h,
00050                       int thumbW, int thumbH, ThreadSet *threadset,
00051                       SegmentationDocument* segDoc) :
00052         OglGui::Window(parent, w, h, true)
00053     {
00054         Init(thumbW, thumbH, threadset, segDoc);
00055     }
00056 
00057     ShotDetailSidebar(OglGui::Window *parent, int x, int y, int w, int h,
00058                      int thumbW, int thumbH, ThreadSet *threadset,
00059                      SegmentationDocument* segDoc) :
00060         OglGui::Window(parent, x, y, w, h, true)
00061     {
00062         Init(thumbW, thumbH, threadset, segDoc);
00063     }
00064 
00065     virtual ~ShotDetailSidebar()
00066     {
00067         // RvB: 3-2-2009 OGL automatically cleans up. Now illegal here
00068         // RemovePreviewBars();
00069         if (mShotPreviewImage)
00070             delete mShotPreviewImage;
00071     }
00072 
00073     void Update()
00074     {
00075         UpdateCurrentShot();
00076     }
00077 
00078     void SetShowSimilarity(bool similarity)
00079     {
00080         mShowPreviewBars = similarity;
00081     }
00082 
00083     bool GetShowSimilarity()
00084     {
00085         return mShowPreviewBars;
00086     }
00087 
00088     void SetListener(ShotDetailSidebarListener *listener)
00089     {
00090         mSidebarListener = listener;
00091     }
00092 
00093     virtual void
00094     KeyframeSelectedEvent(String name, int selectedkeyframe)
00095     {
00096         if (!mSidebarListener) return;
00097 
00098         int shot = mSegDoc->CurShot();
00099         int keyframe = mThreadSet->GetKeyframes()->GetShotRKF(shot);
00100         mSidebarListener->QueryVisualEvent(name, keyframe);
00101     }
00102 
00103 private:
00104 
00105     void Init(int thumbW, int thumbH, ThreadSet *threadset,
00106               SegmentationDocument* segDoc)
00107     {
00108         mThreadSet         = threadset;
00109         mSegDoc            = segDoc;
00110         mThumbWidth        = (thumbW / 4) * 3;
00111         mThumbHeight       = (thumbH / 4) * 3;
00112         mShotPreviewView   = NULL;
00113         mSidebarListener   = NULL;
00114         mShotPreviewImage  = NULL;
00115         mShowPreviewBars   = false;
00116         mPrecalcResults    = 20;
00117 
00118         mVisualQueryEngine = new VisualQueryEngine(mThreadSet, mPrecalcResults);
00119 
00120         mStills = new Core::VideoSet::Stills(segDoc->GetVideoSet(), "stills");
00121 
00122         int xpos, ypos, xwid, ywid;
00123         int labelBackColor = oglTrLIGHTGREY;
00124 
00125         xwid = mThumbWidth + 4;
00126         ywid = mThumbHeight + 4;
00127         xpos = (WndWidth() - xwid) / 2;
00128         ypos = WndHeight() - 6;
00129         mShotPreview = new Window(this, xpos, ypos-ywid, xwid, ywid, true);
00130         mShotPreview->ConnectTo(this, L2L|R2R|T2T|B2T);
00131 
00132         xpos = 2;
00133         ypos -= ywid + 6;
00134         xwid = WndWidth() - 4;
00135         ywid = 20;
00136         StaticText* labelStills =
00137             new StaticText(this, xpos, ypos-ywid, xwid, ywid, "Shot samples:");
00138         labelStills->ConnectTo(this, T2T|B2T);
00139         labelStills->SetBackground(labelBackColor);
00140 
00141         xpos = 2;
00142         ypos -= ywid + 1;
00143         xwid = WndWidth() - 4;
00144         ywid = (int)(mThumbHeight / 3.0f) + 20;
00145         mShotKeyframes = new Window(this, xpos, ypos-ywid, xwid, ywid, true);
00146         mShotKeyframes->ConnectTo(this, L2L|R2R|T2T|B2T);
00147 
00148         xpos = 2;
00149         ypos -= ywid + 8;
00150         xwid = WndWidth() - 4;
00151         ywid = 20;
00152         StaticText* labelDetails =
00153             new StaticText(this, xpos, ypos-ywid, xwid, ywid, "Information:");
00154         labelDetails->ConnectTo(this, T2T|B2T);
00155         labelDetails->SetBackground(labelBackColor);
00156 
00157         xpos = 2;
00158         ypos -= ywid + 1;
00159         xwid = WndWidth() - 4;
00160         ywid = 88;
00161         mShotDetailText = new OglGui::TextEdit(this, xpos, ypos-ywid, xwid,
00162                                                ywid, "Shot details here", 0);
00163         mShotDetailText->Editable(false);
00164         mShotDetailText->SetBackground(0);
00165         mShotDetailText->SetBorderType(0);
00166         mShotDetailText->ConnectTo(this, L2L|R2R|T2T|B2T);
00167 
00168         xpos = 2;
00169         ypos -= ywid + 1;
00170         xwid = WndWidth() - 4;
00171         ywid = 20;
00172         StaticText* labelSimilars =
00173             new StaticText(this, xpos, ypos-ywid, xwid, ywid, "Similarity:");
00174         labelSimilars->ConnectTo(this, T2T|B2T);
00175         labelSimilars->SetBackground(labelBackColor);
00176 
00177         xpos = 2;
00178         ypos -= ywid + 1;
00179         xwid = WndWidth() - 4;
00180         ywid = ypos - 4;
00181         mShotSimilarityPreview = new Window(this,xpos,ypos-ywid,xwid,ywid,true);
00182         mShotSimilarityPreview->ConnectTo(this, ALLSIDES);
00183 
00184         mSetFramesShown = mShotKeyframes->WndWidth() / (int)(thumbW/3.0f) + 1;
00185         mSetFrames = new Visualization::ImageSet(mShotKeyframes,thumbW, thumbH,
00186                                                  0.33, mSetFramesShown, 1);
00187         mSetFrames->SetMakeViewWithRect(true);
00188         mSetFrames->ActivateInfoBox(false);
00189         //mSetFrames->SetImagesListener(this, 0);
00190     }
00191 
00192     void UpdateCurrentShot()
00193     {
00194         if (mSegDoc == NULL || !mSegDoc->HasCurShot())
00195         {
00196             ILOG_WARN("UpdateCurrentShot() trying to update, " <<
00197                       "but no current shot found.");
00198             return;
00199         }
00200 
00201         int shotid = mSegDoc->CurShot();
00202 
00203         // steps:
00204         //  1. retrieve RKF, place in mShotPreview
00205         //  2. retrieve series of keyframes for shot, place in mShotKeyframes
00206         //  3. generate textual information for shot, place in mShotDetails
00207         //  4. retrieve forms of similarity, place in mShotSimilarityPreview
00208 
00209         // STEP 1
00210         ILOG_DEBUG("ShotDetailWindow::UpdateCurrentShot()");
00211 
00212         if (mShotPreviewView == NULL && mShotPreview)
00213         {
00214             OGLWND *oglWnd = mShotPreview->GetOGLWND();
00215             mShotPreviewView = new View(oglWnd,3,3,mThumbWidth,mThumbHeight,1.0,
00216                                         false,false,true,NULL);
00217         }
00218 
00219         if (mShotPreviewImage)
00220         {
00221             delete mShotPreviewImage;
00222             mShotPreviewImage = 0;
00223         }
00224 
00225         mShotPreviewImage = mThreadSet->GetImageByShotID(shotid);
00226         if (mShotPreviewImage == NULL)
00227         {
00228             ILOG_WARN("ShotDetailView::SetShot() could not retrieve RKF for " <<
00229                       shotid);
00230             mShotPreviewImage = 0;
00231             return;
00232         }
00233         mShotPreviewView->UpdateImage(mShotPreviewImage, "Direct");
00234         // STEP 2
00235         UpdateStills();
00236         // STEP 3
00237         UpdateDescription();
00238         // STEP 4
00239         UpdatePreviewBars();
00240     }
00241 
00242     void UpdateStills()
00243     {
00244         if (mSetFrames == NULL)
00245             return;
00246 
00247         mSetFrames->RemoveImages();
00248 
00249         Core::ImageSet::ImageSet* imSetStills = mSegDoc->GetImSetStills();
00250         if (!imSetStills)
00251             return;
00252 
00253         int shot  = mSegDoc->CurShot();
00254         int start = mStills->GetFirstStillShot(shot);
00255         int end   = start + mStills->GetNrStillsShot(shot);
00256 
00257         int totalstills = end - start;
00258         int increment   = 1;
00259         if (totalstills > mSetFramesShown)
00260             increment = totalstills / mSetFramesShown;
00261 
00262         ILOG_DEBUG("ShotDetailWindow::UpdateStills() with " << start <<
00263                    " to "<< end << " total " << totalstills << ", showing " <<
00264                    mSetFramesShown << " using inc " << increment);
00265 
00266         for (int i=start ; i<end ; i+=increment)
00267         {
00268             Array2dVec3UInt8* im = imSetStills->GetImage(i);
00269             mSetFrames->AddImage(im, String("Direct"), "", true);
00270         }
00271     }
00272 
00273     void UpdateDescription()
00274     {
00275         std::ostringstream m;
00276 
00277         Core::VideoSet::VideoSet*   vidSet = mSegDoc->GetVideoSet();
00278         Segmentation*               segm   = mSegDoc->GetSegmentation();
00279 
00280         int curShotId       = mSegDoc->CurShot();
00281         int curVideoId      = segm->GetVideoId(curShotId);
00282         int shotsInCurVideo = segm->GetNrShotsVideo(curVideoId);
00283         int start           = segm->GetStart(curShotId);
00284         int end             = segm->GetEnd(curShotId);
00285 
00286         // Ork - showing path and file crashes on my dataset -- temp removed.
00287         //String curVideoPath = vidSet->GetAsPath(curVideoId);
00288 
00289         m << "shot with ID: " << curShotId << std::endl;
00290         // assuming all shot id's for one video are consecutive:
00291         m << "is no. " << (curShotId - segm->GetFirstShotVideo(curVideoId)+1) <<
00292              " of " << shotsInCurVideo << " shots in the video" << std::endl;
00293         m << "and contains " << (end-start+1) << " frames."
00294         // RvB Added line below for debug purpose
00295         << std::endl <<"[" << vidSet->GetFile(curVideoId) << "]"
00296         << std::endl << std::endl;
00297         //m << "  frame ? of " << segm->GetNrFramesVideo(curVideoId) <<
00298         //     " frames in video" << std::endl;
00299         //m << "  shot ? of " << segm->GetNrShots() << " shots in set" <<
00300         //     std::endl;
00301         //m << "  Video " << (curVideoId + 1) << " of " << segm->GetNrVideos()<<
00302         //     " videos in set" << std::endl;
00303         //m << "file: " << vidSet->GetFile(curVideoId) << std::endl;
00304         //int posLastSep = curVideoPath.find_last_of("/");
00305         //m << "path: " << curVideoPath.substr(0, (posLastSep+1)) << std::endl;
00306 
00307         mShotDetailText->SetText(m.str());
00308     }
00309 
00310     void UpdatePreviewBars()
00311     {
00312         RemovePreviewBars();
00313         if (mShowPreviewBars)
00314             AddVisualPreviewBars();
00315     }
00316 
00317     void RemovePreviewBars()
00318     {
00319         std::list<KeyframeResultBar*>::iterator i;
00320         for (i = mPreviewBars.begin(); i != mPreviewBars.end(); i++)
00321             delete *i;
00322         mPreviewBars.clear();
00323     }
00324 
00325     void AddVisualPreviewBars()
00326     {
00327         ILOG_DEBUG("AddVisualPreviewBars()...");
00328         int shot     = mSegDoc->CurShot();
00329         int keyframe = mThreadSet->GetKeyframes()->GetShotRKF(shot);
00330         ILOG_DEBUG("SHOT: " << shot << " --> FRAME: " << keyframe);
00331 
00332         // temp fix:
00333         int     mThumbWidth  = 320;
00334         int     mThumbHeight = 240;
00335         double  mViewScale   = 0.6;
00336 
00337         ThreadList visuals = mThreadSet->GetThreadsByType(Thread::VISUAL);
00338         for (ThreadList::iterator i = visuals.begin(); i!=visuals.end(); i++)
00339         {
00340             ILOG_DEBUG("adding " << (*i)->GetName());
00341             std::list<KeyframeResult> visualresults =
00342                 mVisualQueryEngine->QueryVisual(*i, keyframe);
00343 
00344             KeyframeResultBar *kfResultBar =
00345                 new KeyframeResultBar(mShotSimilarityPreview,
00346                                       mShotSimilarityPreview->W()-2, 124,
00347                                       (*i)->GetName(), visualresults,
00348                                       mThreadSet->GetKeyframes(),
00349                                       mThreadSet->GetImageSetThumbnails(),
00350                                       mThumbWidth, mThumbHeight, 0.20);
00351             kfResultBar->SetListener(this);
00352             kfResultBar->ConnectTo(mShotSimilarityPreview);
00353             mPreviewBars.push_back(kfResultBar);
00354         }
00355         mShotSimilarityPreview->RepositionViewports();
00356         mShotSimilarityPreview->ScaleChildren(); 
00357     }
00358 
00359     // member variables:
00360     int                             mThumbWidth;
00361     int                             mThumbHeight;
00362     int                             mSetFramesShown;
00363     int                             mPrecalcResults;
00364     bool                            mShowPreviewBars;
00365 
00366     ShotDetailSidebarListener*      mSidebarListener;
00367 
00368     VisualQueryEngine*              mVisualQueryEngine;
00369     std::list<KeyframeResultBar*>   mPreviewBars;
00370     Core::VideoSet::Stills*         mStills;
00371     SegmentationDocument*           mSegDoc;
00372     ThreadSet*                      mThreadSet;
00373     Array2dVec3UInt8*               mShotPreviewImage;
00374 
00375     OglGui::Window*                 mShotPreview;
00376     OglGui::Window*                 mShotKeyframes;
00377     OglGui::Window*                 mShotSimilarityPreview;
00378     OglGui::TextEdit*               mShotDetailText;
00379 
00380     Visualization::ImageSet*        mSetFrames;
00381     Visualization::View*            mShotPreviewView;
00382 
00383     ILOG_VAR_DEC;
00384 
00385 }; // class ShotDetailSidebar
00386 
00387 ILOG_VAR_INIT(ShotDetailSidebar, Impala.Visualization.GUI);
00388 
00389 } // namespace GUI
00390 } // namespace Visualization
00391 } // namespace Impala
00392 
00393 
00394 #endif

Generated on Fri Mar 19 09:31:50 2010 for ImpalaSrc by  doxygen 1.5.1