void sceneLightEnum(INode* node, SContext* sc, MtlBaseLib* mtls) { // For each child of this node, we recurse into ourselves // until no more children are found. for (int c = 0; c < node->NumberOfChildren(); c++) { sceneLightEnum(node->GetChildNode(c), sc, mtls); } // Get the ObjectState. // The ObjectState is the structure that flows up the pipeline. // It contains a matrix, a material index, some flags for channels, // and a pointer to the object in the pipeline. ObjectState ostate = node->EvalWorldState(0); if (ostate.obj==NULL) return; // Examine the superclass ID in order to figure out what kind // of object we are dealing with. if (ostate.obj->SuperClassID() == LIGHT_CLASS_ID) { // Get the light object from the ObjectState LightObject *light = (LightObject*)ostate.obj; // Is this light turned on? if (light->GetUseLight()) { // Create a RenderLight and append it to our list of lights // to fix compiler error LightInfo* li = new LightInfo(node, mtls); sc->lightTab.Append(1, &(li)); //sc->lightTab.Append(1, &(new LightInfo(node, mtls))); } } }
int DirLight::Update(TimeValue t, const RendContext &rc, RenderGlobalContext *rgc, BOOL shadows, BOOL shadowGeomChanged) { int res = 1; BaseObjLight::Update(t,rc,rgc,shadows,shadowGeomChanged); hotsz = ls.hotsize; fallsz = ls.fallsize; fallsq = fallsz*fallsz; hotpct = ls.hotsize/ls.fallsize; ihotpct = 1.0f - hotpct; ObjectState os = inode->EvalWorldState(t); LightObject* lob = (LightObject *)os.obj; assert(os.obj->SuperClassID()==LIGHT_CLASS_ID); plRTDirLight* gl = (lob->GetInterface(I_MAXSCRIPTPLUGIN) != NULL) ? (plRTDirLight*)lob->GetReference(0) : (plRTDirLight*)lob; // JBW 4/7/99 //projector = gl->GetProjector(); aspect = 1.0f; //if (projector){ // projMap = gl->GetProjMap(); // if( projMap ) projMap->Update(t,FOREVER); // } return res; };
int OmniLight::Update(TimeValue t, const RendContext & rc, RenderGlobalContext *rgc, BOOL shadows, BOOL shadowGeomChanged) { BaseObjLight::Update(t,rc,rgc,shadows,shadowGeomChanged); ObjectState os = inode->EvalWorldState(t); LightObject* lob = (LightObject *)os.obj; assert(os.obj->SuperClassID()==LIGHT_CLASS_ID); plRTOmniLight* gl = (lob->GetInterface(I_MAXSCRIPTPLUGIN) != NULL) ? (plRTOmniLight*)lob->GetReference(0) : (plRTOmniLight*)lob; // JBW 4/7/99 decayType = gl->GetDecayType(); decayRadius = gl->GetDecayRadius(t); fov = HALFPI; // 90 degree fov int res=1; if(gl->GetTex()) gl->GetTex()->Update(t, FOREVER); //projector = gl->GetProjector(); //if (projector){ // projMap = gl->GetProjMap(); // if( projMap ) projMap->Update(t,FOREVER); //} return res; }
LightObject* Level::createLight( Vec2f const& pos ,float radius ) { LightObject* light = new LightObject(); light->init(); light->setPos( pos ); light->radius = radius; mLights.push_back( light ); addObjectInternal( light ); return light; }
LightObject* CreationTool::CreateLightObject(XMFLOAT3 position) { LightObject* lightObject = new LightObject(); lightObject->SetName("Light"); lightObject->SetMaterials(Material(Colors::White, Colors::White, XMFLOAT4(229/255.0f, 106/255.0f, 5.0f/255.0f, 1.0f))); lightObject->SetRotation(XMFLOAT3(0.3f, -1.0f, 0.0f)); lightObject->SetLightType(SPOT_LIGHT); lightObject->SetAtt(0, 0.1, 0); lightObject->SetRange(2000.0f); lightObject->SetSpot(16.0f); lightObject->SetPosition(position); lightObject->SetIntensity(0.2f, 1.0f, 0.2f); return lightObject; }
int SpotLight::Update(TimeValue t, const RendContext &rc, RenderGlobalContext *rgc, BOOL shadows, BOOL shadowGeomChanged) { int res = 1; BaseObjLight::Update(t,rc,rgc,shadows, shadowGeomChanged); float hs = DegToRad(ls.hotsize); float fs = DegToRad(ls.fallsize); fall_tan = (float)tan(fs/2.0f); hot_cos = (float)cos(hs/2.0f); fall_cos =(float)cos(fs/2.0f); fall_sin = (float)sin(fs/2.0f); hotpct = ls.hotsize/ls.fallsize; ihotpct = 1.0f - hotpct; ObjectState os = inode->EvalWorldState(t); LightObject* lob = (LightObject *)os.obj; assert(os.obj->SuperClassID()==LIGHT_CLASS_ID); plRTLightBase* gl = (lob->GetInterface(I_MAXSCRIPTPLUGIN) != NULL) ? (plRTLightBase*)lob->GetReference(0) : (plRTLightBase*)lob; // JBW 4/7/99 decayType = gl->GetDecayType(); decayRadius = gl->GetDecayRadius(t); projector = gl->GetProjector(); fov = std::max(fs, hs); float aspect = 1.0f; fov = 2.0f* (float)atan(tan(fov*0.5f)*sqrt(aspect)); zfac = -sz2 /(float)tan(0.5*(double)fov); xscale = zfac; yscale = -zfac*aspect; curve =(float)fabs(1.0f/xscale); rectv0.y = fall_sin * (float)sqrt(aspect); rectv1.y = fall_sin / (float)sqrt(aspect); rectv0.x = rectv1.x = fall_cos; rectv0 = Normalize(rectv0); rectv1 = Normalize(rectv1); Interval v; if (projector){ projMap = gl->GetProjMap(); if( projMap ) projMap->Update(t,v); } return res; }
//------------------------------ LightObject* LightImporter::createSkyLight( const COLLADAFW::Light* light, const SkyLightParameters* skyLightParameters ) { void* lightMaxObject = createMaxObject(LIGHT_CLASS_ID, SKY_LIGHT_CLASS_ID); LightObject* skyLight = (LightObject*)lightMaxObject; IParamBlock2* skyLightParams = (IParamBlock2*) skyLight->GetReference(MaxLight::PBLOCK_REF_SKY); Point3 color = toMaxPoint3(light->getColor()); // param id documented in const Extra::ExtraParameter LightExporter::SKYLIGHT_PARAMETERS skyLightParams->SetValue(0, 0, color); skyLightParams->SetValue(1, 0, skyLightParameters->colorMapAmount); skyLightParams->SetValue(3, 0, skyLightParameters->colorMapOn); skyLightParams->SetValue(4, 0, skyLightParameters->raysPerSample); skyLightParams->SetValue(7, 0, skyLightParameters->mode); skyLightParams->SetValue(10, 0, skyLightParameters->multiplier); skyLightParams->SetValue(11, 0, skyLightParameters->rayBias); skyLightParams->SetValue(12, 0, skyLightParameters->castShadows); skyLightParams->SetValue(13, 0, skyLightParameters->intensityOn); return skyLight; }
//--------------------------------------------------------------- void LightExporter::exportLight( ExportNode* exportNode ) { if ( !exportNode->getIsInVisualScene() ) return; String lightId = getLightId(*exportNode); INode * iNode = exportNode->getINode(); LightObject* lightObject = (LightObject*) (iNode->GetObjectRef()); if ( !lightObject ) return; if ( mDocumentExporter->isExportedObject(ObjectIdentifier(lightObject)) ) return; mDocumentExporter->insertExportedObject(ObjectIdentifier(lightObject), exportNode); // Retrieve the target node, if we are not baking matrices. // Baked matrices must always sample the transform! ULONG ClassId = lightObject->ClassID().PartA(); bool isTargeted = !mDocumentExporter->getOptions().getBakeMatrices() && (ClassId == SPOT_LIGHT_CLASS_ID || ClassId == TDIR_LIGHT_CLASS_ID); INode* targetNode = isTargeted ? iNode->GetTarget() : 0; // some lights are not supported at all switch (ClassId) { case FSPOT_LIGHT_CLASS_ID: case SPOT_LIGHT_CLASS_ID: case DIR_LIGHT_CLASS_ID: case TDIR_LIGHT_CLASS_ID: case SKY_LIGHT_CLASS_ID_PART_A: case OMNI_LIGHT_CLASS_ID: break; default: return; } // Determine the light's type bool isSpot = false; bool isDirectional = false; bool isPoint = false; bool isSky = false; COLLADASW::Light::LightType lightType; switch (ClassId) { case FSPOT_LIGHT_CLASS_ID: case SPOT_LIGHT_CLASS_ID: lightType = COLLADASW::Light::SPOT; isSpot = true; break; case DIR_LIGHT_CLASS_ID: case TDIR_LIGHT_CLASS_ID: lightType = COLLADASW::Light::DIRECTIONAL; isDirectional = true; break; case SKY_LIGHT_CLASS_ID_PART_A: lightType = COLLADASW::Light::POINT; isSky = true; break; case OMNI_LIGHT_CLASS_ID: lightType = COLLADASW::Light::POINT; isPoint = true; break; } COLLADASW::Light * colladaLight = 0; switch ( lightType ) { case COLLADASW::Light::DIRECTIONAL: colladaLight = new COLLADASW::DirectionalLight(COLLADASW::LibraryLights::mSW, lightId, COLLADASW::Utils::checkNCName(NativeString(exportNode->getINode()->GetName()))); break; case COLLADASW::Light::POINT: colladaLight = new COLLADASW::PointLight(COLLADASW::LibraryLights::mSW, lightId, COLLADASW::Utils::checkNCName(NativeString(exportNode->getINode()->GetName()))); break; case COLLADASW::Light::SPOT: colladaLight = new COLLADASW::SpotLight(COLLADASW::LibraryLights::mSW, lightId, COLLADASW::Utils::checkNCName(NativeString(exportNode->getINode()->GetName()))); break; } // Retrieve the parameter block IParamBlock* parameters = 0; IParamBlock2* parametersSky = 0; if (isSky) parametersSky = (IParamBlock2*) lightObject->GetReference(MaxLight::PBLOCK_REF_SKY); else parameters = (IParamBlock*) lightObject->GetReference(MaxLight::PBLOCK_REF); if (!parameters && !parametersSky) { delete colladaLight; return; } if (parameters) { bool hasAnimatedColor = mAnimationExporter->addAnimatedParameter(parameters, MaxLight::PB_COLOR, lightId, colladaLight->getColorDefaultSid(), 0 ); colladaLight->setColor(EffectExporter::maxColor2Color(parameters->GetColor(MaxLight::PB_COLOR)), hasAnimatedColor); } else if (parametersSky ) { bool hasAnimatedColor = mAnimationExporter->addAnimatedParameter(parametersSky, MaxLight::PB_SKY_COLOR, lightId, colladaLight->getColorDefaultSid(), 0 ); colladaLight->setColor(EffectExporter::maxColor2Color(parametersSky->GetColor(MaxLight::PB_SKY_COLOR)), hasAnimatedColor); } if (isSpot || isPoint) { int decayFunction = parameters->GetInt(isPoint ? MaxLight::PB_DECAY : MaxLight::PB_OMNIDECAY, mDocumentExporter->getOptions().getAnimationStart()); switch (decayFunction) { case 1: colladaLight->setConstantAttenuation(0.0f); colladaLight->setLinearAttenuation(1.0f); break; case 2: colladaLight->setConstantAttenuation(0.0f); colladaLight->setQuadraticAttenuation(1.0f); break; case 0: default: colladaLight->setConstantAttenuation(1.0f); break; } } else if (isSky) { colladaLight->setConstantAttenuation(1.0f); } setExtraTechnique(colladaLight); if ( parameters ) addParamBlockAnimatedExtraParameters(LIGHT_ELEMENT, LIGHT_PARAMETERS, LIGHT_PARAMETER_COUNT, parameters, lightId); else addParamBlockAnimatedExtraParameters(SKYLIGHT_ELEMENT, SKYLIGHT_PARAMETERS, SKYLIGHT_PARAMETER_COUNT, parametersSky, lightId); // add all the information to extra tag, that are not contained in IParamBlock if (isSpot || isDirectional || isPoint) { GenLight* light = (GenLight*)(lightObject); if (!light) { delete colladaLight; return; } // Export the overshoot flag for directional lights if (isDirectional || isSpot) { addExtraChildParameter(LIGHT_ELEMENT, OVERSHOOT_PARAMETER, light->GetOvershoot() != false); } addExtraChildParameter(LIGHT_ELEMENT, DECAY_TYPE_PARAMETER, (int)light->GetDecayType()); addExtraChildParameter(LIGHT_ELEMENT, USE_NEAR_ATTENUATION_PARAMETER, (light->GetUseAttenNear() != false)); addExtraChildParameter(LIGHT_ELEMENT, USE_FAR_ATTENUATION_PARAMETER, (light->GetUseAtten() != false)); exportShadowParameters(light); if (light->GetProjector()) { Texmap* projectorMap = light->GetProjMap(); if (projectorMap) { String imageId = exportTexMap(projectorMap); if ( !imageId.empty() ) { addExtraChildParameter(LIGHT_ELEMENT, LIGHT_MAP_ELEMENT, "#" + imageId); } } } } else // isSky { Texmap *colorMap = parametersSky->GetTexmap(MaxLight::PB_SKY_COLOR_MAP, mDocumentExporter->getOptions().getAnimationStart()); String imageId = exportTexMap(colorMap); if ( !imageId.empty()) { addExtraChildParameter(SKYLIGHT_ELEMENT, SKYLIGHT_COLORMAP_ELEMENT, "#" + imageId); } } addLight(*colladaLight); delete colladaLight; }
void Lighting::UpdateLights() { Matrix3 Mat; int i; ObjectState Os; LightObject *LightObj; LightState Ls; RenderLight Light; TimeValue Time = GetCOREInterface()->GetTime(); Interval valid; Point3 Pos,Target; m_Lights.clear(); for(i=0;i<sceneLights.Count();i++) { INode * Node = sceneLights[i]; Os = Node->EvalWorldState(Time); if(Os.obj ) { LightObj = (LightObject *)Os.obj; LightObj->EvalLightState(Time,valid,&Ls); Mat = Node->GetNodeTM(Time); Pos = Mat.GetTrans(); Light.m_Angle = Ls.hotsize; if(Light.m_Angle < 2.0f) { Light.m_Angle = 2.0f; } Mat = Node->GetNodeTM(Time); Light.m_Dir = Mat.GetRow(2); Light.m_Type = (RenderLightType)Ls.type; Light.m_Pos = Pos; Light.m_Dir = Light.m_Dir.Normalize(); Light.m_Color = Ls.color * Ls.intens; if(Ls.useAtten) { Light.m_Atten = true; if(Ls.attenStart <= 0.0f) { Light.m_InnerRange = 1.0f; } else { Light.m_InnerRange = 1.0f / (Ls.attenStart * 2.0f); } if(Ls.attenEnd <= 0.0f) { Light.m_OuterRange = 0.0f; } else { Light.m_OuterRange = 1.0f / (Ls.attenEnd * 2.0f); } } else { Light.m_Atten = false; Light.m_InnerRange = 0.1f; Light.m_OuterRange = 0.00001f; } m_Lights.push_back(Light); } } }