NamedColors
VTKExamples/Cxx/Visualization/NamedColors
Description¶
This example demonstrates the usage of the vtkNamedColors class. Some helper functions are also implemented.
A cone is created and contoured using the BandedPolyDataContourFilter, it is then colored using a LookupTable where the colors have been assigned using color names.
A list of available color names and any synonyms are also output.
Code¶
NamedColors.cxx
/* This example demonstrates the usage of the vtNamedColor class. */ #include <vtkNamedColors.h> #include <vtkActor.h> #include <vtkAlgorithm.h> #include <vtkBandedPolyDataContourFilter.h> #include <vtkConeSource.h> #include <vtkElevationFilter.h> #include <vtkLookupTable.h> #include <vtkPolyData.h> #include <vtkPolyDataMapper.h> #include <vtkProperty.h> #include <vtkRenderWindow.h> #include <vtkRenderWindowInteractor.h> #include <vtkRenderer.h> #include <vtkSmartPointer.h> #include <algorithm> #include <cctype> #include <cstdlib> #include <iostream> #include <iterator> #include <vector> // In C++0x there is a utility function std::next, however compilers // not implementing C++0x will need this equivalent. template <typename ForwardIt> ForwardIt myNext(ForwardIt iter, typename std::iterator_traits<ForwardIt>::difference_type n = 1); // Test if an iterator points to the last item. template <typename Iter, typename Cont> bool IsLast(Iter iter, const Cont& cont); // Parse the color names returning a std::vector<std::string> // colorNames is a string formatted with each name separated // with a linefeed. std::vector<vtkStdString> ParseColorNames(const vtkStdString& colorNames); // Parse the synonyms returning a std::vector<std::vector<std::string> > // synonyms is a string of synonyms separated by a double linefeed where // each synonym is two or more color names separated by a linefeed. std::vector<std::vector<vtkStdString>> ParseSynonyms( const vtkStdString& synonyms); // Print out the colors. void PrintColors(vtkNamedColors* namedColors); // Print out the synonyms. void PrintSynonyms(vtkNamedColors* namedColors); // Find any synonyms for a specified color. void FindSynonyms(const vtkStdString& color, vtkNamedColors* namedColors, vtkStringArray* synonyms); //----------------------------------------------------------------------------- template <typename ForwardIt> ForwardIt myNext( ForwardIt iter, typename std::iterator_traits<ForwardIt>::difference_type n) { std::advance(iter, n); return iter; } //----------------------------------------------------------------------------- template <typename Iter, typename Cont> bool IsLast(Iter iter, const Cont& cont) { return (iter != cont.end()) && (myNext(iter) == cont.end()); } //----------------------------------------------------------------------------- std::vector<vtkStdString> ParseColorNames(const vtkStdString& colorNames) { // The delimiter for a color. const std::string colorDelimiter = "\n"; std::vector<vtkStdString> cn; size_t start = 0; size_t end = colorNames.find(colorDelimiter); while (end != std::string::npos) { cn.push_back(colorNames.substr(start, end - start)); start = end + 1; end = colorNames.find(colorDelimiter, start); } // Get the last color. if (!colorNames.empty()) { cn.push_back(colorNames.substr(start, colorNames.size() - start)); } return cn; } //----------------------------------------------------------------------------- std::vector<std::vector<vtkStdString>> ParseSynonyms( const vtkStdString& synonyms) { // The delimiter for a string of synonyms. const std::string synonymDelimiter = "\n\n"; size_t start = 0; size_t end = synonyms.find("\n\n"); // The delimiter for a string of synonyms. std::vector<vtkStdString> cn; std::vector<std::vector<vtkStdString>> syn; vtkStdString str; while (end != std::string::npos) { str = synonyms.substr(start, end - start); cn = ParseColorNames(str); syn.push_back(cn); start = end + 2; end = synonyms.find(synonymDelimiter, start); } // Get the last set of synonyms. if (!synonyms.empty()) { str = synonyms.substr(start, end - start); cn = ParseColorNames(str); syn.push_back(cn); } return syn; } //----------------------------------------------------------------------------- void FindSynonyms(const vtkStdString& color, vtkNamedColors* namedColors, vtkStringArray* synonyms) { vtkSmartPointer<vtkStringArray> availableColors = vtkSmartPointer<vtkStringArray>::New(); namedColors->GetColorNames(availableColors); // We will be matching on RGB only. vtkColor3ub myColor = namedColors->GetColor3ub(color); // Colors are all stored as lower case, so convert color to lower case. vtkStdString lcColor; std::transform(color.begin(), color.end(), std::back_inserter(lcColor), (int (*)(int))std::tolower); for (vtkIdType i = 0; i < availableColors->GetNumberOfValues(); ++i) { vtkStdString n = availableColors->GetValue(i); vtkColor3ub c = namedColors->GetColor3ub(n); if (myColor.Compare(c, 1) /*&& n != lcColor*/) { synonyms->InsertNextValue(availableColors->GetValue(i)); } } } //----------------------------------------------------------------------------- void PrintColors(vtkNamedColors* namedColors) { // Get the available colors: std::vector<vtkStdString> colors = ParseColorNames(namedColors->GetColorNames()); std::cout << "There are " << namedColors->GetNumberOfColors() << " colors:" << std::endl; int n = 0; for (std::vector<vtkStdString>::const_iterator p = colors.begin(); p != colors.end(); ++p) { ++n; if (n % 5 == 0) { std::cout << std::endl; } std::cout << *p; if (!IsLast(p, colors)) { std::cout << ","; } } std::cout << std::endl; } //----------------------------------------------------------------------------- void PrintSynonyms(vtkNamedColors* namedColors) { // Get the synonyms: std::vector<std::vector<vtkStdString>> synonyms = ParseSynonyms(namedColors->GetSynonyms()); std::cout << "There are " << synonyms.size() << " synonyms:" << std::endl; for (std::vector<std::vector<vtkStdString>>::const_iterator p = synonyms.begin(); p != synonyms.end(); ++p) { for (std::vector<vtkStdString>::const_iterator q = p->begin(); q != p->end(); ++q) { std::cout << *q; if (!IsLast(q, *p)) { std::cout << ","; } } std::cout << std::endl; } } //----------------------------------------------------------------------------- // Create a cone, contour it using the banded contour filter and // color it with the primary additive and subtractive colors. int main(int, char* []) { vtkSmartPointer<vtkNamedColors> namedColors = vtkSmartPointer<vtkNamedColors>::New(); // We can print out the variables // namedColors->PrintSelf(std::cout,vtkIndent(2)); // Here we just print out the colors and any // synonyms. PrintColors(namedColors); PrintSynonyms(namedColors); // Create a cone vtkSmartPointer<vtkConeSource> coneSource = vtkSmartPointer<vtkConeSource>::New(); coneSource->SetCenter(0.0, 0.0, 0.0); coneSource->SetRadius(5.0); coneSource->SetHeight(10); coneSource->SetDirection(0, 1, 0); coneSource->Update(); double bounds[6]; coneSource->GetOutput()->GetBounds(bounds); vtkSmartPointer<vtkElevationFilter> elevation = vtkSmartPointer<vtkElevationFilter>::New(); elevation->SetInputConnection(coneSource->GetOutputPort()); elevation->SetLowPoint(0, bounds[2], 0); elevation->SetHighPoint(0, bounds[3], 0); vtkSmartPointer<vtkBandedPolyDataContourFilter> bcf = vtkSmartPointer<vtkBandedPolyDataContourFilter>::New(); bcf->SetInputConnection(elevation->GetOutputPort()); bcf->SetScalarModeToValue(); bcf->GenerateContourEdgesOn(); bcf->GenerateValues(7, elevation->GetScalarRange()); // Build a simple lookup table of // primary additive and subtractive colors. vtkSmartPointer<vtkLookupTable> lut = vtkSmartPointer<vtkLookupTable>::New(); lut->SetNumberOfTableValues(7); double rgba[4]; // Test setting and getting colors here. // We are also modifying alpha. namedColors->GetColor("Red", rgba); rgba[3] = 0.5; namedColors->SetColor("My Red", rgba); namedColors->GetColor("My Red", rgba); lut->SetTableValue(0, rgba); // Does "My Red" match anything? vtkSmartPointer<vtkStringArray> matchingColors = vtkSmartPointer<vtkStringArray>::New(); // Demonstrates how to find synonyms. FindSynonyms("My Red", namedColors, matchingColors); if (matchingColors->GetNumberOfValues() != 0) { std::cout << "Matching colors to My Red: "; for (vtkIdType i = 0; i < matchingColors->GetNumberOfValues(); ++i) { std::cout << matchingColors->GetValue(i); if (i != matchingColors->GetNumberOfValues() - 1) { std::cout << ","; } } std::cout << std::endl; } namedColors->GetColor("DarkGreen", rgba); rgba[3] = 0.3; lut->SetTableValue(1, rgba); // Alternatively we can use tuple methods here: lut->SetTableValue(2, namedColors->GetColor4d("Blue").GetData()); lut->SetTableValue(3, namedColors->GetColor4d("Cyan").GetData()); lut->SetTableValue(4, namedColors->GetColor4d("Magenta").GetData()); lut->SetTableValue(5, namedColors->GetColor4d("Yellow").GetData()); lut->SetTableValue(6, namedColors->GetColor4d("White").GetData()); lut->SetTableRange(elevation->GetScalarRange()); lut->Build(); vtkSmartPointer<vtkPolyDataMapper> mapper = vtkSmartPointer<vtkPolyDataMapper>::New(); mapper->SetInputConnection(bcf->GetOutputPort()); mapper->SetScalarRange(elevation->GetScalarRange()); mapper->SetLookupTable(lut); mapper->SetScalarModeToUseCellData(); vtkSmartPointer<vtkPolyDataMapper> contourLineMapper = vtkSmartPointer<vtkPolyDataMapper>::New(); contourLineMapper->SetInputData(bcf->GetContourEdgesOutput()); contourLineMapper->SetScalarRange(elevation->GetScalarRange()); contourLineMapper->SetResolveCoincidentTopologyToPolygonOffset(); vtkSmartPointer<vtkActor> actor = vtkSmartPointer<vtkActor>::New(); actor->SetMapper(mapper); vtkSmartPointer<vtkActor> contourLineActor = vtkSmartPointer<vtkActor>::New(); contourLineActor->SetMapper(contourLineMapper); contourLineActor->GetProperty()->SetColor( namedColors->GetColor3d("Black").GetData()); vtkSmartPointer<vtkRenderer> renderer = vtkSmartPointer<vtkRenderer>::New(); vtkSmartPointer<vtkRenderWindow> renderWindow = vtkSmartPointer<vtkRenderWindow>::New(); renderWindow->AddRenderer(renderer); vtkSmartPointer<vtkRenderWindowInteractor> renderWindowInteractor = vtkSmartPointer<vtkRenderWindowInteractor>::New(); renderWindowInteractor->SetRenderWindow(renderWindow); renderer->AddActor(actor); renderer->AddActor(contourLineActor); renderer->SetBackground(namedColors->GetColor3d("SteelBlue").GetData()); renderWindow->Render(); renderWindowInteractor->Start(); return EXIT_SUCCESS; }
CMakeLists.txt¶
cmake_minimum_required(VERSION 2.8) PROJECT(NamedColors) find_package(VTK REQUIRED) include(${VTK_USE_FILE}) add_executable(NamedColors MACOSX_BUNDLE NamedColors.cxx) target_link_libraries(NamedColors ${VTK_LIBRARIES})
Download and Build NamedColors¶
Danger
The generation of tar files has not been ported to the new VTKExamples. Some tarballs may be missing or out-of-date.
Click here to download NamedColors and its CMakeLists.txt file. Once the tarball NamedColors.tar has been downloaded and extracted,
cd NamedColors/build
If VTK is installed:
cmake ..
If VTK is not installed but compiled on your system, you will need to specify the path to your VTK build:
cmake -DVTK_DIR:PATH=/home/me/vtk_build ..
Build the project:
make
and run it:
./NamedColors
WINDOWS USERS PLEASE NOTE: Be sure to add the VTK bin directory to your path. This will resolve the VTK dll's at run time.