1 /*=========================================================================
2
3 Program: Visualization Toolkit
4 Module: vtkFinitePlaneRepresentation.cxx
5
6 Copyright (c)
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 #include "vtkFinitePlaneRepresentation.h"
17
18 #include "vtkActor.h"
19 #include "vtkAssemblyPath.h"
20 #include "vtkBox.h"
21 #include "vtkCamera.h"
22 #include "vtkCellArray.h"
23 #include "vtkCellPicker.h"
24 #include "vtkConeSource.h"
25 #include "vtkDoubleArray.h"
26 #include "vtkFeatureEdges.h"
27 #include "vtkInteractorObserver.h"
28 #include "vtkLineSource.h"
29 #include "vtkMath.h"
30 #include "vtkNew.h"
31 #include "vtkObjectFactory.h"
32 #include "vtkPickingManager.h"
33 #include "vtkPolyData.h"
34 #include "vtkPolyDataMapper.h"
35 #include "vtkProperty.h"
36 #include "vtkRenderer.h"
37 #include "vtkRenderWindow.h"
38 #include "vtkRenderWindowInteractor.h"
39 #include "vtkSphereSource.h"
40 #include "vtkTransform.h"
41 #include "vtkTubeFilter.h"
42 #include "vtkWindow.h"
43
44 vtkStandardNewMacro(vtkFinitePlaneRepresentation);
45
46 //----------------------------------------------------------------------------
vtkFinitePlaneRepresentation()47 vtkFinitePlaneRepresentation::vtkFinitePlaneRepresentation()
48 {
49 // The initial state
50 this->InteractionState = vtkFinitePlaneRepresentation::Outside;
51
52 // Handle size is in pixels for this widget
53 this->HandleSize = 5.;
54
55 // Set up the initial properties
56 this->CreateDefaultProperties();
57
58 this->Origin[0] = 0.;
59 this->Origin[1] = 0.;
60 this->Origin[2] = 0.;
61
62 this->Normal[0] = 0.;
63 this->Normal[1] = 0.;
64 this->Normal[2] = 1.;
65
66 this->PreviousNormal[0] = 0.;
67 this->PreviousNormal[1] = 0.;
68 this->PreviousNormal[2] = 1.;
69 this->Transform = vtkTransform::New();
70 this->Transform->Identity();
71
72 this->V1[0] = 1.;
73 this->V1[1] = 0.;
74 this->V1[2] = 0.;
75 this->V2[0] = 0.;
76 this->V2[1] = 1.;
77 this->V2[2] = 0.;
78
79 double p1[3];
80 p1[0] = this->Origin[0] + this->V1[0];
81 p1[1] = this->Origin[1] + this->V1[1];
82 p1[2] = this->Origin[2] + this->V1[2];
83
84 double p2[3];
85 p2[0] = this->Origin[0] + this->V2[0];
86 p2[1] = this->Origin[1] + this->V2[1];
87 p2[2] = this->Origin[2] + this->V2[2];
88
89 // the origin
90 this->OriginGeometry = vtkSphereSource::New();
91 this->OriginGeometry->SetCenter(this->Origin);
92 this->OriginGeometry->Update();
93 this->OriginMapper = vtkPolyDataMapper::New();
94 this->OriginMapper->SetInputConnection(this->OriginGeometry->GetOutputPort());
95 this->OriginActor = vtkActor::New();
96 this->OriginActor->SetMapper(this->OriginMapper);
97
98 // the X Vector
99 this->V1Geometry = vtkSphereSource::New();
100 this->V1Geometry->SetCenter(p1);
101 this->V1Geometry->Update();
102 this->V1Mapper = vtkPolyDataMapper::New();
103 this->V1Mapper->SetInputConnection(this->V1Geometry->GetOutputPort());
104 this->V1Actor = vtkActor::New();
105 this->V1Actor->SetMapper(this->V1Mapper);
106
107 // the Y Vector
108 this->V2Geometry = vtkSphereSource::New();
109 this->V2Geometry->SetCenter(p2);
110 this->V2Geometry->Update();
111 this->V2Mapper = vtkPolyDataMapper::New();
112 this->V2Mapper->SetInputConnection(this->V2Geometry->GetOutputPort());
113 this->V2Actor = vtkActor::New();
114 this->V2Actor->SetMapper(this->V2Mapper);
115
116 // Create the + plane normal
117 this->LineSource = vtkLineSource::New();
118 this->LineSource->SetResolution(1);
119 this->LineMapper = vtkPolyDataMapper::New();
120 this->LineMapper->SetInputConnection(this->LineSource->GetOutputPort());
121 this->LineActor = vtkActor::New();
122 this->LineActor->SetMapper(this->LineMapper);
123
124 this->ConeSource = vtkConeSource::New();
125 this->ConeSource->SetResolution(12);
126 this->ConeSource->SetAngle(25.0);
127 this->ConeMapper = vtkPolyDataMapper::New();
128 this->ConeMapper->SetInputConnection(this->ConeSource->GetOutputPort());
129 this->ConeActor = vtkActor::New();
130 this->ConeActor->SetMapper(this->ConeMapper);
131
132 // Create the - plane normal
133 this->LineSource2 = vtkLineSource::New();
134 this->LineSource2->SetResolution(1);
135 this->LineMapper2 = vtkPolyDataMapper::New();
136 this->LineMapper2->SetInputConnection(this->LineSource2->GetOutputPort());
137 this->LineActor2 = vtkActor::New();
138 this->LineActor2->SetMapper(this->LineMapper2);
139
140 this->ConeSource2 = vtkConeSource::New();
141 this->ConeSource2->SetResolution(12);
142 this->ConeSource2->SetAngle(25.0);
143 this->ConeMapper2 = vtkPolyDataMapper::New();
144 this->ConeMapper2->SetInputConnection(this->ConeSource2->GetOutputPort());
145 this->ConeActor2 = vtkActor::New();
146 this->ConeActor2->SetMapper(this->ConeMapper2);
147
148 // The finite plane
149 this->PlanePolyData = vtkPolyData::New();
150
151 // Construct initial points
152 vtkNew<vtkPoints> points;
153 points->SetDataTypeToDouble();
154 points->SetNumberOfPoints(4);
155 this->PlanePolyData->SetPoints(points);
156 for (int i = 0; i < 4; i++)
157 {
158 points->SetPoint(i, this->Origin);
159 }
160
161 // Construct plane geometry
162 vtkNew<vtkCellArray> cell;
163 cell->Allocate(5);
164 vtkIdType pts[4] = { 0, 1, 2, 3 };
165 cell->InsertNextCell(4, pts);
166 this->PlanePolyData->SetPolys(cell);
167 this->PlanePolyData->BuildCells();
168
169 this->PlaneMapper = vtkPolyDataMapper::New();
170 this->PlaneMapper->SetInputData(this->PlanePolyData);
171 this->PlaneActor = vtkActor::New();
172 this->PlaneActor->SetMapper(this->PlaneMapper);
173
174 this->Edges = vtkFeatureEdges::New();
175 this->Edges->SetInputData(this->PlanePolyData);
176
177 this->EdgesTuber = vtkTubeFilter::New();
178 this->EdgesTuber->SetInputConnection(this->Edges->GetOutputPort());
179 this->EdgesTuber->SetNumberOfSides(12);
180 this->EdgesMapper = vtkPolyDataMapper::New();
181 this->EdgesMapper->SetInputConnection(this->EdgesTuber->GetOutputPort());
182 this->EdgesActor = vtkActor::New();
183 this->EdgesActor->SetMapper(this->EdgesMapper);
184 this->Tubing = true; //control whether tubing is on
185 this->DrawPlane = true; //control whether draw plane is on
186 this->CurrentHandle = nullptr;
187
188 // Initial creation of the widget, serves to initialize it
189 double bounds[6] = { -0.5, 0.5, -0.5, 0.5, -0.5, 0.5 };
190 this->PlaceWidget(bounds);
191
192 //Manage the picking stuff
193 this->HandlePicker = vtkCellPicker::New();
194 this->HandlePicker->SetTolerance(0.001);
195
196 this->HandlePicker->AddPickList(OriginActor);
197 this->HandlePicker->AddPickList(V1Actor);
198 this->HandlePicker->AddPickList(V2Actor);
199 this->HandlePicker->AddPickList(LineActor);
200 this->HandlePicker->AddPickList(ConeActor);
201 this->HandlePicker->AddPickList(LineActor2);
202 this->HandlePicker->AddPickList(ConeActor2);
203 this->HandlePicker->AddPickList(PlaneActor);
204
205 this->HandlePicker->PickFromListOn();
206
207 // The bounding box
208 this->BoundingBox = vtkBox::New();
209
210 this->RepresentationState = vtkFinitePlaneRepresentation::Outside;
211
212 // Pass the initial properties to the actors.
213 this->LineActor->SetProperty(this->NormalProperty);
214 this->ConeActor->SetProperty(this->NormalProperty);
215 this->LineActor2->SetProperty(this->NormalProperty);
216 this->ConeActor2->SetProperty(this->NormalProperty);
217 this->PlaneActor->SetProperty(this->PlaneProperty);
218 this->V1Actor->SetProperty(this->V1HandleProperty);
219 this->V2Actor->SetProperty(this->V2HandleProperty);
220 this->OriginActor->SetProperty(this->OriginHandleProperty);
221
222 // Internal data members for performance
223 this->TransformRotation = vtkTransform::New();
224 }
225
226 //----------------------------------------------------------------------------
~vtkFinitePlaneRepresentation()227 vtkFinitePlaneRepresentation::~vtkFinitePlaneRepresentation()
228 {
229 this->OriginGeometry->Delete();
230 this->OriginMapper->Delete();
231 this->OriginActor->Delete();
232
233 // the X Vector
234 this->V1Geometry->Delete();
235 this->V1Mapper->Delete();
236 this->V1Actor->Delete();
237
238 // the Y Vector
239 this->V2Geometry->Delete();
240 this->V2Mapper->Delete();
241 this->V2Actor->Delete();
242
243 // The + normal cone
244 this->ConeSource->Delete();
245 this->ConeMapper->Delete();
246 this->ConeActor->Delete();
247
248 // The + normal line
249 this->LineSource->Delete();
250 this->LineMapper->Delete();
251 this->LineActor->Delete();
252
253 // The - normal cone
254 this->ConeSource2->Delete();
255 this->ConeMapper2->Delete();
256 this->ConeActor2->Delete();
257
258 // The - normal line
259 this->LineSource2->Delete();
260 this->LineMapper2->Delete();
261 this->LineActor2->Delete();
262
263 // The finite plane
264 this->PlanePolyData->Delete();
265 this->PlaneMapper->Delete();
266 this->PlaneActor->Delete();
267
268 this->Edges->Delete();
269 this->EdgesTuber->Delete();
270 this->EdgesMapper->Delete();
271 this->EdgesActor->Delete();
272
273 this->BoundingBox->Delete();
274
275 this->NormalProperty->Delete();
276 this->SelectedNormalProperty->Delete();
277
278 this->HandlePicker->Delete();
279
280 this->TransformRotation->Delete();
281 this->Transform->Delete();
282
283 this->OriginHandleProperty->Delete();
284 this->V1HandleProperty->Delete();
285 this->V2HandleProperty->Delete();
286 this->SelectedHandleProperty->Delete();
287 this->PlaneProperty->Delete();
288 this->SelectedPlaneProperty->Delete();
289 }
290
291 //----------------------------------------------------------------------
GetPolyData(vtkPolyData * pd)292 void vtkFinitePlaneRepresentation::GetPolyData(vtkPolyData *pd)
293 {
294 pd->ShallowCopy(this->PlanePolyData);
295 }
296
297 //----------------------------------------------------------------------
StartWidgetInteraction(double e[2])298 void vtkFinitePlaneRepresentation::StartWidgetInteraction(double e[2])
299 {
300 // Store the start position
301 this->StartEventPosition[0] = e[0];
302 this->StartEventPosition[1] = e[1];
303 this->StartEventPosition[2] = 0.0;
304
305 // Store the start position
306 this->LastEventPosition[0] = e[0];
307 this->LastEventPosition[1] = e[1];
308 this->LastEventPosition[2] = 0.0;
309 }
310
311 //----------------------------------------------------------------------
WidgetInteraction(double e[2])312 void vtkFinitePlaneRepresentation::WidgetInteraction(double e[2])
313 {
314 // Do different things depending on state
315 // Calculations everybody does
316 double focalPoint[4], pickPoint[4], prevPickPoint[4];
317 double z, vpn[3];
318
319 vtkCamera *camera = this->Renderer->GetActiveCamera();
320 if (!camera)
321 {
322 return;
323 }
324
325 // Compute the two points defining the motion vector
326 double pos[3];
327 this->HandlePicker->GetPickPosition(pos);
328
329 vtkInteractorObserver::ComputeWorldToDisplay(
330 this->Renderer, pos[0], pos[1], pos[2], focalPoint);
331
332 z = focalPoint[2];
333 vtkInteractorObserver::ComputeDisplayToWorld(
334 this->Renderer, this->LastEventPosition[0],
335 this->LastEventPosition[1], z, prevPickPoint);
336 vtkInteractorObserver::ComputeDisplayToWorld(
337 this->Renderer, e[0], e[1], z, pickPoint);
338
339 // Process the motion
340 if (this->InteractionState == vtkFinitePlaneRepresentation::MoveOrigin)
341 {
342 this->TranslateOrigin(prevPickPoint, pickPoint);
343 }
344 else if (this->InteractionState == vtkFinitePlaneRepresentation::ModifyV1)
345 {
346 this->MovePoint1(prevPickPoint, pickPoint);
347 }
348 else if (this->InteractionState == vtkFinitePlaneRepresentation::ModifyV2)
349 {
350 this->MovePoint2(prevPickPoint, pickPoint);
351 }
352 else if (this->InteractionState == vtkFinitePlaneRepresentation::Rotating)
353 {
354 camera->GetViewPlaneNormal(vpn);
355 this->Rotate(e[0], e[1], prevPickPoint, pickPoint, vpn);
356 }
357 else if (this->InteractionState == vtkFinitePlaneRepresentation::Pushing)
358 {
359 this->Push(prevPickPoint, pickPoint);
360 }
361
362 // Store the start position
363 this->LastEventPosition[0] = e[0];
364 this->LastEventPosition[1] = e[1];
365 this->LastEventPosition[2] = 0.0;
366 }
367
368 //----------------------------------------------------------------------------
Rotate(int X,int Y,double * p1,double * p2,double * vpn)369 void vtkFinitePlaneRepresentation::Rotate(int X, int Y,
370 double *p1, double *p2, double *vpn)
371 {
372 double v[3]; //vector of motion
373 double axis[3]; //axis of rotation
374
375 // Mouse motion vector in world space
376 v[0] = p2[0] - p1[0];
377 v[1] = p2[1] - p1[1];
378 v[2] = p2[2] - p1[2];
379
380 // Create axis of rotation and angle of rotation
381 vtkMath::Cross(vpn, v, axis);
382 if (vtkMath::Normalize(axis) == 0.0)
383 {
384 return;
385 }
386 int *size = this->Renderer->GetSize();
387 double l2 = (X - this->LastEventPosition[0]) *
388 (X - this->LastEventPosition[0]) +
389 (Y - this->LastEventPosition[1]) * (Y - this->LastEventPosition[1]);
390 double theta = 360.0 * sqrt(l2 / (size[0] * size[0] + size[1] * size[1]));
391
392 //Manipulate the transform to reflect the rotation
393 this->TransformRotation->Identity();
394 this->TransformRotation->Translate(this->Origin);
395 this->TransformRotation->RotateWXYZ(theta, axis);
396 this->TransformRotation->Translate(
397 -this->Origin[0], -this->Origin[1], -this->Origin[2]);
398
399 //Set the new normal
400 double nNew[3];
401 this->TransformRotation->TransformNormal(this->Normal, nNew);
402 this->SetNormal(nNew);
403 }
404
405 //----------------------------------------------------------------------------
CreateDefaultProperties()406 void vtkFinitePlaneRepresentation::CreateDefaultProperties()
407 {
408 // Normal properties
409 this->NormalProperty = vtkProperty::New();
410 this->NormalProperty->SetColor(1.0, 1.0, 1.0);
411 this->NormalProperty->SetLineWidth(2.0);
412
413 this->SelectedNormalProperty = vtkProperty::New();
414 this->SelectedNormalProperty->SetColor(1.0, 0.0, 0.0);
415 this->NormalProperty->SetLineWidth(2.0);
416
417 // Origin Handle properties
418 this->OriginHandleProperty = vtkProperty::New();
419 this->OriginHandleProperty->SetColor(1.0, 1.0, 1.0);
420
421 // P1 Handle properties
422 this->V1HandleProperty = vtkProperty::New();
423 this->V1HandleProperty->SetColor(1.0, 0.0, 0.0);
424
425 // P2 Handle properties
426 this->V2HandleProperty = vtkProperty::New();
427 this->V2HandleProperty->SetColor(0.0, 1.0, 0.0);
428
429 this->SelectedHandleProperty = vtkProperty::New();
430 this->SelectedHandleProperty->SetColor(1.0, 1.0, 0.0);
431
432 // Plane properties
433 this->PlaneProperty = vtkProperty::New();
434 this->PlaneProperty->SetAmbient(1.0);
435 this->PlaneProperty->SetAmbientColor(1.0, 1.0, 1.0);
436 this->PlaneProperty->SetOpacity(0.5);
437
438 this->SelectedPlaneProperty = vtkProperty::New();
439 this->SelectedPlaneProperty->SetAmbient(1.0);
440 this->SelectedPlaneProperty->SetColor(0.0, 1.0, 0.0);
441 this->SelectedPlaneProperty->SetOpacity(0.25);
442 }
443
444 //----------------------------------------------------------------------------
PlaceWidget(double bnds[6])445 void vtkFinitePlaneRepresentation::PlaceWidget(double bnds[6])
446 {
447 this->Normal[0] = 0.0;
448 this->Normal[1] = 0.0;
449 this->Normal[2] = 1.0;
450
451 this->Origin[0] = ((bnds[1] - bnds[0]) * 0.5) + bnds[0];
452 this->Origin[1] = ((bnds[3] - bnds[2]) * 0.5) + bnds[2];
453 this->Origin[2] = ((bnds[5] - bnds[4]) * 0.5) + bnds[4];
454
455 this->V1[0] = ((bnds[1] - bnds[0]) * 0.5);
456 this->V1[1] = 0.0;
457 this->V1[2] = 0.0;
458
459 this->V2[0] = 0.0;
460 this->V2[1] = ((bnds[3] - bnds[2]) * 0.5);
461 this->V2[2] = 0.0;
462
463 this->InitialLength =
464 sqrt((bnds[1] - bnds[0]) * (bnds[1] - bnds[0]) +
465 (bnds[3] - bnds[2]) * (bnds[3] - bnds[2]) +
466 (bnds[5] - bnds[4]) * (bnds[5] - bnds[4]));
467
468 this->ValidPick = 1; // since we have positioned the widget successfully
469 this->BuildRepresentation();
470 }
471
472 //----------------------------------------------------------------------------
ComputeInteractionState(int X,int Y,int vtkNotUsed (modify))473 int vtkFinitePlaneRepresentation::ComputeInteractionState(int X, int Y,
474 int vtkNotUsed(modify))
475 {
476 // Okay, we can process this. Try to pick handles first;
477 // if no handles picked, then pick the bounding box.
478 if (!this->Renderer || !this->Renderer->IsInViewport(X, Y))
479 {
480 this->SetRepresentationState(vtkFinitePlaneRepresentation::Outside);
481 this->InteractionState = vtkFinitePlaneRepresentation::Outside;
482 return this->InteractionState;
483 }
484
485 this->SetHighlightNormal(0);
486 this->SetHighlightPlane(0);
487 this->SetHighlightHandle(nullptr);
488
489 // See if anything has been selected
490 vtkAssemblyPath* path = this->GetAssemblyPath(X, Y, 0., this->HandlePicker);
491
492 if (path == nullptr) // Not picking this widget
493 {
494 this->SetRepresentationState(vtkFinitePlaneRepresentation::Outside);
495 this->InteractionState = vtkFinitePlaneRepresentation::Outside;
496 return this->InteractionState;
497 }
498
499 // Something picked, continue
500 this->ValidPick = 1;
501 vtkProp *prop = path->GetFirstNode()->GetViewProp();
502
503 if (prop == this->PlaneActor)
504 {
505 this->SetRepresentationState(vtkFinitePlaneRepresentation::Pushing);
506 this->InteractionState = vtkFinitePlaneRepresentation::Pushing;
507 this->SetHighlightNormal(0);
508 this->SetHighlightPlane(1);
509 this->SetHighlightHandle(nullptr);
510 }
511 else if ((prop == this->ConeActor) || (prop == this->ConeActor2) ||
512 (prop == this->LineActor) || (prop == this->LineActor2))
513 {
514 this->SetRepresentationState(vtkFinitePlaneRepresentation::Rotating);
515 this->InteractionState = vtkFinitePlaneRepresentation::Rotating;
516
517 this->SetHighlightNormal(1);
518 this->SetHighlightPlane(1);
519 this->SetHighlightHandle(nullptr);
520 }
521 else if (prop == this->OriginActor)
522 {
523 this->SetRepresentationState(vtkFinitePlaneRepresentation::MoveOrigin);
524 this->InteractionState = vtkFinitePlaneRepresentation::MoveOrigin;
525
526 this->SetHighlightNormal(1);
527 this->SetHighlightPlane(1);
528 this->SetHighlightHandle(prop);
529 }
530 else if (prop == this->V1Actor)
531 {
532 this->SetRepresentationState(vtkFinitePlaneRepresentation::ModifyV1);
533 this->InteractionState = vtkFinitePlaneRepresentation::ModifyV1;
534
535 this->SetHighlightNormal(0);
536 this->SetHighlightPlane(0);
537 this->SetHighlightHandle(prop);
538 }
539 else if (prop == this->V2Actor)
540 {
541 this->SetRepresentationState(vtkFinitePlaneRepresentation::ModifyV2);
542 this->InteractionState = vtkFinitePlaneRepresentation::ModifyV2;
543
544 this->SetHighlightNormal(0);
545 this->SetHighlightPlane(0);
546 this->SetHighlightHandle(prop);
547 }
548
549 return this->InteractionState;
550 }
551
552 //----------------------------------------------------------------------
GetBounds()553 double *vtkFinitePlaneRepresentation::GetBounds()
554 {
555 this->BuildRepresentation();
556
557 this->BoundingBox->SetBounds(this->OriginActor->GetBounds());
558 this->BoundingBox->AddBounds(this->V1Actor->GetBounds());
559 this->BoundingBox->AddBounds(this->V2Actor->GetBounds());
560 this->BoundingBox->AddBounds(this->EdgesActor->GetBounds());
561 this->BoundingBox->AddBounds(this->PlaneActor->GetBounds());
562 this->BoundingBox->AddBounds(this->ConeActor->GetBounds());
563 this->BoundingBox->AddBounds(this->LineActor->GetBounds());
564 this->BoundingBox->AddBounds(this->ConeActor2->GetBounds());
565 this->BoundingBox->AddBounds(this->LineActor2->GetBounds());
566
567 return this->BoundingBox->GetBounds();
568 }
569
570 //----------------------------------------------------------------------------
BuildRepresentation()571 void vtkFinitePlaneRepresentation::BuildRepresentation()
572 {
573 this->SizeHandles();
574
575 if (this->GetMTime() < this->BuildTime &&
576 this->PlanePolyData->GetMTime() < this->BuildTime)
577 {
578 return;
579 }
580
581 double *origin = this->GetOrigin();
582 double *normal = this->GetNormal();
583
584 // Setup the plane normal
585 double d = this->PlanePolyData->GetLength() *1.2;
586
587 double p2Line[3];
588 p2Line[0] = origin[0] + 0.30 * d * normal[0];
589 p2Line[1] = origin[1] + 0.30 * d * normal[1];
590 p2Line[2] = origin[2] + 0.30 * d * normal[2];
591
592 this->LineSource->SetPoint1(origin);
593 this->LineSource->SetPoint2(p2Line);
594 this->ConeSource->SetCenter(p2Line);
595 this->ConeSource->SetDirection(normal);
596
597 p2Line[0] = origin[0] - 0.30 * d * normal[0];
598 p2Line[1] = origin[1] - 0.30 * d * normal[1];
599 p2Line[2] = origin[2] - 0.30 * d * normal[2];
600
601 this->LineSource2->SetPoint1(origin);
602 this->LineSource2->SetPoint2(p2Line);
603 this->ConeSource2->SetCenter(p2Line);
604 this->ConeSource2->SetDirection(normal);
605
606 // Set up the position handle
607 this->OriginGeometry->SetCenter(origin);
608
609 double vector1[3] = { this->V1[0], this->V1[1], this->V1[2] };
610 this->Transform->TransformVector(vector1, vector1);
611
612 double position[3];
613 this->Transform->GetPosition(position);
614
615 double point1[3];
616 point1[0] = origin[0] + vector1[0];
617 point1[1] = origin[1] + vector1[1];
618 point1[2] = origin[2] + vector1[2];
619 this->V1Geometry->SetCenter(point1);
620
621 double vector2[3] = { this->V2[0], this->V2[1], this->V2[2] };
622 this->Transform->TransformPoint(vector2, vector2);
623
624 double point2[3];
625 point2[0] = origin[0] + vector2[0];
626 point2[1] = origin[1] + vector2[1];
627 point2[2] = origin[2] + vector2[2];
628 this->V2Geometry->SetCenter(point2);
629
630 // Build Plane polydata
631 vtkPoints *points = this->PlanePolyData->GetPoints();
632 points->SetPoint(0,
633 origin[0] - vector1[0] - vector2[0],
634 origin[1] - vector1[1] - vector2[1],
635 origin[2] - vector1[2] - vector2[2]);
636 points->SetPoint(1,
637 origin[0] - vector1[0] + vector2[0],
638 origin[1] - vector1[1] + vector2[1],
639 origin[2] - vector1[2] + vector2[2]);
640 points->SetPoint(2,
641 origin[0] + vector1[0] + vector2[0],
642 origin[1] + vector1[1] + vector2[1],
643 origin[2] + vector1[2] + vector2[2]);
644 points->SetPoint(3,
645 origin[0] + vector1[0] - vector2[0],
646 origin[1] + vector1[1] - vector2[1],
647 origin[2] + vector1[2] - vector2[2]);
648 points->Modified();
649
650 this->PlanePolyData->Modified();
651
652 // Control the look of the edges
653 this->EdgesMapper->SetInputConnection(this->Tubing ?
654 this->EdgesTuber->GetOutputPort(): this->Edges->GetOutputPort());
655
656 this->SizeHandles();
657 this->BuildTime.Modified();
658 }
659
660 //----------------------------------------------------------------------------
ReleaseGraphicsResources(vtkWindow * w)661 void vtkFinitePlaneRepresentation::ReleaseGraphicsResources(vtkWindow *w)
662 {
663 this->OriginActor->ReleaseGraphicsResources(w);
664 this->V1Actor->ReleaseGraphicsResources(w);
665 this->V2Actor->ReleaseGraphicsResources(w);
666 this->PlaneActor->ReleaseGraphicsResources(w);
667 this->EdgesActor->ReleaseGraphicsResources(w);
668 this->ConeActor->ReleaseGraphicsResources(w);
669 this->LineActor->ReleaseGraphicsResources(w);
670 this->ConeActor2->ReleaseGraphicsResources(w);
671 this->LineActor2->ReleaseGraphicsResources(w);
672 }
673
674 //----------------------------------------------------------------------------
RenderOpaqueGeometry(vtkViewport * v)675 int vtkFinitePlaneRepresentation::RenderOpaqueGeometry(vtkViewport *v)
676 {
677 int count = 0;
678 this->BuildRepresentation();
679
680 if (this->OriginActor->GetVisibility())
681 {
682 count += this->OriginActor->RenderOpaqueGeometry(v);
683 }
684 if (this->V1Actor->GetVisibility())
685 {
686 count += this->V1Actor->RenderOpaqueGeometry(v);
687 }
688 if (this->V2Actor->GetVisibility())
689 {
690 count += this->V2Actor->RenderOpaqueGeometry(v);
691 }
692 count += this->EdgesActor->RenderOpaqueGeometry(v);
693 count += this->ConeActor->RenderOpaqueGeometry(v);
694 count += this->LineActor->RenderOpaqueGeometry(v);
695 count += this->ConeActor2->RenderOpaqueGeometry(v);
696 count += this->LineActor2->RenderOpaqueGeometry(v);
697
698 if (this->DrawPlane)
699 {
700 count += this->PlaneActor->RenderOpaqueGeometry(v);
701 }
702
703 return count;
704 }
705
706 //----------------------------------------------------------------------------
RenderTranslucentPolygonalGeometry(vtkViewport * v)707 int vtkFinitePlaneRepresentation::RenderTranslucentPolygonalGeometry(vtkViewport *v)
708 {
709 int count = 0;
710 this->BuildRepresentation();
711
712 if (this->OriginActor->GetVisibility())
713 {
714 count += this->OriginActor->RenderTranslucentPolygonalGeometry(v);
715 }
716 if (this->V1Actor->GetVisibility())
717 {
718 count += this->V1Actor->RenderTranslucentPolygonalGeometry(v);
719 }
720 if (this->V2Actor->GetVisibility())
721 {
722 count += this->V2Actor->RenderTranslucentPolygonalGeometry(v);
723 }
724
725 count += this->EdgesActor->RenderTranslucentPolygonalGeometry(v);
726 count += this->ConeActor->RenderTranslucentPolygonalGeometry(v);
727 count += this->LineActor->RenderTranslucentPolygonalGeometry(v);
728 count += this->ConeActor2->RenderTranslucentPolygonalGeometry(v);
729 count += this->LineActor2->RenderTranslucentPolygonalGeometry(v);
730
731 if (this->DrawPlane)
732 {
733 count += this->PlaneActor->RenderTranslucentPolygonalGeometry(v);
734 }
735
736 return count;
737 }
738
739 //----------------------------------------------------------------------------
HasTranslucentPolygonalGeometry()740 vtkTypeBool vtkFinitePlaneRepresentation::HasTranslucentPolygonalGeometry()
741 {
742 int result = 0;
743 this->BuildRepresentation();
744
745 if (this->OriginActor->GetVisibility())
746 {
747 result |= this->OriginActor->HasTranslucentPolygonalGeometry();
748 }
749 if (this->V1Actor->GetVisibility())
750 {
751 result |= this->V1Actor->HasTranslucentPolygonalGeometry();
752 }
753 if (this->V2Actor->GetVisibility())
754 {
755 result |= this->V2Actor->HasTranslucentPolygonalGeometry();
756 }
757
758 result |= this->EdgesActor->HasTranslucentPolygonalGeometry();
759 result |= this->ConeActor->HasTranslucentPolygonalGeometry();
760 result |= this->LineActor->HasTranslucentPolygonalGeometry();
761 result |= this->ConeActor2->HasTranslucentPolygonalGeometry();
762 result |= this->LineActor2->HasTranslucentPolygonalGeometry();
763
764 if (this->DrawPlane)
765 {
766 result |= this->PlaneActor->HasTranslucentPolygonalGeometry();
767 }
768
769 return result;
770 }
771
772 //----------------------------------------------------------------------------
SetHandles(bool handles)773 void vtkFinitePlaneRepresentation::SetHandles(bool handles)
774 {
775 int h = handles ? 1 : 0;
776 if (this->V1Actor->GetVisibility() == h)
777 {
778 return;
779 }
780 this->V1Actor->SetVisibility(h);
781 this->V2Actor->SetVisibility(h);
782 this->OriginActor->SetVisibility(h);
783 this->Modified();
784 }
785
786 //----------------------------------------------------------------------------
HandlesOn()787 void vtkFinitePlaneRepresentation::HandlesOn()
788 {
789 this->SetHandles(true);
790 }
791
792 //----------------------------------------------------------------------------
HandlesOff()793 void vtkFinitePlaneRepresentation::HandlesOff()
794 {
795 this->SetHandles(false);
796 }
797
798 //----------------------------------------------------------------------------
SizeHandles()799 void vtkFinitePlaneRepresentation::SizeHandles()
800 {
801 double radius =
802 this->vtkWidgetRepresentation::SizeHandlesInPixels(1.5, this->GetOrigin());
803
804 this->OriginGeometry->SetRadius(radius);
805 this->V1Geometry->SetRadius(radius);
806 this->V2Geometry->SetRadius(radius);
807
808 this->ConeSource->SetHeight(radius * 2.0);
809 this->ConeSource->SetRadius(radius);
810 this->ConeSource2->SetHeight(radius * 2.0);
811 this->ConeSource2->SetRadius(radius);
812
813 this->EdgesTuber->SetRadius(radius * 0.25);
814 }
815
816 //----------------------------------------------------------------------------
SetHighlightHandle(vtkProp * prop)817 void vtkFinitePlaneRepresentation::SetHighlightHandle(vtkProp *prop)
818 {
819 if (this->CurrentHandle == this->OriginActor)
820 {
821 this->OriginActor->SetProperty(this->OriginHandleProperty);
822 }
823 else if (this->CurrentHandle == this->V1Actor)
824 {
825 this->CurrentHandle->SetProperty(this->V1HandleProperty);
826 }
827 else if (this->CurrentHandle == this->V2Actor)
828 {
829 this->CurrentHandle->SetProperty(this->V2HandleProperty);
830 }
831
832 this->CurrentHandle = dynamic_cast<vtkActor*>(prop);
833
834 if (this->CurrentHandle)
835 {
836 this->CurrentHandle->SetProperty(this->SelectedHandleProperty);
837 }
838 }
839
840 //------------------------------------------------------------------------------
RegisterPickers()841 void vtkFinitePlaneRepresentation::RegisterPickers()
842 {
843 vtkPickingManager* pm = this->GetPickingManager();
844 if (!pm)
845 {
846 return;
847 }
848 pm->AddPicker(this->HandlePicker, this);
849 }
850
851 //----------------------------------------------------------------------------
SetOrigin(double x,double y,double z)852 void vtkFinitePlaneRepresentation::SetOrigin(double x, double y, double z)
853 {
854 double origin[3] = { x, y, z };
855 this->SetOrigin(origin);
856 }
857
858 //----------------------------------------------------------------------------
SetOrigin(double x[3])859 void vtkFinitePlaneRepresentation::SetOrigin(double x[3])
860 {
861 if (this->Origin[0] != x[0] ||
862 this->Origin[1] != x[1] ||
863 this->Origin[2] != x[2])
864 {
865 this->Origin[0] = x[0];
866 this->Origin[1] = x[1];
867 this->Origin[2] = x[2];
868
869 this->Modified();
870 this->BuildRepresentation();
871 }
872 }
873
874 //----------------------------------------------------------------------------
SetV1(double x,double y)875 void vtkFinitePlaneRepresentation::SetV1(double x, double y)
876 {
877 double v1[2] = { x, y };
878 this->SetV1(v1);
879 }
880
881 //----------------------------------------------------------------------------
SetV1(double x[2])882 void vtkFinitePlaneRepresentation::SetV1(double x[2])
883 {
884 if (this->V1[0] != x[0] ||
885 this->V1[1] != x[1])
886 {
887 this->V1[0] = x[0];
888 this->V1[1] = x[1];
889
890 this->Modified();
891 this->BuildRepresentation();
892 }
893 }
894
895 //----------------------------------------------------------------------------
SetV2(double x,double y)896 void vtkFinitePlaneRepresentation::SetV2(double x, double y)
897 {
898 double v2[2] = { x, y };
899 this->SetV2(v2);
900 }
901
902 //----------------------------------------------------------------------------
SetV2(double x[2])903 void vtkFinitePlaneRepresentation::SetV2(double x[2])
904 {
905 if (this->V2[0] != x[0] ||
906 this->V2[1] != x[1])
907 {
908 this->V2[0] = x[0];
909 this->V2[1] = x[1];
910
911 this->Modified();
912 this->BuildRepresentation();
913 }
914 }
915
916 //----------------------------------------------------------------------------
SetNormal(double x,double y,double z)917 void vtkFinitePlaneRepresentation::SetNormal(double x, double y, double z)
918 {
919 double n[3] = { x, y, z };
920 vtkMath::Normalize(n);
921
922 this->PreviousNormal[0] = this->Normal[0];
923 this->PreviousNormal[1] = this->Normal[1];
924 this->PreviousNormal[2] = this->Normal[2];
925
926 if (n[0] != this->Normal[0] || n[1] != this->Normal[1] || n[2] != this->Normal[2])
927 {
928 this->Normal[0] = n[0];
929 this->Normal[1] = n[1];
930 this->Normal[2] = n[2];
931
932 double RotationAxis[3];
933 vtkMath::Cross(this->PreviousNormal, this->Normal, RotationAxis);
934 vtkMath::Normalize(RotationAxis);
935 double RotationAngle = vtkMath::DegreesFromRadians(
936 acos(vtkMath::Dot(this->PreviousNormal, this->Normal)));
937
938 this->Transform->PostMultiply();
939 this->Transform->RotateWXYZ(RotationAngle,
940 RotationAxis[0], RotationAxis[1], RotationAxis[2]);
941
942 this->Modified();
943 this->BuildRepresentation();
944 }
945 }
946
947 //----------------------------------------------------------------------------
SetNormal(double n[3])948 void vtkFinitePlaneRepresentation::SetNormal(double n[3])
949 {
950 this->SetNormal(n[0], n[1], n[2]);
951 }
952
953 //----------------------------------------------------------------------------
SetDrawPlane(bool drawPlane)954 void vtkFinitePlaneRepresentation::SetDrawPlane(bool drawPlane)
955 {
956 if (drawPlane == this->DrawPlane)
957 {
958 return;
959 }
960
961 this->DrawPlane = drawPlane;
962 this->Modified();
963 this->BuildRepresentation();
964 }
965
966 //----------------------------------------------------------------------------
SetHighlightPlane(int highlight)967 void vtkFinitePlaneRepresentation::SetHighlightPlane(int highlight)
968 {
969 this->PlaneActor->SetProperty(
970 highlight ? this->SelectedPlaneProperty : this->PlaneProperty);
971 }
972
973 //----------------------------------------------------------------------------
SetHighlightNormal(int highlight)974 void vtkFinitePlaneRepresentation::SetHighlightNormal(int highlight)
975 {
976 vtkProperty* p =
977 highlight ? this->SelectedNormalProperty : this->NormalProperty;
978 this->LineActor->SetProperty(p);
979 this->ConeActor->SetProperty(p);
980 this->LineActor2->SetProperty(p);
981 this->ConeActor2->SetProperty(p);
982 this->OriginActor->SetProperty(p);
983 }
984
985 //----------------------------------------------------------------------------
SetRepresentationState(int state)986 void vtkFinitePlaneRepresentation::SetRepresentationState(int state)
987 {
988 if (this->RepresentationState == state)
989 {
990 return;
991 }
992
993 // Clamp the state
994 state = (state < vtkFinitePlaneRepresentation::Outside ?
995 vtkFinitePlaneRepresentation::Outside :
996 (state > vtkFinitePlaneRepresentation::Pushing ?
997 vtkFinitePlaneRepresentation::Pushing : state));
998
999 this->RepresentationState = state;
1000 this->Modified();
1001 }
1002
1003 //----------------------------------------------------------------------------
1004 // translate origin of plane
TranslateOrigin(double * p1,double * p2)1005 void vtkFinitePlaneRepresentation::TranslateOrigin(double *p1, double *p2)
1006 {
1007 // Get the motion vector
1008 double v[3];
1009 v[0] = p2[0] - p1[0];
1010 v[1] = p2[1] - p1[1];
1011 v[2] = p2[2] - p1[2];
1012
1013 // Add to the current point
1014 this->SetOrigin(
1015 this->Origin[0] + v[0],
1016 this->Origin[1] + v[1],
1017 this->Origin[2] + v[2]);
1018 }
1019
1020 //----------------------------------------------------------------------------
1021 // Move Point 1
MovePoint1(double * p1,double * p2)1022 void vtkFinitePlaneRepresentation::MovePoint1(double *p1, double *p2)
1023 {
1024 //Get the motion vector
1025 double v[3];
1026 v[0] = p2[0] - p1[0];
1027 v[1] = p2[1] - p1[1];
1028 v[2] = p2[2] - p1[2];
1029
1030 vtkNew<vtkMatrix4x4> mat;
1031 this->Transform->GetInverse(mat);
1032
1033 vtkNew<vtkTransform> t;
1034 t->SetMatrix(mat);
1035 t->TransformVector(v, v);
1036
1037 double *v1 = this->GetV1();
1038
1039 double newV1[2];
1040 newV1[0] = v1[0] + v[0];
1041 newV1[1] = v1[1] + v[1];
1042
1043 this->SetV1(newV1[0], newV1[1]);
1044 }
1045
1046 //----------------------------------------------------------------------------
1047 // Modified Vector v2
MovePoint2(double * p1,double * p2)1048 void vtkFinitePlaneRepresentation::MovePoint2(double *p1, double *p2)
1049 {
1050 //Get the motion vector
1051 double v[3];
1052 v[0] = p2[0] - p1[0];
1053 v[1] = p2[1] - p1[1];
1054 v[2] = p2[2] - p1[2];
1055
1056 vtkNew<vtkMatrix4x4> mat;
1057 this->Transform->GetInverse(mat);
1058
1059 vtkNew<vtkTransform> t;
1060 t->SetMatrix(mat);
1061 t->TransformVector(v, v);
1062
1063 double *v2 = this->GetV2();
1064
1065 double newV2[2];
1066 newV2[0] = v2[0] + v[0];
1067 newV2[1] = v2[1] + v[1];
1068
1069 this->SetV2(newV2[0], newV2[1]);
1070 }
1071
1072 //----------------------------------------------------------------------------
1073 // Push Face
Push(double * p1,double * p2)1074 void vtkFinitePlaneRepresentation::Push(double *p1, double *p2)
1075 {
1076 //Get the motion vector
1077 double v[3];
1078 v[0] = p2[0] - p1[0];
1079 v[1] = p2[1] - p1[1];
1080 v[2] = p2[2] - p1[2];
1081
1082 double distance = vtkMath::Dot(v, this->Normal);
1083
1084 if (distance == 0.0)
1085 {
1086 return;
1087 }
1088
1089 double origin[3];
1090 this->GetOrigin(origin);
1091 origin[0] += distance * this->Normal[0];
1092 origin[1] += distance * this->Normal[1];
1093 origin[2] += distance * this->Normal[2];
1094
1095 this->SetOrigin(origin);
1096 }
1097
1098 //----------------------------------------------------------------------------
PrintSelf(ostream & os,vtkIndent indent)1099 void vtkFinitePlaneRepresentation::PrintSelf(ostream& os, vtkIndent indent)
1100 {
1101 this->Superclass::PrintSelf(os, indent);
1102
1103 double *bounds = this->InitialBounds;
1104 os << indent << "Initial Bounds: "
1105 << "(" << bounds[0] << ", " << bounds[1] << ") "
1106 << "(" << bounds[2] << ", " << bounds[3] << ") "
1107 << "(" << bounds[4] << ", " << bounds[5] << ")\n";
1108
1109 if (this->OriginHandleProperty)
1110 {
1111 os << indent << "Origin Handle Property: " << this->OriginHandleProperty << "\n";
1112 }
1113 else
1114 {
1115 os << indent << "Origin Handle Property: (none)\n";
1116 }
1117 if (this->V1HandleProperty)
1118 {
1119 os << indent << "P1 Handle Property: " << this->V1HandleProperty << "\n";
1120 }
1121 else
1122 {
1123 os << indent << "P1 Handle Property: (none)\n";
1124 }
1125 if (this->V2HandleProperty)
1126 {
1127 os << indent << "P2 Handle Property: " << this->V2HandleProperty << "\n";
1128 }
1129 else
1130 {
1131 os << indent << "P2 Handle Property: (none)\n";
1132 }
1133 if (this->SelectedHandleProperty)
1134 {
1135 os << indent << "Selected Handle Property: "
1136 << this->SelectedHandleProperty << "\n";
1137 }
1138 else
1139 {
1140 os << indent << "SelectedHandle Property: (none)\n";
1141 }
1142
1143 if (this->PlaneProperty)
1144 {
1145 os << indent << "Plane Property: " << this->PlaneProperty << "\n";
1146 }
1147 else
1148 {
1149 os << indent << "Plane Property: (none)\n";
1150 }
1151 if (this->SelectedPlaneProperty)
1152 {
1153 os << indent << "Selected Plane Property: "
1154 << this->SelectedPlaneProperty << "\n";
1155 }
1156 else
1157 {
1158 os << indent << "Selected Plane Property: (none)\n";
1159 }
1160
1161 os << indent << "Tubing: " << (this->Tubing ? "On" : "Off") << "\n";
1162 os << indent << "Draw Plane: " << (this->DrawPlane ? "On" : "Off") << "\n";
1163 }
1164