float LightPoint(CDB::COLLIDER& DB, Fvector &P, Fvector &N, LSelection& SEL) { Fvector Ldir,Pnew; Pnew.mad (P,N,0.05f); R_Light **IT = SEL.begin(), **E = SEL.end(); float amount = 0; for (; IT!=E; IT++) { R_Light* L = *IT; if (L->type==LT_DIRECT) { // Cos Ldir.invert (L->direction); float D = Ldir.dotproduct( N ); if( D <=0 ) continue; // Raypick if (!RayPick(DB,Pnew,Ldir,1000.f,*L)) amount+=D*L->amount; } else { // Distance float sqD = P.distance_to_sqr(L->position); if (sqD > L->range2) continue; // Dir Ldir.sub (L->position,P); Ldir.normalize_safe(); float D = Ldir.dotproduct( N ); if( D <=0 ) continue; // Raypick float R = _sqrt(sqD); if (!RayPick(DB,Pnew,Ldir,R,*L)) amount += (D*L->amount)/(L->attenuation0 + L->attenuation1*R + L->attenuation2*sqD); } } return amount; }
void CEffect_Thunderbolt::Bolt(shared_str id, float period, float lt) { VERIFY (id.size()); state = stWorking; life_time = lt+Random.randF(-lt*0.5f,lt*0.5f); current_time = 0.f; current = g_pGamePersistent->Environment().thunderbolt_collection(collection, id)->GetRandomDesc(); VERIFY(current); Fmatrix XF,S; Fvector pos,dev; float sun_h, sun_p; CEnvironment& environment = g_pGamePersistent->Environment(); environment.CurrentEnv->sun_dir.getHP (sun_h,sun_p); float alt = environment.p_var_alt;//Random.randF(environment.p_var_alt.x,environment.p_var_alt.y); float lng = Random.randF(sun_h-environment.p_var_long+PI,sun_h+environment.p_var_long+PI); float dist = Random.randF(FAR_DIST*environment.p_min_dist,FAR_DIST*.95f); current_direction.setHP (lng,alt); pos.mad (Device.vCameraPosition,current_direction,dist); dev.x = Random.randF(-environment.p_tilt,environment.p_tilt); dev.y = Random.randF(0,PI_MUL_2); dev.z = Random.randF(-environment.p_tilt,environment.p_tilt); XF.setXYZi (dev); Fvector light_dir = {0.f,-1.f,0.f}; XF.transform_dir (light_dir); lightning_size = FAR_DIST*2.f; RayPick (pos,light_dir,lightning_size); lightning_center.mad (pos,light_dir,lightning_size*0.5f); S.scale (lightning_size,lightning_size,lightning_size); XF.translate_over (pos); current_xform.mul_43 (XF,S); float next_v = Random.randF(); if (next_v<environment.p_second_prop){ next_lightning_time = Device.fTimeGlobal+lt+EPS_L; }else{ next_lightning_time = Device.fTimeGlobal+period+Random.randF(-period*0.3f,period*0.3f); current->snd.play_no_feedback (0,0,dist/300.f,&pos,0,0,&Fvector2().set(dist/2,dist*2.f)); } current_direction.invert (); // for env-sun }