1 /*=========================================================================
2 
3   Program:   Visualization Toolkit
4   Module:    vtkImplicitCylinderWidget.h
5 
6   Copyright (c) Ken Martin, Will Schroeder, Bill Lorensen
7   All rights reserved.
8   See Copyright.txt or http://www.kitware.com/Copyright.htm for details.
9 
10      This software is distributed WITHOUT ANY WARRANTY; without even
11      the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
12      PURPOSE.  See the above copyright notice for more information.
13 
14 =========================================================================*/
15 /**
16  * @class   vtkImplicitCylinderWidget
17  * @brief   3D widget for manipulating an infinite cylinder
18  *
19  * This 3D widget defines an infinite cylinder that can be
20  * interactively placed in a scene. The widget is assumed to consist
21  * of four parts: 1) a cylinder contained in a 2) bounding box, with a
22  * 3) cylinder axis, which is rooted at a 4) center point in the bounding
23  * box. (The representation paired with this widget determines the
24  * actual geometry of the widget.)
25  *
26  * To use this widget, you generally pair it with a vtkImplicitCylinderRepresentation
27  * (or a subclass). Various options are available for controlling how the
28  * representation appears, and how the widget functions.
29  *
30  * @par Event Bindings:
31  * By default, the widget responds to the following VTK events (i.e., it
32  * watches the vtkRenderWindowInteractor for these events):
33  * <pre>
34  * If the cylinder axis is selected:
35  *   LeftButtonPressEvent - select normal
36  *   LeftButtonReleaseEvent - release (end select) normal
37  *   MouseMoveEvent - orient the normal vector
38  * If the center point (handle) is selected:
39  *   LeftButtonPressEvent - select handle (if on slider)
40  *   LeftButtonReleaseEvent - release handle (if selected)
41  *   MouseMoveEvent - move the center point (constrained to plane or on the
42  *                    axis if CTRL key is pressed)
43  * If the cylinder is selected:
44  *   LeftButtonPressEvent - select cylinder
45  *   LeftButtonReleaseEvent - release cylinder
46  *   MouseMoveEvent - increase/decrease cylinder radius
47  * If the outline is selected:
48  *   LeftButtonPressEvent - select outline
49  *   LeftButtonReleaseEvent - release outline
50  *   MouseMoveEvent - move the outline
51  * If the keypress characters are used
52  *   'Down/Left' Move cylinder away from viewer
53  *   'Up/Right' Move cylinder towards viewer
54  * In all the cases, independent of what is picked, the widget responds to the
55  * following VTK events:
56  *   MiddleButtonPressEvent - move the cylinder
57  *   MiddleButtonReleaseEvent - release the cylinder
58  *   RightButtonPressEvent - scale the widget's representation
59  *   RightButtonReleaseEvent - stop scaling the widget
60  *   MouseMoveEvent - scale (if right button) or move (if middle button) the widget
61  * </pre>
62  *
63  * @par Event Bindings:
64  * Note that the event bindings described above can be changed using this
65  * class's vtkWidgetEventTranslator. This class translates VTK events
66  * into the vtkImplicitCylinderWidget's widget events:
67  * <pre>
68  *   vtkWidgetEvent::Select -- some part of the widget has been selected
69  *   vtkWidgetEvent::EndSelect -- the selection process has completed
70  *   vtkWidgetEvent::Move -- a request for widget motion has been invoked
71  *   vtkWidgetEvent::Up and vtkWidgetEvent::Down -- MoveCylinderAction
72  * </pre>
73  *
74  * @par Event Bindings:
75  * In turn, when these widget events are processed, the vtkImplicitCylinderWidget
76  * invokes the following VTK events on itself (which observers can listen for):
77  * <pre>
78  *   vtkCommand::StartInteractionEvent (on vtkWidgetEvent::Select)
79  *   vtkCommand::EndInteractionEvent (on vtkWidgetEvent::EndSelect)
80  *   vtkCommand::InteractionEvent (on vtkWidgetEvent::Move)
81  * </pre>
82  *
83  *
84  * @sa
85  * vtk3DWidget vtkImplicitPlaneWidget
86  */
87 
88 #ifndef vtkImplicitCylinderWidget_h
89 #define vtkImplicitCylinderWidget_h
90 
91 #include "vtkAbstractWidget.h"
92 #include "vtkInteractionWidgetsModule.h" // For export macro
93 
94 class vtkImplicitCylinderRepresentation;
95 
96 class VTKINTERACTIONWIDGETS_EXPORT vtkImplicitCylinderWidget : public vtkAbstractWidget
97 {
98 public:
99   /**
100    * Instantiate the object.
101    */
102   static vtkImplicitCylinderWidget* New();
103 
104   ///@{
105   /**
106    * Standard vtkObject methods
107    */
108   vtkTypeMacro(vtkImplicitCylinderWidget, vtkAbstractWidget);
109   void PrintSelf(ostream& os, vtkIndent indent) override;
110   ///@}
111 
112   /**
113    * Specify an instance of vtkWidgetRepresentation used to represent this
114    * widget in the scene. Note that the representation is a subclass of vtkProp
115    * so it can be added to the renderer independent of the widget.
116    */
117   void SetRepresentation(vtkImplicitCylinderRepresentation* rep);
118 
119   /**
120    * Return the representation as a vtkImplicitCylinderRepresentation.
121    */
GetCylinderRepresentation()122   vtkImplicitCylinderRepresentation* GetCylinderRepresentation()
123   {
124     return reinterpret_cast<vtkImplicitCylinderRepresentation*>(this->WidgetRep);
125   }
126 
127   /**
128    * Create the default widget representation if one is not set.
129    */
130   void CreateDefaultRepresentation() override;
131 
132 protected:
133   vtkImplicitCylinderWidget();
134   ~vtkImplicitCylinderWidget() override = default;
135 
136   // Manage the state of the widget
137   int WidgetState;
138   enum _WidgetState
139   {
140     Start = 0,
141     Active
142   };
143 
144   // These methods handle events
145   static void SelectAction(vtkAbstractWidget*);
146   static void TranslateAction(vtkAbstractWidget*);
147   static void ScaleAction(vtkAbstractWidget*);
148   static void EndSelectAction(vtkAbstractWidget*);
149   static void MoveAction(vtkAbstractWidget*);
150   static void MoveCylinderAction(vtkAbstractWidget*);
151   static void TranslationAxisLock(vtkAbstractWidget*);
152   static void TranslationAxisUnLock(vtkAbstractWidget*);
153 
154   /**
155    * Update the cursor shape based on the interaction state. Returns 1
156    * if the cursor shape requested is different from the existing one.
157    */
158   int UpdateCursorShape(int interactionState);
159 
160 private:
161   vtkImplicitCylinderWidget(const vtkImplicitCylinderWidget&) = delete;
162   void operator=(const vtkImplicitCylinderWidget&) = delete;
163 };
164 
165 #endif
166