Add preliminary spot light animation
This commit is contained in:
parent
d393e4a019
commit
5a96b283f6
118
simgear/scene/model/SGLightAnimation.cxx
Normal file
118
simgear/scene/model/SGLightAnimation.cxx
Normal file
@ -0,0 +1,118 @@
|
|||||||
|
// Copyright (C) 2011 Frederic Bouvier (fredfgfs01@free.fr)
|
||||||
|
//
|
||||||
|
// This library is free software; you can redistribute it and/or
|
||||||
|
// modify it under the terms of the GNU Library General Public
|
||||||
|
// License as published by the Free Software Foundation; either
|
||||||
|
// version 2 of the License, or (at your option) any later version.
|
||||||
|
//
|
||||||
|
// This library is distributed in the hope that it will be useful,
|
||||||
|
// but WITHOUT ANY WARRANTY; without even the implied warranty of
|
||||||
|
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
|
||||||
|
// Library General Public License for more details.
|
||||||
|
//
|
||||||
|
// You should have received a copy of the GNU General Public License
|
||||||
|
// along with this program; if not, write to the Free Software
|
||||||
|
// Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
|
||||||
|
//
|
||||||
|
|
||||||
|
#ifdef HAVE_CONFIG_H
|
||||||
|
# include <simgear_config.h>
|
||||||
|
#endif
|
||||||
|
|
||||||
|
#include "animation.hxx"
|
||||||
|
#include "ConditionNode.hxx"
|
||||||
|
|
||||||
|
#include <osg/Geometry>
|
||||||
|
#include <osg/MatrixTransform>
|
||||||
|
#include <simgear/scene/material/EffectGeode.hxx>
|
||||||
|
#include <boost/scoped_array.hpp>
|
||||||
|
|
||||||
|
SGLightAnimation::SGLightAnimation(const SGPropertyNode* configNode,
|
||||||
|
SGPropertyNode* modelRoot) :
|
||||||
|
SGAnimation(configNode, modelRoot)
|
||||||
|
{
|
||||||
|
}
|
||||||
|
|
||||||
|
osg::Group*
|
||||||
|
SGLightAnimation::createAnimationGroup(osg::Group& parent)
|
||||||
|
{
|
||||||
|
osg::MatrixTransform* grp = new osg::MatrixTransform;
|
||||||
|
osg::Vec3 position( getConfig()->getDoubleValue("position/x-m"),
|
||||||
|
getConfig()->getDoubleValue("position/y-m"),
|
||||||
|
getConfig()->getDoubleValue("position/z-m") );
|
||||||
|
grp->setMatrix(osg::Matrix::translate(position));
|
||||||
|
parent.addChild(grp);
|
||||||
|
grp->setNodeMask( simgear::MODELLIGHT_BIT );
|
||||||
|
return grp;
|
||||||
|
}
|
||||||
|
|
||||||
|
void
|
||||||
|
SGLightAnimation::install(osg::Node& node)
|
||||||
|
{
|
||||||
|
SGAnimation::install(node);
|
||||||
|
|
||||||
|
std::string light_type = getConfig()->getStringValue("light-type");
|
||||||
|
if (light_type == "spot") {
|
||||||
|
osg::Vec3 axis( getConfig()->getDoubleValue("axis/x"),
|
||||||
|
getConfig()->getDoubleValue("axis/y"),
|
||||||
|
getConfig()->getDoubleValue("axis/z") );
|
||||||
|
double l = axis.length();
|
||||||
|
if (l < 0.001) return;
|
||||||
|
axis /= l;
|
||||||
|
|
||||||
|
osg::Vec3 p1( axis.z(), axis.x(), axis.y() ),
|
||||||
|
p2 = axis ^ p1;
|
||||||
|
p1 = p2 ^ axis;
|
||||||
|
|
||||||
|
float n = getConfig()->getFloatValue("near-m"),
|
||||||
|
f = getConfig()->getFloatValue("far-m"),
|
||||||
|
a1 = getConfig()->getFloatValue("angle-inner-deg"),
|
||||||
|
a2 = getConfig()->getFloatValue("angle-outer-deg"),
|
||||||
|
r1 = n * tan( a2 * SG_DEGREES_TO_RADIANS ),
|
||||||
|
r2 = f * tan( a2 * SG_DEGREES_TO_RADIANS );
|
||||||
|
|
||||||
|
osg::Geometry* cone = new osg::Geometry;
|
||||||
|
cone->setUseDisplayList(false);
|
||||||
|
osg::Vec3Array* vertices = new osg::Vec3Array(36);
|
||||||
|
(*vertices)[0] = osg::Vec3(0.0,0.0,0.0);
|
||||||
|
for (int i=0; i<16; ++i) {
|
||||||
|
(*vertices)[16-i] = axis*f + p1*r2*cos( i * 2 * M_PI / 16 ) + p2*r2*sin( i * 2 * M_PI / 16 );
|
||||||
|
}
|
||||||
|
(*vertices)[17] = (*vertices)[1];
|
||||||
|
|
||||||
|
// Bottom
|
||||||
|
(*vertices)[18] = axis*f;
|
||||||
|
for (int i=0; i<16; ++i) {
|
||||||
|
(*vertices)[19+i] = axis*f + p1*r2*cos( i * 2 * M_PI / 16 ) + p2*r2*sin( i * 2 * M_PI / 16 );
|
||||||
|
}
|
||||||
|
(*vertices)[35] = (*vertices)[19];
|
||||||
|
|
||||||
|
osg::Vec4Array* colours = new osg::Vec4Array(1);
|
||||||
|
(*colours)[0].set( getConfig()->getFloatValue("color/red"),
|
||||||
|
getConfig()->getFloatValue("color/green"),
|
||||||
|
getConfig()->getFloatValue("color/blue"),
|
||||||
|
1.0f);
|
||||||
|
cone->setColorArray(colours);
|
||||||
|
cone->setColorBinding(osg::Geometry::BIND_OVERALL);
|
||||||
|
|
||||||
|
osg::Vec3Array* normals = new osg::Vec3Array(1);
|
||||||
|
(*normals)[0] = axis;
|
||||||
|
cone->setNormalArray(normals);
|
||||||
|
cone->setNormalBinding(osg::Geometry::BIND_OVERALL);
|
||||||
|
|
||||||
|
cone->setVertexArray(vertices);
|
||||||
|
cone->addPrimitiveSet( new osg::DrawArrays( GL_TRIANGLE_FAN, 0, 18 ) );
|
||||||
|
cone->addPrimitiveSet( new osg::DrawArrays( GL_TRIANGLE_FAN, 18, 18 ) );
|
||||||
|
|
||||||
|
simgear::EffectGeode* geode = new simgear::EffectGeode;
|
||||||
|
geode->addDrawable( cone );
|
||||||
|
|
||||||
|
node.asGroup()->addChild( geode );
|
||||||
|
simgear::Effect *effect = simgear::makeEffect("Effects/light-spot", true);
|
||||||
|
if (effect) {
|
||||||
|
effect->parametersProp->setFloatValue("inner-angle",getConfig()->getFloatValue("angle-inner-deg"));
|
||||||
|
effect->parametersProp->setFloatValue("outer-angle",getConfig()->getFloatValue("angle-outer-deg"));
|
||||||
|
geode->setEffect(effect);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
}
|
@ -427,6 +427,7 @@ sgLoad3DModel_internal(const SGPath& path,
|
|||||||
}
|
}
|
||||||
PropertyList effect_nodes = props->getChildren("effect");
|
PropertyList effect_nodes = props->getChildren("effect");
|
||||||
PropertyList animation_nodes = props->getChildren("animation");
|
PropertyList animation_nodes = props->getChildren("animation");
|
||||||
|
PropertyList light_nodes = props->getChildren("light");
|
||||||
// Some material animations (eventually all) are actually effects.
|
// Some material animations (eventually all) are actually effects.
|
||||||
makeEffectAnimations(animation_nodes, effect_nodes);
|
makeEffectAnimations(animation_nodes, effect_nodes);
|
||||||
{
|
{
|
||||||
|
@ -465,6 +465,9 @@ SGAnimation::animate(osg::Node* node, const SGPropertyNode* configNode,
|
|||||||
} else if (type == "translate") {
|
} else if (type == "translate") {
|
||||||
SGTranslateAnimation animInst(configNode, modelRoot);
|
SGTranslateAnimation animInst(configNode, modelRoot);
|
||||||
animInst.apply(node);
|
animInst.apply(node);
|
||||||
|
} else if (type == "light") {
|
||||||
|
SGLightAnimation animInst(configNode, modelRoot);
|
||||||
|
animInst.apply(node);
|
||||||
} else if (type == "null" || type == "none" || type.empty()) {
|
} else if (type == "null" || type == "none" || type.empty()) {
|
||||||
SGGroupAnimation animInst(configNode, modelRoot);
|
SGGroupAnimation animInst(configNode, modelRoot);
|
||||||
animInst.apply(node);
|
animInst.apply(node);
|
||||||
|
@ -343,4 +343,18 @@ private:
|
|||||||
class VncCallback;
|
class VncCallback;
|
||||||
};
|
};
|
||||||
|
|
||||||
|
|
||||||
|
//////////////////////////////////////////////////////////////////////
|
||||||
|
// Light animation
|
||||||
|
//////////////////////////////////////////////////////////////////////
|
||||||
|
|
||||||
|
class SGLightAnimation : public SGAnimation {
|
||||||
|
public:
|
||||||
|
SGLightAnimation(const SGPropertyNode* configNode,
|
||||||
|
SGPropertyNode* modelRoot);
|
||||||
|
virtual osg::Group* createAnimationGroup(osg::Group& parent);
|
||||||
|
virtual void install(osg::Node& node);
|
||||||
|
private:
|
||||||
|
};
|
||||||
|
|
||||||
#endif // _SG_ANIMATION_HXX
|
#endif // _SG_ANIMATION_HXX
|
||||||
|
@ -43,7 +43,8 @@ enum NodeMask {
|
|||||||
BACKGROUND_BIT = (1 << 11),
|
BACKGROUND_BIT = (1 << 11),
|
||||||
// Everything else that isn't terrain. Initially for clouds;
|
// Everything else that isn't terrain. Initially for clouds;
|
||||||
// eventually for other models?
|
// eventually for other models?
|
||||||
MODEL_BIT = (1 << 12)
|
MODEL_BIT = (1 << 12),
|
||||||
|
MODELLIGHT_BIT = (1 << 13)
|
||||||
};
|
};
|
||||||
|
|
||||||
// Theory of bin numbering:
|
// Theory of bin numbering:
|
||||||
|
Loading…
Reference in New Issue
Block a user