OSGLightChunk.cpp

Go to the documentation of this file.
00001 /*---------------------------------------------------------------------------*\
00002  *                                OpenSG                                     *
00003  *                                                                           *
00004  *                                                                           *
00005  *             Copyright (C) 2000-2002 by the OpenSG Forum                   *
00006  *                                                                           *
00007  *                            www.opensg.org                                 *
00008  *                                                                           *
00009  *   contact: dirk@opensg.org, gerrit.voss@vossg.org, jbehr@zgdv.de          *
00010  *                                                                           *
00011 \*---------------------------------------------------------------------------*/
00012 /*---------------------------------------------------------------------------*\
00013  *                                License                                    *
00014  *                                                                           *
00015  * This library is free software; you can redistribute it and/or modify it   *
00016  * under the terms of the GNU Library General Public License as published    *
00017  * by the Free Software Foundation, version 2.                               *
00018  *                                                                           *
00019  * This library is distributed in the hope that it will be useful, but       *
00020  * WITHOUT ANY WARRANTY; without even the implied warranty of                *
00021  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU         *
00022  * Library General Public License for more details.                          *
00023  *                                                                           *
00024  * You should have received a copy of the GNU Library General Public         *
00025  * License along with this library; ifnot, write to the Free Software       *
00026  * Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.                 *
00027  *                                                                           *
00028 \*---------------------------------------------------------------------------*/
00029 /*---------------------------------------------------------------------------*\
00030  *                                Changes                                    *
00031  *                                                                           *
00032  *                                                                           *
00033  *                                                                           *
00034  *                                                                           *
00035  *                                                                           *
00036  *                                                                           *
00037 \*---------------------------------------------------------------------------*/
00038
00039 //---------------------------------------------------------------------------
00040 //  Includes
00041 //---------------------------------------------------------------------------
00042
00043 #include <cstdlib>
00044 #include <cstdio>
00045
00046 #include "OSGConfig.h"
00047
00048 #include "OSGGL.h"
00049 #include "OSGGLU.h"
00050
00051 #include "OSGMatrix.h"
00052 #include "OSGNode.h"
00053 #include "OSGLightChunk.h"
00054 #include "OSGDrawEnv.h"
00055
00056 OSG_USING_NAMESPACE
00057
00058 // Documentation for this class is emited in the
00059 // OSGLightChunkBase.cpp file.
00060 // To modify it, please change the .fcd file (OSGLightChunk.fcd) and
00061 // regenerate the base file.
00062
00063 /***************************************************************************\
00064  *                           Class variables                               *
00065 \***************************************************************************/
00066
00067 StateChunkClass LightChunk::_class("Light", 8);
00068
00069 /***************************************************************************\
00070  *                           Class methods                                 *
00071 \***************************************************************************/
00072
00073 /*-------------------------------------------------------------------------*\
00074  -  private                                                                -
00075 \*-------------------------------------------------------------------------*/
00076
00077 void LightChunk::initMethod(InitPhase ePhase)
00078 {
00079     Inherited::initMethod(ePhase);
00080 }
00081
00082 /***************************************************************************\
00083  *                           Instance methods                              *
00084 \***************************************************************************/
00085
00086 /*-------------------------------------------------------------------------*\
00087  -  public                                                                 -
00088 \*-------------------------------------------------------------------------*/
00089
00090
00091 /*------------- constructors & destructors --------------------------------*/
00092
00093 LightChunk::LightChunk(void) :
00094     Inherited()
00095 {
00096 }
00097
00098 LightChunk::LightChunk(const LightChunk &source) :
00099     Inherited(source)
00100 {
00101 }
00102
00103 LightChunk::~LightChunk(void)
00104 {
00105 }
00106
00107 /*------------------------- Chunk Class Access ---------------------------*/
00108
00109 const StateChunkClass *LightChunk::getClass(void) const
00110 {
00111     return &_class;
00112 }
00113
00114 /*------------------------------- Sync -----------------------------------*/
00115
00116 void LightChunk::changed(ConstFieldMaskArg whichField,
00117                          UInt32            origin,
00118                          BitVector         details)
00119 {
00120     Inherited::changed(whichField, origin, details);
00121 }
00122
00123 /*------------------------------ Output ----------------------------------*/
00124
00125 void LightChunk::dump(      UInt32    OSG_CHECK_ARG(uiIndent),
00126                       const BitVector OSG_CHECK_ARG(bvFlags )) const
00127 {
00128     SLOG << "Dump LightChunk NI" << std::endl;
00129 }
00130
00131
00132 /*------------------------------ State ------------------------------------*/
00133
00134 void LightChunk::activate(DrawEnv *pEnv, UInt32 index)
00135 {
00136     glErr("light:activate:precheck");
00137
00138     Matrixr tobeacon;
00139
00140     if(_sfBeacon.getValue() != NULL)
00141     {
00142         _sfBeacon.getValue()->getToWorld(tobeacon);
00143     }
00144     else
00145     {
00146         tobeacon.setIdentity();
00147     }
00148
00149     Matrixr cameraMat = pEnv->getCameraViewing();
00150
00151     cameraMat.mult(tobeacon);
00152
00153
00154     glPushMatrix();
00155     GLP::glLoadMatrixf(cameraMat.getValues());
00156
00157
00158     GLP::glLightfv( GL_LIGHT0 + index,
00159                     GL_DIFFUSE,
00160                    _sfDiffuse.getValue().getValuesRGBA());
00161
00162     GLP::glLightfv( GL_LIGHT0 + index,
00163                     GL_AMBIENT,
00164                    _sfAmbient.getValue().getValuesRGBA());
00165
00166     GLP::glLightfv( GL_LIGHT0 + index,
00167                     GL_SPECULAR,
00168                    _sfSpecular.getValue().getValuesRGBA());
00169     GLP::glLightfv( GL_LIGHT0 + index,
00170                     GL_POSITION,
00171                    _sfPosition.getValue().getValues());
00172
00173     GLP::glLightf ( GL_LIGHT0 + index,
00174                     GL_CONSTANT_ATTENUATION,
00175                    _sfConstantAttenuation.getValue());
00176
00177     GLP::glLightf ( GL_LIGHT0 + index,
00178                     GL_LINEAR_ATTENUATION,
00179                    _sfLinearAttenuation.getValue());
00180
00181     GLP::glLightf ( GL_LIGHT0 + index,
00182                     GL_QUADRATIC_ATTENUATION,
00183                    _sfQuadraticAttenuation.getValue());
00184
00185     GLP::glLightf( GL_LIGHT0 + index,
00186                    GL_SPOT_CUTOFF,
00187                   _sfCutoff.getValue());
00188
00189     if(_sfCutoff.getValue() < 180.f)
00190     {
00191         GLP::glLightfv( GL_LIGHT0 + index,
00192                         GL_SPOT_DIRECTION,
00193                        _sfDirection.getValue().getValues());
00194
00195         GLP::glLightf( GL_LIGHT0 + index,
00196                        GL_SPOT_EXPONENT,
00197                       _sfExponent.getValue());
00198     }
00199
00200     glEnable(GL_LIGHT0 + index);
00201
00202     glPopMatrix();
00203
00204     glErr("light:activate:postcheck");
00205 }
00206
00207 void LightChunk::changeFrom(DrawEnv    *pEnv,
00208                             StateChunk *old_chunk,
00209                             UInt32      index    )
00210 {
00211     glErr("light:changed:precheck");
00212
00213     LightChunk const *old = dynamic_cast<LightChunk const *>(old_chunk);
00214
00215     // change from me to me?
00216     // this assumes I haven't changed in the meantime. is that a valid 
00217     // assumption?
00218
00219     if(old == this)
00220         return;
00221
00222     Matrixr tobeacon;
00223
00224     if(_sfBeacon.getValue() != NULL)
00225     {
00226         _sfBeacon.getValue()->getToWorld(tobeacon);
00227     }
00228     else
00229     {
00230         tobeacon.setIdentity();
00231     }
00232
00233     Matrixr cameraMat = pEnv->getCameraViewing();
00234
00235     cameraMat.mult(tobeacon);
00236
00237     glPushMatrix();
00238     GLP::glLoadMatrixf(cameraMat.getValues());
00239
00240     // it could theoretically be more efficient to turn the light off before
00241     // changing its parameters, have to try that sometime
00242
00243     GLP::glLightfv( GL_LIGHT0 + index,
00244                     GL_DIFFUSE,
00245                    _sfDiffuse.getValue().getValuesRGBA());
00246
00247     GLP::glLightfv( GL_LIGHT0 + index,
00248                     GL_AMBIENT,
00249                    _sfAmbient.getValue().getValuesRGBA());
00250
00251     GLP::glLightfv( GL_LIGHT0 + index,
00252                     GL_SPECULAR,
00253                    _sfSpecular.getValue().getValuesRGBA());
00254
00255     GLP::glLightfv( GL_LIGHT0 + index,
00256                     GL_POSITION,
00257                    _sfPosition.getValue().getValues());
00258
00259     GLP::glLightf ( GL_LIGHT0 + index,
00260                     GL_CONSTANT_ATTENUATION,
00261                    _sfConstantAttenuation.getValue());
00262
00263     GLP::glLightf ( GL_LIGHT0 + index,
00264                     GL_LINEAR_ATTENUATION,
00265                    _sfLinearAttenuation.getValue());
00266
00267     GLP::glLightf ( GL_LIGHT0 + index,
00268                     GL_QUADRATIC_ATTENUATION,
00269                    _sfQuadraticAttenuation.getValue());
00270
00271     GLP::glLightf( GL_LIGHT0 + index,
00272                    GL_SPOT_CUTOFF,
00273                   _sfCutoff.getValue());
00274
00275     if(_sfCutoff.getValue() < 180.f)
00276     {
00277         GLP::glLightfv( GL_LIGHT0 + index,
00278                         GL_SPOT_DIRECTION,
00279                        _sfDirection.getValue().getValues());
00280
00281         GLP::glLightf( GL_LIGHT0 + index,
00282                        GL_SPOT_EXPONENT,
00283                       _sfExponent.getValue());
00284     }
00285
00286     glPopMatrix();
00287
00288     glErr("light:changed:postcheck");
00289 }
00290
00291 void LightChunk::deactivate(DrawEnv *, UInt32 index)
00292 {
00293     glDisable(GL_LIGHT0 + index);
00294 }
00295
00296
00297 /*-------------------------- Comparison -----------------------------------*/
00298
00299 Real32 LightChunk::switchCost(StateChunk *OSG_CHECK_ARG(chunk))
00300 {
00301     return 0;
00302 }
00303
00304 bool LightChunk::operator < (const StateChunk &other) const
00305 {
00306     return this < &other;
00307 }
00308
00309 bool LightChunk::operator == (const StateChunk &other) const
00310 {
00311     LightChunk const *tother = dynamic_cast<LightChunk const*>(&other);
00312
00313     if(!tother)
00314         return false;
00315
00316     if(tother == this)
00317         return true;
00318
00319     if(!getAmbient  ().equals(tother->getAmbient  (), Eps) ||
00320        !getDiffuse  ().equals(tother->getDiffuse  (), Eps) ||
00321        !getSpecular ().equals(tother->getSpecular (), Eps) ||
00322        !getPosition ().equals(tother->getPosition (), Eps) ||
00323        !getDirection().equals(tother->getDirection(), Eps) ||
00324
00325         getConstantAttenuation () != tother->getConstantAttenuation () ||
00326         getLinearAttenuation   () != tother->getLinearAttenuation   () ||
00327         getQuadraticAttenuation() != tother->getQuadraticAttenuation() ||
00328         getCutoff              () != tother->getCutoff              () ||
00329         getExponent            () != tother->getExponent            ()
00330       )
00331     {
00332         return false;
00333     }
00334
00335     return true;
00336 }
00337
00338 bool LightChunk::operator != (const StateChunk &other) const
00339 {
00340     return ! (*this == other);
00341 }