Dear Robert,
my colleague pointed out today that the vertical bar is upside down, and
hence not as the documentation says it should be. This is corrected with
this patch. Sorry for the inconvenience ;-(
- Kristofer
On 24 January 2014 17:20, Robert Osfield <[email protected]> wrote:
> Thanks Kristofer, changes look good and the example works nicely once
> again. Changes now merged and submitted to svn/trunk. Cheers, Robert.
>
>
> On 24 January 2014 09:59, Kristofer Tingdahl <[email protected]
> > wrote:
>
>> Dear Robert,
>>
>> Thanks for the input. It is true that it does not render as it did
>> before, but it renders as the documentation says it should render. In my
>> view, the vertical bar was not correctly rotated. Instead of doing what the
>> documentation said (and which is logical: go along the Y axis), it still
>> was aligned with the x-axis (though sitting in the XZ plane rather than in
>> the XY plane). With my patch, it renders in the XY plane (as the Horizonal
>> one), but it goes along the Y axis.
>>
>> To illustrate this, I have modified the example program to render both a
>> horizontal and a vertical in the scene so the difference can be seen.
>>
>> Compared to my previous revision, I have fixed the flaw with the title
>> being in the wrong plane on the vertical one, and I have also repositioned
>> it to the top of the vertical one. Further, I have made the ticks on the
>> colortable shorter to make it more compact.
>>
>> Please advice,
>>
>>
>> Kristofer
>>
>> --
>> Kristofer Tingdahl, Ph. D.
>> CEO
>> dGB Earth Sciences
>>
>> _______________________________________________
>> osg-submissions mailing list
>> [email protected]
>>
>> http://lists.openscenegraph.org/listinfo.cgi/osg-submissions-openscenegraph.org
>>
>>
>
> _______________________________________________
> osg-submissions mailing list
> [email protected]
>
> http://lists.openscenegraph.org/listinfo.cgi/osg-submissions-openscenegraph.org
>
>
--
Kristofer Tingdahl, Ph. D.
CEO
dGB Earth Sciences
/* OpenSceneGraph example, osgscalarbar.
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE.
*/
#include <osg/Geode>
#include <osg/ShapeDrawable>
#include <osg/Material>
#include <osg/Texture2D>
#include <osg/MatrixTransform>
#include <osg/PositionAttitudeTransform>
#include <osg/BlendFunc>
#include <osg/ClearNode>
#include <osg/Projection>
#include <osgUtil/CullVisitor>
#include <osgGA/TrackballManipulator>
#include <osgViewer/Viewer>
#include <osgDB/ReadFile>
#include <osgSim/ScalarsToColors>
#include <osgSim/ColorRange>
#include <osgSim/ScalarBar>
#include <sstream>
#include <iostream>
#include <math.h>
using namespace osgSim;
using osgSim::ScalarBar;
#if defined(_MSC_VER)
// not have to have this pathway for just VS6.0 as its unable to handle the full
// ScalarBar::ScalarPrinter::printScalar scoping.
// Create a custom scalar printer
struct MyScalarPrinter: public ScalarBar::ScalarPrinter
{
std::string printScalar(float scalar)
{
std::cout<<"In MyScalarPrinter::printScalar"<<std::endl;
if(scalar==0.0f) return ScalarPrinter::printScalar(scalar)+" Bottom";
else if(scalar==0.5f) return ScalarPrinter::printScalar(scalar)+" Middle";
else if(scalar==1.0f) return ScalarPrinter::printScalar(scalar)+" Top";
else return ScalarPrinter::printScalar(scalar);
}
};
#else
// Create a custom scalar printer
struct MyScalarPrinter: public ScalarBar::ScalarPrinter
{
std::string printScalar(float scalar)
{
std::cout<<"In MyScalarPrinter::printScalar"<<std::endl;
if(scalar==0.0f) return ScalarBar::ScalarPrinter::printScalar(scalar)+" Bottom";
else if(scalar==0.5f) return ScalarBar::ScalarPrinter::printScalar(scalar)+" Middle";
else if(scalar==1.0f) return ScalarBar::ScalarPrinter::printScalar(scalar)+" Top";
else return ScalarBar::ScalarPrinter::printScalar(scalar);
}
};
#endif
osg::Node* createScalarBar(bool vertical)
{
#if 1
//ScalarsToColors* stc = new ScalarsToColors(0.0f,1.0f);
//ScalarBar* sb = new ScalarBar(2,3,stc,"STC_ScalarBar");
// Create a custom color set
std::vector<osg::Vec4> cs;
cs.push_back(osg::Vec4(1.0f,0.0f,0.0f,1.0f)); // R
cs.push_back(osg::Vec4(0.0f,1.0f,0.0f,1.0f)); // G
cs.push_back(osg::Vec4(1.0f,1.0f,0.0f,1.0f)); // G
cs.push_back(osg::Vec4(0.0f,0.0f,1.0f,1.0f)); // B
cs.push_back(osg::Vec4(0.0f,1.0f,1.0f,1.0f)); // R
ColorRange* cr = new ColorRange(0.0f,1.0f,cs);
ScalarBar* sb = new ScalarBar(20, 11, cr,
vertical ? "Vertical" : "Horizontal",
vertical ? ScalarBar::VERTICAL : ScalarBar::HORIZONTAL,
0.1f, new MyScalarPrinter);
sb->setScalarPrinter(new MyScalarPrinter);
if ( !vertical )
{
sb->setPosition( osg::Vec3(0.5f,0.5f,0));
}
return sb;
#else
ScalarBar *sb = new ScalarBar;
ScalarBar::TextProperties tp;
tp._fontFile = "fonts/times.ttf";
sb->setTextProperties(tp);
return sb;
#endif
}
osg::Node * createScalarBar_HUD()
{
osgSim::ScalarBar * geode = new osgSim::ScalarBar;
osgSim::ScalarBar::TextProperties tp;
tp._fontFile = "fonts/times.ttf";
geode->setTextProperties(tp);
osg::StateSet * stateset = geode->getOrCreateStateSet();
stateset->setMode(GL_LIGHTING, osg::StateAttribute::OFF);
stateset->setMode(GL_DEPTH_TEST,osg::StateAttribute::OFF);
stateset->setRenderBinDetails(11, "RenderBin");
osg::MatrixTransform * modelview = new osg::MatrixTransform;
modelview->setReferenceFrame(osg::Transform::ABSOLUTE_RF);
osg::Matrixd matrix(osg::Matrixd::scale(1000,1000,1000) * osg::Matrixd::translate(120,10,0)); // I've played with these values a lot and it seems to work, but I have no idea why
modelview->setMatrix(matrix);
modelview->addChild(geode);
osg::Projection * projection = new osg::Projection;
projection->setMatrix(osg::Matrix::ortho2D(0,1280,0,1024)); // or whatever the OSG window res is
projection->addChild(modelview);
return projection; //make sure you delete the return sb line
}
int main(int , char **)
{
// construct the viewer.
osgViewer::Viewer viewer;
osg::Group* group = new osg::Group;
group->addChild(createScalarBar(true));
group->addChild(createScalarBar(false));
group->addChild(createScalarBar_HUD());
// add model to viewer.
viewer.setSceneData( group );
return viewer.run();
}
#include <osgSim/ScalarBar>
#include <osgText/Text>
#include <osg/Geometry>
#include <osg/Material>
#include <osg/PolygonOffset>
#include <sstream>
using namespace osgSim;
ScalarBar::~ScalarBar()
{
}
std::string ScalarBar::ScalarPrinter::printScalar(float scalar)
{
std::stringstream ostr;
ostr<<scalar;
return ostr.str();
}
void ScalarBar::setNumColors(int numColors)
{
_numColors = numColors;
createDrawables();
}
int ScalarBar::getNumColors() const
{
return _numColors;
}
void ScalarBar::setNumLabels(int numLabels)
{
_numLabels = numLabels;
createDrawables();
}
int ScalarBar::getNumLabels() const
{
return _numLabels;
}
void ScalarBar::setScalarsToColors(ScalarsToColors* stc)
{
_stc = stc;
createDrawables();
}
const ScalarsToColors* ScalarBar::getScalarsToColors() const
{
return _stc.get();
}
void ScalarBar::setTitle(const std::string& title)
{
_title = title;
createDrawables();
}
const std::string& ScalarBar::getTitle() const
{
return _title;
}
void ScalarBar::setPosition(const osg::Vec3& pos)
{
_position = pos;
createDrawables();
}
void ScalarBar::setWidth(float width)
{
_width = width;
createDrawables();
}
void ScalarBar::setOrientation(ScalarBar::Orientation orientation)
{
_orientation = orientation;
createDrawables();
}
ScalarBar::Orientation ScalarBar::getOrientation() const
{
return _orientation;
}
void ScalarBar::setAspectRatio(float aspectRatio)
{
_aspectRatio = aspectRatio;
createDrawables();
}
float ScalarBar::getAspectRatio() const
{
return _aspectRatio;
}
void ScalarBar::setScalarPrinter(ScalarPrinter* sp)
{
_sp = sp;
createDrawables();
}
const ScalarBar::ScalarPrinter* ScalarBar::getScalarPrinter() const
{
return _sp.get();
}
void ScalarBar::setTextProperties(const TextProperties& tp)
{
_textProperties = tp;
createDrawables();
}
const ScalarBar::TextProperties& ScalarBar::getTextProperties() const
{
return _textProperties;
}
void ScalarBar::createDrawables()
{
// Remove any existing Drawables
_drawables.erase(_drawables.begin(), _drawables.end());
if (_numColors==0) return;
osg::Matrix matrix;
if(_orientation==HORIZONTAL)
{
matrix = osg::Matrix::translate(_position);
}
else
{
matrix = osg::Matrix::rotate(osg::DegreesToRadians(90.0f),0.0f,0.0f,1.0f) * osg::Matrix::translate(_position);
}
// 1. First the bar
// =================
osg::ref_ptr<osg::Geometry> bar = new osg::Geometry();
// Create the bar - created in 'real' coordinate space the moment,
// with xyz values reflecting those of the actual scalar values in play.
// FIXME: Consider positioning at origin! Should be easy enough to do.
// Vertices
osg::ref_ptr<osg::Vec3Array> vs(new osg::Vec3Array);
vs->reserve(4*_numColors);
float incr = (_stc->getMax() - _stc->getMin()) / _numColors;
float xincr = (_width) / _numColors;
float arOffset = _width * _aspectRatio;
int i;
for(i=1; i<=_numColors; ++i)
{
vs->push_back(osg::Vec3((i-1) * xincr, 0.0f, 0.0f)*matrix);
vs->push_back(osg::Vec3((i-1) * xincr, arOffset, 0.0f)*matrix);
vs->push_back(osg::Vec3(i * xincr, arOffset, 0.0f)*matrix);
vs->push_back(osg::Vec3(i * xincr, 0.0f, 0.0f)*matrix);
}
bar->setVertexArray(vs.get());
// Colours
osg::ref_ptr<osg::Vec4Array> cs(new osg::Vec4Array);
cs->reserve(4*_numColors);
const float halfIncr = incr*0.5;
for(i=0; i<_numColors; ++i)
{
// We add half an increment to the color look-up to get the color
// square in the middle of the 'block'.
osg::Vec4 c = _stc->getColor(_stc->getMin() + (i*incr) + halfIncr);
cs->push_back(c);
cs->push_back(c);
cs->push_back(c);
cs->push_back(c);
}
bar->setColorArray(cs.get(), osg::Array::BIND_PER_VERTEX);
// Normal
osg::ref_ptr<osg::Vec3Array> ns(new osg::Vec3Array);
ns->push_back(osg::Matrix::transform3x3(osg::Vec3(0.0f,0.0f,1.0f),matrix));
bar->setNormalArray(ns.get(), osg::Array::BIND_OVERALL);
// The Quad strip that represents the bar
bar->addPrimitiveSet(new osg::DrawArrays(GL_QUADS,0,vs->size()));
bar->getOrCreateStateSet()->setAttributeAndModes( new osg::PolygonOffset(1,1),
osg::StateAttribute::OVERRIDE|osg::StateAttribute::ON );
addDrawable(bar.get());
#define CHARACTER_OFFSET_FACTOR (0.3f)
// 2. Then the text labels
// =======================
// Check the character size, if it's 0, estimate a good character size
float characterSize = _textProperties._characterSize;
if(characterSize == 0) characterSize = _width * 0.03f;
osgText::Font* font = osgText::readFontFile(_textProperties._fontFile.c_str());
std::vector<osgText::Text*> texts(_numLabels); // We'll need to collect pointers to these for later
float labelIncr = (_numLabels>0) ? (_stc->getMax()-_stc->getMin())/(_numLabels-1) : 0.0f;
float labelxIncr = (_numLabels>0) ? (_width)/(_numLabels-1) : 0.0f;
const float labelStickStartY = _orientation==HORIZONTAL ? arOffset : 0;
const float labelY = labelStickStartY +
(_orientation==HORIZONTAL ? characterSize : -characterSize) * CHARACTER_OFFSET_FACTOR;
for(i=0; i<_numLabels; ++i)
{
osgText::Text* text = new osgText::Text;
text->setFont(font);
text->setColor(_textProperties._color);
text->setFontResolution(_textProperties._fontResolution.first,_textProperties._fontResolution.second);
text->setCharacterSize(characterSize);
text->setText(_sp->printScalar(_stc->getMin()+(i*labelIncr)));
text->setPosition(osg::Vec3((i*labelxIncr), labelY, 0.0f)*matrix);
text->setAlignment( (_orientation==HORIZONTAL) ? osgText::Text::CENTER_BASE_LINE : osgText::Text::LEFT_CENTER);
addDrawable(text);
texts[i] = text;
}
// 3. The title
// ============
if(_title != "")
{
osgText::Text* text = new osgText::Text;
text->setFont(font);
text->setColor(_textProperties._color);
text->setFontResolution(_textProperties._fontResolution.first,_textProperties._fontResolution.second);
text->setCharacterSize(characterSize);
text->setText(_title);
osg::Vec3 titlePos;
if ( _orientation==HORIZONTAL )
{
const float titleY = (_numLabels>0) ? labelY + characterSize : labelY;
titlePos = osg::Vec3((_width/2.0f), titleY, 0.0f);
}
else
{
titlePos = osg::Vec3( _width, arOffset/2, 0 );
}
// Position the title at the middle of the bar above any labels.
text->setPosition(titlePos*matrix);
text->setAlignment(
_orientation==HORIZONTAL ? osgText::Text::CENTER_BASE_LINE : osgText::Text::CENTER_BOTTOM);
addDrawable(text);
}
// 4. The rectangular border and sticks
// ====================================
osg::ref_ptr<osg::Vec3Array> annotVertices = new osg::Vec3Array;
//Border
annotVertices->push_back( osg::Vec3(0.0f,0.0f,0.0f) * matrix );
annotVertices->push_back( osg::Vec3(0.0f,arOffset,0.0f) * matrix );
annotVertices->push_back( osg::Vec3(0.0f,arOffset,0.0f) * matrix );
annotVertices->push_back( osg::Vec3(_width,arOffset,0.0f) * matrix );
annotVertices->push_back( osg::Vec3(_width,arOffset,0.0f) * matrix );
annotVertices->push_back( osg::Vec3(_width,0.0f,0.0f) * matrix );
annotVertices->push_back( osg::Vec3(_width,0.0f,0.0f) * matrix );
annotVertices->push_back( osg::Vec3(0.0f,0.0f,0.0f) * matrix );
//Sticks
for(i=0; i<_numLabels; ++i)
{
const osg::Vec3 p1(osg::Vec3((i*labelxIncr), labelStickStartY, 0.0f)*matrix);
const osg::Vec3 p2(osg::Vec3((i*labelxIncr), labelY, 0.0f)*matrix);
annotVertices->push_back( p1 );
annotVertices->push_back( p2 );
}
osg::ref_ptr<osg::Geometry> annotationGeom = new osg::Geometry();
annotationGeom->addPrimitiveSet( new osg::DrawArrays(GL_LINES,0,annotVertices->size()) );
annotationGeom->setVertexArray( annotVertices.get() );
osg::ref_ptr<osg::Material> annotMaterial = new osg::Material;
annotMaterial->setDiffuse( osg::Material::FRONT, _textProperties._color );
annotationGeom->getOrCreateStateSet()->setAttribute( annotMaterial.get() );
addDrawable( annotationGeom.get() );
}
_______________________________________________
osg-submissions mailing list
[email protected]
http://lists.openscenegraph.org/listinfo.cgi/osg-submissions-openscenegraph.org