[vtkusers] positioning a cylinder
Marc Cotran
marc at cotran.ca
Sat Mar 31 01:58:13 EDT 2007
Hi Mark,
I have a 'hard' way of doing what you are asking. The easiest way is
what Amy proposes, but if you definitely want a cylinder that can update
quickly with changes to the endpoints...
- useablePt1 and 2 are classes (Coord) with 3 variables (x, y, z) for
coordinates. Although we implemented some convenience methods in Coord,
you could do it all with vtkMath.
- this->transform corresponds to that of the actor made from the
cylinderSource
//////////////////////////////
this->cylinderSource = vtkCylinderSource::New();
this->cylinderSource->SetCapping(1);
this->cylinderSource->SetResolution(5);
// find out halfway point
Coord halfwayPt(
(useablePt1.x() + useablePt2.x()) / 2,
(useablePt1.y() + useablePt2.y()) / 2,
(useablePt1.z() + useablePt2.z()) / 2);
double pos[4];
double res[4];
pos[0] = halfwayPt.x();
pos[1] = halfwayPt.y();
pos[2] = halfwayPt.z();
pos[3] = 1;
this->transform.getTransform()->MultiplyPoint(pos, res);
// we found the center point
Coord diff(this->pt2 - this->pt1);
Coord normalized(diff.normalize());
double norm = diff.norm();
this->cachedActor->SetScale(this->radius, norm, this->radius);
// get cross product
double cross[3];
double input[3];
double output[3];
input[0] = 0;
input[1] = 1;
input[2] = 0;
output[0] = normalized.x();
output[1] = normalized.y();
output[2] = normalized.z();
vtkMath::Cross(input, output, cross);
// get the angle
double angle = HelperClass::getAngle(Coord(0,1,0), Coord(), normalized);
// start with no rotation so they don't accumulate
this->cachedActor->SetOrientation(0,0,0);
this->cachedActor->RotateWXYZ(angle, cross[0], cross[1], cross[2]);
this->cachedActor->SetPosition(
res[0] / res[3],
res[1] / res[3],
res[2] / res[3]);
//////////////////////////////
It is quite possible that the code can be optimized (or at least made
shorter). The only advantage to this method is that you don't have to
remap the actor when you change one or both of the endpoints. If you
don't care about updates, I strongly recommend the lineSource/TubeFilter
method (it's much simpler!!!)
Marc
Mark Wyszomierski wrote:
> Hi,
>
> I have two points in VTK space, is there an easy way to construct a
> cylinder so that its two endpoints touch the two points? Something
> like:
>
> cylinder->SetEndpoint1(x,y,z);
> cylinder->SetEndpoint2(x,y,z);
>
> Thanks,
> Mark
> _______________________________________________
> This is the private VTK discussion list. Please keep messages
> on-topic. Check the FAQ at: http://www.vtk.org/Wiki/VTK_FAQ
> Follow this link to subscribe/unsubscribe:
> http://www.vtk.org/mailman/listinfo/vtkusers
More information about the vtkusers
mailing list