last update 20 Sep 2009 |
00001 /* 00002 * Copyright (C) 1998-2005 00003 * Lehrstuhl fuer Technische Informatik, RWTH-Aachen, Germany 00004 * 00005 * 00006 * This file is part of the Computer Vision and Robotics Library (CVR-Lib) 00007 * 00008 * The CVR-Lib is free software; you can redistribute it and/or 00009 * modify it under the terms of the BSD License. 00010 * 00011 * All rights reserved. 00012 * 00013 * Redistribution and use in source and binary forms, with or without 00014 * modification, are permitted provided that the following conditions are met: 00015 * 00016 * 1. Redistributions of source code must retain the above copyright notice, 00017 * this list of conditions and the following disclaimer. 00018 * 00019 * 2. Redistributions in binary form must reproduce the above copyright notice, 00020 * this list of conditions and the following disclaimer in the documentation 00021 * and/or other materials provided with the distribution. 00022 * 00023 * 3. Neither the name of the authors nor the names of its contributors may be 00024 * used to endorse or promote products derived from this software without 00025 * specific prior written permission. 00026 * 00027 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" 00028 * AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 00029 * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE 00030 * ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE 00031 * LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR 00032 * CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF 00033 * SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS 00034 * INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN 00035 * CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) 00036 * ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE 00037 * POSSIBILITY OF SUCH DAMAGE. 00038 */ 00039 00040 00041 /** 00042 * \file cvrViewerBase.h 00043 * Contains the abstract base class for all CVR-Lib viewers. 00044 * \author Pablo Alvarado 00045 * \date 05.01.2005 00046 * 00047 * revisions ..: $Id: cvrViewerBase.h,v 1.9 2007/10/18 05:05:48 alvarado Exp $ 00048 */ 00049 00050 #ifndef _CVR_VIEWER_BASE_H_ 00051 #define _CVR_VIEWER_BASE_H_ 00052 00053 #include "cvrParametersManager.h" 00054 #include "cvrMutex.h" 00055 #include "cvrSemaphore.h" 00056 #include "cvrPoint.h" 00057 00058 namespace cvr { 00059 /** 00060 * Class viewerBase. 00061 * 00062 * Abstract class, parent for all CVR-Lib viewers. 00063 00064 * It provides some basic interfacing that all viewers must support. 00065 * The management of the viewer parameters is also provided here 00066 * (similar to the functor concept). 00067 * 00068 * The architecture of the class tree is supposed to support a strong 00069 * encapsulation of the GUI toolkit specifics, which won't be found here, 00070 * but in the internal (here still undefined) classes 'tk', which are 00071 * defined in the files corresponding to the toolkit (like 00072 * cvrViewerBaseGtk.h) 00073 */ 00074 class viewerBase : public ioObject, 00075 public status, 00076 public parametersManager { 00077 public: 00078 /** 00079 * Interaction events recognized by the interface 00080 */ 00081 enum eInteractionType { 00082 Idle=0, /**< No interaction reported */ 00083 KeyPressed, /**< Key Pressed */ 00084 KeyReleased, /**< Key Released */ 00085 ButtonPressed, /**< Mouse Button Pressed */ 00086 ButtonReleased, /**< Mouse Button Released */ 00087 MouseMoved, /**< Mouse Pointer Moved */ 00088 Closed /**< Window has been closed */ 00089 }; 00090 00091 /** 00092 * Mouse button symbols 00093 */ 00094 enum eMouseButton { 00095 NoButton =0, /**< No button pressed */ 00096 LeftButton =1, /**< Left mouse button */ 00097 MiddleButton=2, /**< Middle mouse button */ 00098 RightButton =4, /**< Right mouse button */ 00099 WheelUp =8, /**< Mouse wheel turned up */ 00100 WheelDown =16, /**< Mouse wheel turned down */ 00101 OtherButton =32 /**< Any other mouse button */ 00102 }; 00103 00104 /** 00105 * Key Modifiers. 00106 * This flags can be combined with the bitwise logic operators. 00107 */ 00108 enum eKeyModifiers { 00109 NoModifier = 0, /**< No modifier */ 00110 ShiftKey = 1, /**< Shift key */ 00111 CtrlKey = 2, /**< Control key */ 00112 AltKey = 4 /**< Alternate key */ 00113 }; 00114 00115 /** 00116 * Interaction structure 00117 * 00118 * An interaction of the user with the main window is usually 00119 * given through the mouse or the keyboard. The key or mouse 00120 * button pressed, the modifiers used (e.g. shift, alt or ctrl 00121 * keys) and the kind of interaction (mouse or keyboard) are 00122 * packed in objects of this type. 00123 */ 00124 struct interaction { 00125 /** 00126 * Type of interaction 00127 */ 00128 eInteractionType action; 00129 00130 /** 00131 * Key or mouse button pressed (or released). 00132 */ 00133 int key; 00134 00135 /** 00136 * Modifiers used (shift, ctrl or alt). 00137 */ 00138 int modifiers; 00139 00140 /** 00141 * Default constructor initializes with right-button press action 00142 */ 00143 interaction(); 00144 00145 /** 00146 * Constructor that initialize the structure with default values 00147 */ 00148 interaction(const eInteractionType action, 00149 const int k, 00150 const int m); 00151 00152 00153 /** 00154 * Compare with the interaction type, which is an usual operation. 00155 */ 00156 inline bool operator==(const eInteractionType ia) const { 00157 return (action == ia); 00158 } 00159 00160 /** 00161 * Compare with the interaction type, which is an usual operation. 00162 */ 00163 inline bool operator!=(const eInteractionType ia) const { 00164 return (action != ia); 00165 } 00166 00167 /** 00168 * Compare with the interaction type, which is an usual operation. 00169 */ 00170 inline bool operator==(const interaction& ia) const { 00171 return ((action == ia.action) && 00172 (key == ia.key) && 00173 (modifiers == ia.modifiers)); 00174 } 00175 00176 /** 00177 * Compare with the interaction type, which is an usual operation. 00178 */ 00179 inline bool operator!=(const interaction& ia) const { 00180 return ((action != ia.action) || 00181 (key != ia.key) || 00182 (modifiers != ia.modifiers)); 00183 } 00184 00185 }; 00186 // end of struct interaction 00187 00188 /** 00189 * Parameters of the cvr::viewerBase class. 00190 * 00191 * There are parameters related with the GUI, for example which 00192 * interaction type starts the config dialog, the position and 00193 * size of the window, etc. There are other parameters related 00194 * with the visualization of the data, which are defined in the 00195 * functors that do the painting jobs for the viewers 00196 * (e.g. cvr::viewer1DPainter.h, cvr::viewer2DPainter.h, 00197 * cvr::viewer3DPainter.h). This functionality separation permits 00198 * to use the painters without the GUI interfaces, in case the 00199 * user wants to provide the same viewer abilities in his own GUI. 00200 * The functors of the derived viewers will have parameters that 00201 * inherit from this class and from the painters as well. 00202 * 00203 * possible solution: the gui parameters follow, and they DO NOT 00204 * inherit from functor. The other parameters can be found in the 00205 * derived viewer classes so that their parameters can inherit 00206 * from the current parameters AND from the painter functors' parameters. 00207 * 00208 * This way, the viewers can make use of the functors using their 00209 * own parameters, but a painter's parameters alone makes no sense here. 00210 */ 00211 class parameters : virtual public parametersManager::parameters { 00212 public: 00213 00214 /** 00215 * Default constructor 00216 */ 00217 parameters(); 00218 00219 /** 00220 * Copy constructor 00221 */ 00222 parameters(const parameters& other); 00223 00224 /** 00225 * Destructor 00226 */ 00227 virtual ~parameters(); 00228 00229 /** 00230 * Copy data of "other" parameters 00231 */ 00232 parameters& copy(const parameters& other); 00233 00234 /** 00235 * Returns the name of this class 00236 */ 00237 virtual const std::string& name() const = 0; 00238 00239 /** 00240 * Returns a pointer to a clone of the parameters. 00241 */ 00242 virtual parameters* clone() const = 0; 00243 00244 /** 00245 * Returns a pointer to a clone of the parameters. 00246 */ 00247 virtual parameters* newInstance() const = 0; 00248 00249 00250 /** 00251 * Write the parameters in the given ioHandler 00252 * @param handler the ioHandler to be used 00253 * @param complete if true (the default) the enclosing begin/end will 00254 * be also written, otherwise only the data block will be written. 00255 * @return true if write was successful 00256 */ 00257 virtual bool write(ioHandler& handler, 00258 const bool complete=true) const; 00259 00260 /** 00261 * Read the parameters from the given ioHandler 00262 * @param handler the ioHandler to be used 00263 * @param complete if true (the default) the enclosing begin/end will 00264 * be also written, otherwise only the data block will be written. 00265 * @return true if write was successful 00266 */ 00267 virtual bool read(ioHandler& handler,const bool complete=true); 00268 00269 00270 protected: 00271 /** 00272 * Copy data of "other" parameters 00273 */ 00274 parameters& operator=(const parameters& other); 00275 00276 public: 00277 // 00278 // Attributes 00279 // 00280 00281 /** 00282 * Title for the main window 00283 */ 00284 std::string title; 00285 00286 /** 00287 * What must happen in order to activate the configuration dialog. 00288 * 00289 * Default value: {ButtonPressed,RightButton,NoModifier} 00290 */ 00291 interaction actionForConfig; 00292 00293 /** 00294 * Position of the window. 00295 * 00296 * Default value: (0,0) 00297 */ 00298 ipoint position; 00299 00300 /** 00301 * Size of the window in pixels. 00302 * 00303 * The size corresponds to the display area, which is a little bit 00304 * smaller (depending on theme, window manager, etc.) than the whole 00305 * size of the viewer window. 00306 * 00307 * If you give negative values here, the size will be automatically set. 00308 * 00309 * Default value: (-1,-1) 00310 */ 00311 ipoint size; 00312 }; 00313 // end of class parameters 00314 00315 /** 00316 * Information block 00317 * 00318 * This is the parent class for all information blocks used to transmit 00319 * some data to the configuration dialogs, which are to be displayed in a 00320 * read-only manner. 00321 * 00322 * It has a simplified interface if compared with cvr::object 00323 */ 00324 class information { 00325 public: 00326 /** 00327 * Default constructor 00328 */ 00329 information(); 00330 00331 /** 00332 * Copy constructor 00333 */ 00334 information(const information& other); 00335 00336 /** 00337 * Virtual destructor 00338 */ 00339 virtual ~information(); 00340 00341 /** 00342 * Copy method 00343 */ 00344 information& copy(const information& other); 00345 00346 /** 00347 * Clone 00348 */ 00349 virtual information* clone() const = 0; 00350 }; 00351 // end of class information 00352 00353 /** 00354 * @name Interaction functions. 00355 * 00356 * The interaction activity with the viewer is not considered to 00357 * alter its state. So you can have a constant viewer (for 00358 * example, you give the viewer as const argument to a method, 00359 * where the viewer already shows something) and make some 00360 * interaction with it. You can query for interaction with the 00361 * viewer without problems. 00362 */ 00363 //@{ 00364 /** 00365 * The most complete interaction function reports almost anything. 00366 * 00367 * @param action interaction object where all information about 00368 * key/button, modifiers and type of interaction is stored. 00369 * @param position position where the mouse was clicked 00370 * @param onlyIfValid if true, this method waits until the mouse 00371 * pointer and focus of the window lies on the main viewer window. 00372 * If false, only the focus is required to report any interaction 00373 * @return true if an interaction took place, false if the function returns 00374 * due to the destruction of the viewer object (for example, the 00375 * user closed the window). 00376 */ 00377 virtual bool waitInteraction(interaction& action, 00378 ipoint& position, 00379 const bool onlyIfValid = true) const; 00380 00381 00382 /** 00383 * Waits until a mouse button is pressed. 00384 * 00385 * @param action interaction object where all information about 00386 * key/button, modifiers and type of interaction is stored. 00387 * @param position position where the mouse was clicked 00388 * @param onlyIfValid if true, this method waits until the mouse 00389 * pointer and focus of the window lies on the main viewer window. 00390 * If false, only the focus is required to report any interaction 00391 * @return true if an interaction took place, false if the function returns 00392 * due to the destruction of the viewer object (for example, the 00393 * user closed the window). 00394 */ 00395 virtual bool waitButtonPressed(interaction& action, 00396 ipoint& position, 00397 const bool onlyIfValid = true) const; 00398 00399 /** 00400 * Waits until a mouse button is released. 00401 * 00402 * @param action interaction object where all information about 00403 * key/button, modifiers and type of interaction is stored. 00404 * @param position position where the mouse was clicked 00405 * @param onlyIfValid if true, this method waits until the mouse 00406 * pointer and focus of the window lies on the main viewer window. 00407 * If false, only the focus is required to report any interaction 00408 * @return true if an interaction took place, false if the function returns 00409 * due to the destruction of the viewer object (for example, the 00410 * user closed the window). 00411 */ 00412 virtual bool waitButtonReleased(interaction& action, 00413 ipoint& position, 00414 const bool onlyIfValid = true) const; 00415 00416 /** 00417 * Waits until a keyboard key is pressed. 00418 * 00419 * \b Note. This get triggered for key down and for key up. In a loop that 00420 * executes quickly and uses waitKey() to stop for viewing after each 00421 * iteration you might get the impression that two steps are taken at 00422 * once. This is because iteration time is faster than the time it takes 00423 * to lift the finger. Consider using waitKeyPressed instead. 00424 * 00425 * @param action interaction object where all information about 00426 * key/button, modifiers and type of interaction is stored. 00427 * @return true if an interaction took place, false if the function returns 00428 * due to the destruction of the viewer object (for example, the 00429 * user closed the window). 00430 */ 00431 virtual bool waitKey(interaction& action); 00432 00433 /** 00434 * Waits until a keyboard key is pressed down. 00435 * 00436 * @param action interaction object where all information about 00437 * key/button, modifiers and type of interaction is stored. 00438 * @return true if an interaction took place, false if the function returns 00439 * due to the destruction of the viewer object (for example, the 00440 * user closed the window). 00441 */ 00442 virtual bool waitKeyPressed(interaction& action); 00443 00444 /** 00445 * Returns the information available about the last action 00446 */ 00447 virtual void getLastAction(interaction& action, 00448 ipoint& position) const; 00449 //@} 00450 00451 /** 00452 * Construct a viewerBase 00453 */ 00454 viewerBase(); 00455 00456 /** 00457 * Copy constructor 00458 */ 00459 viewerBase(const viewerBase& other); 00460 00461 /** 00462 * Virtual destructor 00463 */ 00464 ~viewerBase(); 00465 00466 /** 00467 * Name of the class 00468 */ 00469 virtual const std::string& name() const; 00470 00471 /** 00472 * copy all attributes of the viewerBase 00473 */ 00474 viewerBase& copy(const viewerBase& other); 00475 00476 /** 00477 * Hide the current window and all its configuration dialogs if displayed. 00478 * 00479 * @return true if window was hidden or false if it was already hidden or 00480 * it has not been shown up yet. 00481 */ 00482 bool hide(); 00483 00484 /** 00485 * Update parameters 00486 * 00487 * Overload necessary to transfer some data to the corresponding windows 00488 */ 00489 virtual bool updateParameters(); 00490 00491 /** 00492 * Return current parameter's instance 00493 */ 00494 const parameters& getParameters() const; 00495 00496 protected: 00497 00498 /** 00499 * Return current parameter's instance 00500 */ 00501 parameters& getParametersRW(); 00502 00503 /** 00504 * Parent class for all configuration classes. 00505 * 00506 * The "parent" of a configuration dialog is its corresponding main window, 00507 * which is set at construction time. This way, the configuration has the 00508 * binding necessary to manage all information exchange. 00509 * 00510 * The specific configDialog instance for a viewer is indicated with the 00511 * method viewerBase::useConfig(). TODO: What to expect from the memory 00512 * management? 00513 */ 00514 class configDialog { 00515 friend class viewerBase; 00516 public: 00517 /** 00518 * Construction 00519 */ 00520 configDialog(viewerBase& parent); 00521 00522 /** 00523 * Sort of copy constructor but with a new parent 00524 */ 00525 configDialog(const configDialog& other,viewerBase& parent); 00526 00527 /** 00528 * Destruction 00529 */ 00530 virtual ~configDialog(); 00531 00532 /** 00533 * Use the given information block. 00534 * 00535 * This method does not copy the information block, it just stores a 00536 * reference to the given instance. 00537 * 00538 * Inherited methods should call this one and transfer all data in the 00539 * information block to the GUI elements. 00540 */ 00541 virtual bool useInformation(const information* dataInfo); 00542 00543 /** 00544 * Use the given information block. 00545 * 00546 * This method does not copy the information block, it just stores a 00547 * reference to the given instance, but it overtakes the memory 00548 * management. 00549 * 00550 * The implementation of this method is based on useInformation(), so 00551 * that you may want to overload just that method. 00552 */ 00553 virtual bool attachInformation(const information* dataInfo); 00554 00555 /** 00556 * Get a read-only reference to the data block 00557 */ 00558 const information& getInformation() const; 00559 00560 /** 00561 * Check if an information block has been assigned or not 00562 */ 00563 bool validInformation() const; 00564 00565 /** 00566 * Set a copy of the given parameters. 00567 * 00568 * Here at the base class this method just set-ups the pointer 00569 * making a copy of the given parameters. 00570 * 00571 * Inherited classes have to set also the GUI elements of the 00572 * configuration dialog to the corresponding parameters. 00573 */ 00574 virtual bool setParameters(const parameters& par); 00575 00576 /** 00577 * Get read-only reference to the internal parameters 00578 */ 00579 const parameters& getParameters() const; 00580 00581 /** 00582 * Get a writable reference to the internal parameters 00583 */ 00584 parameters& getParameters(); 00585 00586 /** 00587 * Get the internal copy of the parameters and eliminate the internal 00588 * reference. 00589 */ 00590 parameters* detachParameters(); 00591 00592 /** 00593 * @name Toolkit dependent functions 00594 */ 00595 //@{ 00596 /** 00597 * Constructs the main window. 00598 * 00599 * You usually don't need to call this method directly, as 00600 * it is called by show() if necessary. 00601 * 00602 * This is called just once for the configuration dialog at its 00603 * construction time. 00604 * 00605 * In inherited classes it is usually employed to build the basic 00606 * structure of the configuration dialog 00607 */ 00608 virtual bool build(); 00609 00610 /** 00611 * Show the configuration dialog 00612 */ 00613 virtual bool show(); 00614 00615 /** 00616 * Hides the configuration dialog 00617 */ 00618 virtual bool hide(); 00619 00620 /** 00621 * Destroys the widget completely. 00622 * 00623 * Before the widget is destroyed, the window is hidden, and the 00624 * parent viewer is signalized accordingly in order to destroy 00625 * the configuration dialog. 00626 */ 00627 virtual bool destroy(); 00628 //@} 00629 00630 /** 00631 * Copy method. 00632 * 00633 * Copies everything, but the parent main window 00634 */ 00635 configDialog& copy(const configDialog& other); 00636 00637 /** 00638 * This clone requires the parent window 00639 */ 00640 virtual configDialog* clone(viewerBase& parent) const; 00641 00642 private: 00643 /** 00644 * Data block. 00645 * 00646 * The memory block is managed by the class and corresponds to the 00647 * meta information about the data being displayed. 00648 */ 00649 const information* data_; 00650 00651 /** 00652 * Flag of data ownership 00653 * 00654 * This flag is true if data_ belongs to this class, or false if 00655 * it is just a reference to some external data. 00656 */ 00657 bool ownsData_; 00658 00659 protected: 00660 /** 00661 * Reference to the parent viewer 00662 */ 00663 viewerBase* parent_; 00664 00665 /** 00666 * Parameters of the configuration dialog. They are a copy of the 00667 * given parameters, and they have to be removed by this class. 00668 */ 00669 parameters* params_; 00670 00671 /** 00672 * Private class used to contain all internals based on each specific 00673 * widget toolkit 00674 */ 00675 class tk; 00676 00677 /** 00678 * The toolkit instance created only at construction time through the 00679 * initToolkit() method and destroyed in the destructor through the 00680 * destroyToolkit() method. 00681 */ 00682 mutable tk* tk_; 00683 00684 /** 00685 * Initialize toolkit dependent class 00686 * 00687 * This is called at construction time but is implemented by the 00688 * toolkit being used. 00689 */ 00690 virtual void initToolkit(); 00691 00692 /** 00693 * Destroy toolkit dependent class 00694 * 00695 * This is called at destruction time and is implemented by the 00696 * toolkit being used. 00697 */ 00698 virtual void destroyToolkit(); 00699 00700 /** 00701 * Virtual function called when the user clicks the cancel button 00702 */ 00703 virtual bool onCancelButtonClicked(); 00704 00705 /** 00706 * Virtual function called when the user clicks the apply button 00707 */ 00708 virtual bool onApplyButtonClicked(); 00709 00710 /** 00711 * Virtual function called when the user clicks the ok button 00712 */ 00713 virtual bool onOkButtonClicked(); 00714 00715 /** 00716 * Disable operator= 00717 */ 00718 configDialog& operator=(const configDialog& other); 00719 }; 00720 00721 /** 00722 * Parent class of all main windows. 00723 */ 00724 /* Maybe with the proper interfacing we don't need more main windows: 00725 * it just need to display given 2D data in a window (plain drawing). 00726 * 00727 * The question is: should we take care of partial zooming or we leave 00728 * that task the toolkit: 00729 * Since I have had the problem of huge zoomed images, taking care of the 00730 * zoom is a good idea, but much more work. 00731 * 00732 * The other thing is what should be made available for 3D viewers: 00733 * for this I need to check of 3D libraries (VTK was not good) or just 00734 * create our own framework: 00735 * 00736 * 3D points / lines / triangles / polygons / delauney triangulation 00737 * faces / objects / scenes / cameras / coordinate systems. 00738 * 00739 * Since the focus is on vision, we don't really need the more 00740 * complex issues. 00741 * 00742 * On the other hand, checking for other libraries and making the CVR-Lib 00743 * structures compatible with them saves lots of work and let those other 00744 * people do a better dedicated job on the visualization and 3D analysis. 00745 * 00746 * Pros: perfect matching with other CVR-Lib functors 00747 * Contras: a HUGE LOT of work. 00748 * 00749 * In other words: since it is not really known what is to be 00750 * drawn on this window, the interface has to be very general. 00751 */ 00752 class mainWindow { 00753 friend class viewerBase; 00754 00755 public: 00756 00757 /** 00758 * Create an "empty" window. 00759 * 00760 * The constructor creates just the object, without interacting 00761 * with the GUI, to save some time (maybe the users still do not 00762 * want to show any data. This is the one and only constructor 00763 * and requires to know who is the parent viewer, in order to 00764 * make possible the communication with it. 00765 */ 00766 mainWindow(viewerBase& parent); 00767 00768 /** 00769 * Copy constructor. 00770 * 00771 * This makes a deep copy except of the parent, which has to be 00772 * given explicitely. 00773 */ 00774 mainWindow(const mainWindow& other,viewerBase& parent); 00775 00776 /** 00777 * Destructor 00778 */ 00779 virtual ~mainWindow(); 00780 00781 /** 00782 * Clone 00783 * 00784 * A new mainWindow is created with everything identical to the current 00785 * one expect for the parent viewer, which has to be given explicitely 00786 */ 00787 virtual mainWindow* clone(viewerBase& parent) const; 00788 00789 /** 00790 * Get information hold by the viewerBase 00791 */ 00792 const information& getInformation() const; 00793 00794 /** 00795 * @name Toolkit dependent functions 00796 */ 00797 //@{ 00798 /** 00799 * Constructs the main window. 00800 * 00801 * You usually don't need to call this method directly, as 00802 * it is called by show() if necessary. 00803 * 00804 * This is called just once for a viewer. 00805 */ 00806 virtual bool build(); 00807 00808 /** 00809 * Shows the main window. 00810 * 00811 * If it is not constructed yet, then the main window is constructed. 00812 */ 00813 virtual bool show(); 00814 00815 /** 00816 * Hides the main window 00817 */ 00818 virtual bool hide(); 00819 00820 /** 00821 * Destroys the widget completely. 00822 * 00823 * Before the widget is destroyed, the window is hidden, and the 00824 * parent viewer is signalized accordingly in order to destroy 00825 * the configuration dialog. 00826 */ 00827 virtual bool destroy(); 00828 00829 /** 00830 * Display in the status bar the given text 00831 */ 00832 virtual bool statusBar(const std::string& txt); 00833 00834 /** 00835 * Resize canvas. 00836 * 00837 * Update the size of the area used to display data. 00838 * 00839 * The "canvas" may receive different names in different toolkits. 00840 * In the GTK implementation is a gtk-drawing-area, but QT and Windows 00841 * might use other similar names. 00842 * 00843 * The canvas is usually as big the the image being displayed or as the 00844 * largest possible projection plane in rendering 3D scenes. 00845 */ 00846 virtual bool setCanvasSize(const ipoint& newSize); 00847 //@} 00848 00849 /** 00850 * Return the by now registered canvas size. 00851 * 00852 * This method does not return the real canvas size, but an internal 00853 * value stored the las time the canvas size was changed. 00854 */ 00855 virtual const ipoint& getCanvasSize() const; 00856 00857 /** 00858 * Compute the new canvas size. 00859 * 00860 * Nothing but the computation of the "optimal" size has to be in an 00861 * overloaded method. The setCanvasSize() method decides if the change 00862 * takes place or not. 00863 */ 00864 virtual ipoint computeCanvasSize() const; 00865 00866 /** 00867 * Keyboard/Mouse slot. 00868 * 00869 * Virtual function called by the toolkit when there is some 00870 * sort of interaction with the main window. This function then 00871 * calls parentViewer.setKMInteraction() with the appropriate 00872 * parameters and checks if it is the key/button configuration 00873 * that starts the configuration dialog. 00874 */ 00875 virtual bool onKMInteraction(const interaction& action, 00876 const ipoint& position); 00877 00878 /** 00879 * Called when the main window was closed. 00880 * 00881 * The default implementation just generates the proper 00882 * event (for waitInteration()) and hides everything. 00883 */ 00884 virtual bool closeWindow(); 00885 00886 /** 00887 * Change the parameters being used. 00888 * 00889 * This method is implemented in the toolkit dependent part, as 00890 * it is the toolkit the one that knows how to set all parameters. 00891 * 00892 * Note that the given reference can/will be modified by the toolkit, 00893 * since the user can change the geometry of the window, and that will 00894 * be reflected in the parameters. 00895 */ 00896 virtual bool updateParameters(parameters& params); 00897 00898 /** 00899 * Get a read-only reference to the parameters 00900 */ 00901 const viewerBase::parameters& getParameters() const; 00902 00903 protected: 00904 00905 /** 00906 * Private class used to contain all internals for a specific 00907 * widget toolkit 00908 */ 00909 class tk; 00910 00911 /** 00912 * The toolkit instance created only at construction time and 00913 * destroyed in the destructor. 00914 */ 00915 mutable tk* tk_; 00916 00917 /** 00918 * Initialize toolkit dependent class 00919 * 00920 * This is called at construction time but is implemented by the 00921 * toolkit being used. 00922 */ 00923 virtual void initToolkit(); 00924 00925 /** 00926 * Destroy toolkit dependent class 00927 * 00928 * This is called at destruction time and is implemented by the 00929 * toolkit being used. 00930 */ 00931 virtual void destroyToolkit(); 00932 00933 /** 00934 * Disable operator= 00935 */ 00936 mainWindow& operator=(const mainWindow& other); 00937 00938 /** 00939 * Reference to the parent window 00940 */ 00941 viewerBase* parent_; 00942 00943 /** 00944 * Parameters of the viewer 00945 */ 00946 parameters* params_; 00947 00948 /** 00949 * Last hint about the size of the canvas, i.e. the area which 00950 * is going to be used by the used toolkit to display the information 00951 */ 00952 ipoint canvasSize_; 00953 }; 00954 // end of class mainWindow 00955 00956 private: 00957 /** 00958 * Function called by the main window if the user interacts with it. 00959 * 00960 * It takes care of the semaphore management to coordinate with the 00961 * waitInteraction() and similar methods. 00962 */ 00963 bool setKMInteraction(const interaction& action, 00964 const ipoint& position); 00965 00966 protected: 00967 /** 00968 * Determine if the given position is valid 00969 */ 00970 virtual bool validPosition(const ipoint& position) const; 00971 00972 /** 00973 * Mouse/Keyboard interaction handler. 00974 * 00975 * This virtual function can be completely overriden and is called each 00976 * time some interaction with the main window occurs. The default 00977 * behaviour is to display the position of the mouse pointer within the 00978 * window in the status bar. 00979 * 00980 * Usually, derived classes override this method to intercept the 00981 * interaction used to display some information under the mouse pointer. 00982 */ 00983 virtual bool onKMInteraction(const interaction& action, 00984 const ipoint& position); 00985 00986 /** 00987 * Return a read-only reference to the configuration dialog 00988 */ 00989 const configDialog& getConfigDialog() const; 00990 00991 /** 00992 * Return a writable reference to the configuration dialog 00993 */ 00994 configDialog& getConfigDialog(); 00995 00996 /** 00997 * Give the configuration dialog to be used. 00998 * 00999 * The memory management is responsibility of the user. 01000 * @see setConfig() 01001 */ 01002 virtual bool useConfig(configDialog* dlg); 01003 01004 /** 01005 * Give the configuration dialog to be used. 01006 * 01007 * The memory management is taken from the user. 01008 * @see useConfig() 01009 */ 01010 virtual bool attachConfig(configDialog* dlg); 01011 01012 /** 01013 * Function called if the configuration dialog is to be shown. 01014 * 01015 * The derived classes have to set the data of the configuration dialog 01016 */ 01017 virtual bool showConfig(); 01018 01019 /** 01020 * Function called if the user pressed "apply" or "ok" on the configuration 01021 * dialog, which is normally used to apply all changes in the dialog 01022 * parameters to the displayed data. 01023 * 01024 * 01025 * @param keepConfigData if true, the configuration dialog has to 01026 * keep its data, which is desired when "apply" is 01027 * pressed. 01028 * if false, the parameters won't be copied, but 01029 * just transfered to the viewer. 01030 */ 01031 virtual bool updateFromConfig(const bool keepConfigData); 01032 01033 /** 01034 * Function called if for some reason the configuration dialog has to 01035 * be hidden. 01036 */ 01037 virtual bool hideConfig(); 01038 01039 /** 01040 * Ensure that a main window of the proper type has been created. 01041 * 01042 * @return true if a new mainWindow instance was created or false if 01043 * it already existed. 01044 */ 01045 virtual bool ensureMainWindow(); 01046 01047 /** 01048 * Returns true if the mainWindow has been set. 01049 */ 01050 bool validMainWindow() const; 01051 01052 /** 01053 * Return the main window as read-only reference. 01054 * 01055 * This will throw an assertion if the mainWindow has not been set yet. 01056 */ 01057 const mainWindow& getMainWindow() const; 01058 01059 /** 01060 * Return the main window as reference. 01061 * 01062 * This will throw an assertion if the mainWindow has not been set yet. 01063 */ 01064 mainWindow& getMainWindow(); 01065 01066 /** 01067 * Set mainWindow 01068 * 01069 * Exactly the pointed object will be utilized, without copying it, and 01070 * the memory management is assumed to be done by the user himself. 01071 * 01072 * @see attachMainWindow 01073 * 01074 * @return true if the new object was simply assigned, or false if a 01075 * previous object had to be removed first. 01076 */ 01077 bool useMainWindow(mainWindow* newWnd); 01078 01079 /** 01080 * Set mainWindow 01081 * 01082 * Exactly the pointed object will be utilized, without copying it, and the 01083 * memory management is taken from the user. 01084 * 01085 * @warning The user should never remove the given instance. 01086 * 01087 * @see useMainWindow() 01088 * 01089 * @return true if the new object was simply assigned, or false if a 01090 * previous object had to be removed first. 01091 */ 01092 bool attachMainWindow(mainWindow* newWnd); 01093 01094 /** 01095 * Returns true if the information block has been set or false otherwise 01096 */ 01097 bool validInformation() const; 01098 01099 /** 01100 * Make a copy of the given information block and store it internally. 01101 * 01102 */ 01103 bool setInformation(const information& info); 01104 01105 /** 01106 * Get a read-only reference to the internal information block. 01107 * 01108 * This can return a wrong reference. You should check validInformation() 01109 * first. 01110 */ 01111 const information& getInformation() const; 01112 01113 /** 01114 * This virtual method is called just before the configuration dialog 01115 * is to be displayed, in order to update the information block to the 01116 * data being processed. 01117 */ 01118 virtual bool updateInformation(); 01119 01120 /** 01121 * Get a writable reference to the internal information block 01122 * 01123 * This can return a wrong reference. You should check validInformation() 01124 * first. 01125 */ 01126 information& getInformation(); 01127 01128 01129 private: 01130 /** 01131 * Pointer to the main window 01132 */ 01133 mainWindow* mainWnd_; 01134 01135 /** 01136 * Flag for ownership of the mainWindow 01137 */ 01138 bool ownsMainWnd_; 01139 01140 /** 01141 * Pointer to the main window 01142 */ 01143 configDialog* configDlg_; 01144 01145 /** 01146 * Flag for ownership of the configDlg_ 01147 */ 01148 bool ownsConfigDlg_; 01149 01150 /** 01151 * Pointer to used information block 01152 */ 01153 information* info_; 01154 01155 /** 01156 * Flag for ownership of the information block 01157 */ 01158 bool ownsInfo_; 01159 01160 /** 01161 * Disable operator= until it is implemented 01162 */ 01163 viewerBase& operator=(const viewerBase& other); 01164 01165 /** 01166 * Protect access to flags for interaction 01167 */ 01168 mutable mutex lock_; 01169 01170 /** 01171 * Flag that indicates if the viewer is waiting for some user interaction 01172 */ 01173 mutable bool waitingInteraction_; 01174 01175 /** 01176 * Semaphore that counts the number of threads that are waiting for 01177 * a user interaction. 01178 */ 01179 mutable semaphore kmSem_; 01180 01181 /** 01182 * Bitwise combination of the used modifiers (see eKeyModifiers) 01183 */ 01184 int modifiers_; 01185 01186 /** 01187 * Key pressed 01188 */ 01189 int key_; 01190 01191 /** 01192 * Mouse button pressed 01193 */ 01194 eMouseButton button_; 01195 01196 /** 01197 * Position where the button/key were pressed 01198 */ 01199 ipoint pos_; 01200 01201 /** 01202 * Last interaction type reported 01203 */ 01204 eInteractionType action_; 01205 01206 }; 01207 01208 // two global io functions 01209 bool read(ioHandler& handler, 01210 viewerBase::interaction& obj, 01211 bool complete=true); 01212 bool write(ioHandler& handler, 01213 const viewerBase::interaction& obj, 01214 bool complete=true); 01215 } 01216 01217 #endif