00001 /*!@file GUI/QtImageStack.qt.C */ 00002 00003 // //////////////////////////////////////////////////////////////////// // 00004 // The iLab Neuromorphic Vision C++ Toolkit - Copyright (C) 2000-2005 // 00005 // by the University of Southern California (USC) and the iLab at USC. // 00006 // See http://iLab.usc.edu for information about this project. // 00007 // //////////////////////////////////////////////////////////////////// // 00008 // Major portions of the iLab Neuromorphic Vision Toolkit are protected // 00009 // under the U.S. patent ``Computation of Intrinsic Perceptual Saliency // 00010 // in Visual Environments, and Applications'' by Christof Koch and // 00011 // Laurent Itti, California Institute of Technology, 2001 (patent // 00012 // pending; application number 09/912,225 filed July 23, 2001; see // 00013 // http://pair.uspto.gov/cgi-bin/final/home.pl for current status). // 00014 // //////////////////////////////////////////////////////////////////// // 00015 // This file is part of the iLab Neuromorphic Vision C++ Toolkit. // 00016 // // 00017 // The iLab Neuromorphic Vision C++ Toolkit is free software; you can // 00018 // redistribute it and/or modify it under the terms of the GNU General // 00019 // Public License as published by the Free Software Foundation; either // 00020 // version 2 of the License, or (at your option) any later version. // 00021 // // 00022 // The iLab Neuromorphic Vision C++ Toolkit is distributed in the hope // 00023 // that it will be useful, but WITHOUT ANY WARRANTY; without even the // 00024 // implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR // 00025 // PURPOSE. See the GNU General Public License for more details. // 00026 // // 00027 // You should have received a copy of the GNU General Public License // 00028 // along with the iLab Neuromorphic Vision C++ Toolkit; if not, write // 00029 // to the Free Software Foundation, Inc., 59 Temple Place, Suite 330, // 00030 // Boston, MA 02111-1307 USA. // 00031 // //////////////////////////////////////////////////////////////////// // 00032 // 00033 // Primary maintainer for this file: Rob Peters <rjpeters at usc dot edu> 00034 // $HeadURL: svn://isvn.usc.edu/software/invt/trunk/saliency/src/GUI/QtImageStack.qt.C $ 00035 // $Id: QtImageStack.qt.C 12962 2010-03-06 02:13:53Z irock $ 00036 // 00037 00038 #include "GUI/QtImageStack.qt.H" 00039 00040 #include "GUI/QtImageFrame.qt.H" 00041 #include "Raster/GenericFrame.H" 00042 #include "Util/Pause.H" 00043 #include "Util/log.H" 00044 00045 #include <QtGui/QFrame> 00046 #include <QtGui/QCloseEvent> 00047 #include <QtGui/QCheckBox> 00048 #include <QtGui/QListWidget> 00049 #include <QtGui/QListWidgetItem> 00050 #include <QtGui/QSplitter> 00051 #include <QtGui/QStackedWidget> 00052 #include <QtGui/QVBoxLayout> 00053 00054 #include <vector> 00055 00056 struct QtImageStack::Impl 00057 { 00058 Impl() 00059 : 00060 pausebutton(0), 00061 listbox(0), 00062 widgstack(0), 00063 isClosed(false), 00064 frameNumber(0), 00065 entries(), 00066 preferredDims(), 00067 preferredMaxDims() 00068 {} 00069 00070 // ###################################################################### 00071 struct Entry 00072 { 00073 Entry(QListWidgetItem* listitem_, QtImageFrame* imageframe_, std::string name_) : 00074 listitem(listitem_), imageframe(imageframe_), name(name_) 00075 { } 00076 00077 QListWidgetItem* listitem; 00078 QtImageFrame* imageframe; 00079 std::string name; 00080 }; 00081 00082 // ###################################################################### 00083 Entry* findOrMakeEntry(const std::string& name) 00084 { 00085 // do we already have an Entry for this name? 00086 for (unsigned int i = 0; i < this->entries.size(); ++i) 00087 if (this->entries[i].name.compare(name) == 0) return &(this->entries[i]); // found it 00088 00089 // ok, no existing Entry, so let's set up a new one: 00090 QListWidgetItem* t = new QListWidgetItem(QString(name.c_str()), this->listbox); 00091 ////this->listbox->sortItems(); 00092 00093 QtImageFrame* f = new QtImageFrame(this->widgstack, this->preferredDims, this->preferredMaxDims); 00094 this->widgstack->addWidget(f); 00095 00096 if (this->entries.size() == 0) 00097 { 00098 this->listbox->setCurrentItem(t); 00099 this->widgstack->setCurrentWidget(f); 00100 } 00101 00102 this->entries.push_back(Impl::Entry(t, f, name)); 00103 00104 return &(this->entries.back()); 00105 } 00106 00107 // ###################################################################### 00108 void removeEntry(const std::string& name) 00109 { 00110 for (unsigned int i = 0; i < this->entries.size(); ++i) 00111 if (this->entries[i].name.compare(name) == 0) // found it 00112 { 00113 this->widgstack->removeWidget(this->entries[i].imageframe); 00114 delete this->entries[i].imageframe; 00115 delete this->entries[i].listitem; 00116 this->entries.erase(this->entries.begin() + i); 00117 return; 00118 } 00119 } 00120 00121 QCheckBox* pausebutton; 00122 QListWidget* listbox; 00123 QStackedWidget* widgstack; 00124 bool isClosed; 00125 int frameNumber; 00126 std::vector<Entry> entries; 00127 Dims preferredDims; 00128 Dims preferredMaxDims; 00129 }; 00130 00131 // ###################################################################### 00132 QtImageStack::QtImageStack(QWidget* parent) : 00133 QWidget(parent), rep(new Impl) 00134 { 00135 QVBoxLayout *main = new QVBoxLayout(this); 00136 main->setSpacing(4); 00137 00138 QHBoxLayout* buttons = new QHBoxLayout; 00139 00140 rep->pausebutton = new QCheckBox(this); 00141 rep->pausebutton->setText("Pause (click to pause)"); 00142 connect(rep->pausebutton, SIGNAL(toggled(bool)), this, SLOT(togglePause(bool))); 00143 00144 QPalette palette; 00145 palette.setColor(rep->pausebutton->foregroundRole(), QColor(96, 96, 0)); 00146 rep->pausebutton->setPalette(palette); 00147 00148 buttons->addWidget(rep->pausebutton); 00149 00150 buttons->addStretch(1); 00151 00152 main->addLayout(buttons); 00153 00154 QSplitter* splitter = new QSplitter(Qt::Horizontal, this); 00155 splitter->setChildrenCollapsible(false); 00156 00157 rep->listbox = new QListWidget(this); 00158 rep->listbox->setMinimumWidth(150); 00159 splitter->addWidget(rep->listbox); 00160 00161 rep->widgstack = new QStackedWidget(this); 00162 connect(rep->listbox, SIGNAL(currentRowChanged(int)), rep->widgstack, SLOT(setCurrentIndex(int))); 00163 splitter->addWidget(rep->widgstack); 00164 00165 splitter->setStretchFactor(0, 1); 00166 splitter->setStretchFactor(1, 7); // preferentially stretch the image pane over the text list pane 00167 00168 00169 main->addWidget(splitter); 00170 00171 this->setLayout(main); 00172 } 00173 00174 // ###################################################################### 00175 QtImageStack::~QtImageStack() 00176 { 00177 delete rep; 00178 } 00179 00180 // ###################################################################### 00181 void QtImageStack::addFrame(const GenericFrame& frame, const std::string& name, const FrameInfo& auxinfo) 00182 { 00183 Impl::Entry* e = rep->findOrMakeEntry(name); 00184 00185 ASSERT(e != 0); 00186 00187 e->imageframe->setFrame(frame, name, rep->frameNumber, auxinfo); 00188 } 00189 00190 // ###################################################################### 00191 void QtImageStack::removeFrame(const std::string& name) 00192 { 00193 rep->removeEntry(name); 00194 } 00195 00196 // ###################################################################### 00197 bool QtImageStack::setFrameNumber(int n) 00198 { 00199 rep->frameNumber = n; 00200 return true; 00201 } 00202 00203 // ###################################################################### 00204 bool QtImageStack::isClosed() const 00205 { 00206 return rep->isClosed; 00207 } 00208 00209 // ###################################################################### 00210 void QtImageStack::setPreferredDims(const Dims& dims) 00211 { 00212 rep->preferredDims = dims; 00213 } 00214 00215 // ###################################################################### 00216 void QtImageStack::setPreferredMaxDims(const Dims& dims) 00217 { 00218 rep->preferredMaxDims = dims; 00219 } 00220 00221 // ###################################################################### 00222 void QtImageStack::togglePause(bool on) 00223 { 00224 if (on) 00225 { 00226 rep->pausebutton->setText("Paused (click to resume)"); 00227 00228 QPalette palette; 00229 palette.setColor(rep->pausebutton->foregroundRole(), QColor(0, 96, 0)); 00230 rep->pausebutton->setPalette(palette); 00231 setPause(true); 00232 } 00233 else 00234 { 00235 rep->pausebutton->setText("Pause (click to pause)"); 00236 QPalette palette; 00237 palette.setColor(rep->pausebutton->foregroundRole(), QColor(96, 96, 0)); 00238 rep->pausebutton->setPalette(palette); 00239 setPause(false); 00240 } 00241 } 00242 00243 // ###################################################################### 00244 void QtImageStack::closeEvent(QCloseEvent* e) 00245 { 00246 QWidget::closeEvent(e); 00247 rep->isClosed = true; 00248 } 00249 00250 // ###################################################################### 00251 /* So things look consistent in everyone's emacs... */ 00252 /* Local Variables: */ 00253 /* mode: c++ */ 00254 /* indent-tabs-mode: nil */ 00255 /* End: */