Commit ad0b261f authored by Ken Martin's avatar Ken Martin Committed by Kitware Robot

Merge topic 'add_flagpole_class'

f4b62a6d add a flagpole label class and test
Acked-by: Kitware Robot's avatarKitware Robot <kwrobot@kitware.com>
Merge-request: !5006
parents ae2901c4 f4b62a6d
......@@ -26,6 +26,7 @@ set(Module_SRCS
vtkDataSetMapper.cxx
vtkDiscretizableColorTransferFunction.cxx
vtkDistanceToCamera.cxx
vtkFlagpoleLabel.cxx
vtkFollower.cxx
vtkFrameBufferObjectBase.cxx
vtkFrustumCoverageCuller.cxx
......
This diff is collapsed.
/*=========================================================================
Program: Visualization Toolkit
Module: vtkFlagpoleLabel.h
Copyright (c) Ken Martin, Will Schroeder, Bill Lorensen
All rights reserved.
See Copyright.txt or http://www.kitware.com/Copyright.htm for details.
This software is distributed WITHOUT ANY WARRANTY; without even
the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
PURPOSE. See the above copyright notice for more information.
=========================================================================*/
/**
* @class vtkFlagpoleLabel
* @brief Renders a flagpole (line) with a label at the top that faces the camera
*
* This class draws a line from the base to the top of the flagpole. It then
* places a text annotation at the top, centered horizontally. The text is
* always oriented with the flagpole but will rotate aroundthe flagpole to
* face the camera.
*/
#ifndef vtkFlagpoleLabel_h
#define vtkFlagpoleLabel_h
#include "vtkRenderingCoreModule.h" // For export macro
#include "vtkProp3D.h"
#include "vtkNew.h" // For.... vtkNew!
#include "vtkSmartPointer.h" // For.... vtkSmartPointer!
class vtkActor;
class vtkImageData;
class vtkLineSource;
class vtkPolyData;
class vtkPolyDataMapper;
class vtkRenderer;
class vtkTextProperty;
class vtkTextRenderer;
class vtkTexture;
class VTKRENDERINGCORE_EXPORT vtkFlagpoleLabel: public vtkProp3D
{
public:
static vtkFlagpoleLabel* New();
vtkTypeMacro(vtkFlagpoleLabel, vtkProp3D)
void PrintSelf(ostream &os, vtkIndent indent) override;
/**
* The UTF-8 encoded string to display.
* @{
*/
void SetInput(const char *in);
vtkGetStringMacro(Input)
/** @} */
/**
* The vtkTextProperty object that controls the rendered text.
* @{
*/
void SetTextProperty(vtkTextProperty *tprop);
vtkGetObjectMacro(TextProperty, vtkTextProperty)
/** @} */
/**
* Force the actor to render during the opaque or translucent pass.
* @{
*/
virtual void SetForceOpaque(bool opaque);
virtual bool GetForceOpaque();
virtual void ForceOpaqueOn();
virtual void ForceOpaqueOff();
virtual void SetForceTranslucent(bool trans);
virtual bool GetForceTranslucent();
virtual void ForceTranslucentOn();
virtual void ForceTranslucentOff();
/**@}*/
/**
* Defers to internal actor.
*/
vtkTypeBool HasTranslucentPolygonalGeometry() override;
/**
* Check/update geometry/texture in opaque pass, since it only happens once.
*/
int RenderOpaqueGeometry(vtkViewport *vp) override;
/**
* Just render in translucent pass, since it can execute multiple times
* (depth peeling, for instance).
*/
int RenderTranslucentPolygonalGeometry(vtkViewport *vp) override;
void ReleaseGraphicsResources(vtkWindow *win) override;
double *GetBounds() override;
using Superclass::GetBounds;
/**
* Set/Get the world coordinate position of the base
*/
vtkGetVector3Macro(BasePosition, double)
void SetBasePosition(double x, double y, double z);
/**
* Set/Get the world coordinate position of the top
*/
vtkGetVector3Macro(TopPosition, double)
void SetTopPosition(double x, double y, double z);
/**
* Set/Get the size of the flag. 1.0 is the default size
* which corresponds to a preset texels/window value. Adjust this
* to increase or decrease the default size.
*/
vtkGetMacro(FlagSize, double)
vtkSetMacro(FlagSize, double)
protected:
vtkFlagpoleLabel();
~vtkFlagpoleLabel() override;
bool InputIsValid();
void UpdateInternals(vtkRenderer *ren);
bool TextureIsStale(vtkRenderer *ren);
void GenerateTexture(vtkRenderer *ren);
bool QuadIsStale(vtkRenderer *ren);
void GenerateQuad(vtkRenderer *ren);
// Used by the opaque pass to tell the translucent pass not to render.
void Invalidate();
bool IsValid();
// Used to sync the internal actor's state.
void PreRender();
// Text specification:
char *Input;
vtkTextProperty *TextProperty;
// Cached metadata to determine if things need rebuildin'
int RenderedDPI;
vtkTimeStamp InputMTime;
// We cache this so we can recompute the bounds between renders, if needed.
vtkSmartPointer<vtkRenderer> RenderedRenderer;
// Rendering stuffies
vtkNew<vtkTextRenderer> TextRenderer;
vtkNew<vtkImageData> Image;
vtkNew<vtkTexture> Texture;
vtkNew<vtkPolyData> Quad;
vtkNew<vtkPolyDataMapper> QuadMapper;
vtkNew<vtkActor> QuadActor;
vtkNew<vtkPolyDataMapper> PoleMapper;
vtkNew<vtkLineSource> LineSource;
vtkNew<vtkActor> PoleActor;
double TopPosition[3];
double BasePosition[3];
double FlagSize;
private:
vtkFlagpoleLabel(const vtkFlagpoleLabel&) = delete;
void operator=(const vtkFlagpoleLabel&) = delete;
};
#endif // vtkFlagpoleLabel_h
......@@ -6,6 +6,7 @@ set(TestMathTextFreeTypeTextRendererNoMath_ARGS
vtk_add_test_cxx(vtkRenderingFreeTypeCxxTests tests
TestBillboardTextActor3D.cxx
TestFTStringToPath.cxx
TestFlagpoleLabel.cxx
TestFreeTypeTextMapperNoMath.cxx
TestFreeTypeTools.cxx,NO_VALID
TestMathTextFreeTypeTextRendererNoMath.cxx
......
/*=========================================================================
Program: Visualization Toolkit
Copyright (c) Ken Martin, Will Schroeder, Bill Lorensen
All rights reserved.
See Copyright.txt or http://www.kitware.com/Copyright.htm for details.
This software is distributed WITHOUT ANY WARRANTY; without even
the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
PURPOSE. See the above copyright notice for more information.
=========================================================================*/
#include "vtkFlagpoleLabel.h"
#include "vtkActor.h"
#include "vtkCamera.h"
#include "vtkCellArray.h"
#include "vtkCellData.h"
#include "vtkNew.h"
#include "vtkPolyData.h"
#include "vtkPolyDataMapper.h"
#include "vtkProperty.h"
#include "vtkRenderWindow.h"
#include "vtkRenderWindowInteractor.h"
#include "vtkRenderer.h"
#include "vtkTestingInteractor.h"
#include "vtkTextProperty.h"
#include "vtkUnsignedCharArray.h"
#include <algorithm>
#include <sstream>
#include <vector>
namespace
{
void setupFlagpoleText(vtkFlagpoleLabel *actor,
vtkPolyData *anchor)
{
vtkTextProperty *p = actor->GetTextProperty();
std::ostringstream label;
label << "HAlign: " << p->GetJustificationAsString() << "\n"
<< "VAlign: " << p->GetVerticalJustificationAsString();
actor->SetInput(label.str().c_str());
// Add the anchor point:
double *pos = actor->GetTopPosition();
double *col = p->GetColor();
vtkIdType ptId = anchor->GetPoints()->InsertNextPoint(pos[0], pos[1], pos[2]);
anchor->GetVerts()->InsertNextCell(1, &ptId);
anchor->GetCellData()->GetScalars()->InsertNextTuple4(col[0] * 255,
col[1] * 255,
col[2] * 255, 255);
}
void setupGrid(vtkPolyData *grid)
{
double marks[4] = {0., 200., 400., 600.};
double thickness = 200.;
vtkNew<vtkPoints> points;
grid->SetPoints(points);
for (int x_i = 0; x_i < 4; ++x_i)
{
for (int y_i = 0; y_i < 4; ++y_i)
{
points->InsertNextPoint(marks[x_i], marks[y_i], -thickness / 2.);
points->InsertNextPoint(marks[x_i], marks[y_i], +thickness / 2.);
}
}
std::vector<vtkIdType> quads;
for (vtkIdType col = 0; col < 4; ++col)
{
for (int row = 0; row < 3; ++row)
{
// Along y:
vtkIdType base = 8 * col + 2 * row;
quads.push_back(base + 0);
quads.push_back(base + 1);
quads.push_back(base + 3);
quads.push_back(base + 2);
}
}
vtkNew<vtkCellArray> cellArray;
grid->SetPolys(cellArray);
for (size_t i = 0; i < quads.size(); i += 4)
{
grid->InsertNextCell(VTK_QUAD, 4, &quads[i]);
}
}
}
//----------------------------------------------------------------------------
int TestFlagpoleLabel(int, char *[])
{
vtkNew<vtkRenderer> ren;
ren->UseDepthPeelingOn();
int width = 600;
int height = 600;
int x[3] = {100, 300, 500};
int y[3] = {100, 300, 500};
// Render the anchor points to check alignment:
vtkNew<vtkPolyData> anchors;
vtkNew<vtkPoints> points;
anchors->SetPoints(points);
vtkNew<vtkCellArray> verts;
anchors->SetVerts(verts);
vtkNew<vtkUnsignedCharArray> colors;
colors->SetNumberOfComponents(4);
anchors->GetCellData()->SetScalars(colors);
for (size_t row = 0; row < 3; ++row)
{
for (size_t col = 0; col < 3; ++col)
{
vtkNew<vtkFlagpoleLabel> actor;
switch (row)
{
case 0:
actor->GetTextProperty()->SetJustificationToRight();
break;
case 1:
actor->GetTextProperty()->SetJustificationToCentered();
break;
case 2:
actor->GetTextProperty()->SetJustificationToLeft();
break;
}
switch (col)
{
case 0:
actor->GetTextProperty()->SetVerticalJustificationToBottom();
break;
case 1:
actor->GetTextProperty()->SetVerticalJustificationToCentered();
break;
case 2:
actor->GetTextProperty()->SetVerticalJustificationToTop();
break;
}
actor->GetTextProperty()->SetColor(0.75, .2 + col * .26, .2 + row * .26);
actor->GetTextProperty()->SetBackgroundColor(0.,
1. - col * .26,
1. - row * .26);
actor->GetTextProperty()->SetFrameColor(
actor->GetTextProperty()->GetBackgroundColor());
actor->GetTextProperty()->SetBackgroundOpacity(0.85);
actor->SetBasePosition(x[col], y[row] - 50.0, 0.);
actor->SetTopPosition(x[col], y[row] + 50.0, 0.);
setupFlagpoleText(actor, anchors);
ren->AddActor(actor);
}
}
vtkNew<vtkPolyDataMapper> anchorMapper;
anchorMapper->SetInputData(anchors);
vtkNew<vtkActor> anchorActor;
anchorActor->SetMapper(anchorMapper);
anchorActor->GetProperty()->SetPointSize(5);
ren->AddActor(anchorActor);
vtkNew<vtkPolyData> grid;
setupGrid(grid);
vtkNew<vtkPolyDataMapper> gridMapper;
gridMapper->SetInputData(grid);
vtkNew<vtkActor> gridActor;
gridActor->GetProperty()->SetRepresentationToSurface();
gridActor->GetProperty()->SetColor(0.6, 0.6, 0.6);
gridActor->SetMapper(gridMapper);
ren->AddActor(gridActor);
vtkNew<vtkRenderWindow> win;
win->AddRenderer(ren);
vtkNew<vtkRenderWindowInteractor> iren;
iren->SetRenderWindow(win);
ren->SetBackground(0.0, 0.0, 0.0);
ren->GetActiveCamera()->SetPosition(width/2, height/2, 1400);
ren->GetActiveCamera()->SetFocalPoint(width/2, height/2, 0);
ren->GetActiveCamera()->SetViewUp(0, 1, 0);
ren->GetActiveCamera()->Azimuth(15.);
ren->GetActiveCamera()->Roll(5.);
ren->ResetCameraClippingRange();
win->SetSize(width, height);
win->SetMultiSamples(0);
win->GetInteractor()->Initialize();
win->GetInteractor()->Start();
return EXIT_SUCCESS;
}
6aae07c892c4413cd4181962b26cff1f3d821b67f4ca396cbbcfd376229e071ca5ae3c405d2acf1399d4414774fade1d9d0ce90a956b9fccd3dd75a0fee98353
Markdown is supported
0% or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment