bool CEditShape::GetBox(Fbox& box) { if (m_Box.is_valid()){ box.xform(m_Box,FTransform); return true; } return false; }
IC void get_cam_oob( Fvector &bc, Fvector &bd, Fmatrix33 &mat, const Fmatrix &xform, const SRotation &r_torso, float alpha, float radius, float c ) { get_box_mat ( mat, alpha, r_torso ); Fbox xf; get_q_box( xf, c, alpha, radius ); xf.xform ( Fbox().set(xf), xform ) ; // query xf.get_CD (bc,bd) ; }
r_aabb_ssa r_pixel_calculator::calculate (dxRender_Visual* V) { r_aabb_ssa result = {0}; float area = float(_sqr(rt_dimensions)); // u32 id [6] ; for (u32 face=0; face<6; face++) { // setup matrices Fmatrix mProject,mView ; Fvector vFrom ; Fbox aabb ; // camera - left-to-right mView.build_camera_dir (vFrom.invert(cmDir[face]).mul(100.f), cmDir[face], cmNorm[face]) ; aabb.xform (V->vis.box,mView); D3DXMatrixOrthoOffCenterLH ( (D3DXMATRIX*)&mProject, aabb.min.x, aabb.max.x, aabb.min.y, aabb.max.y, aabb.min.z, aabb.max.z ); RCache.set_xform_world (Fidentity); RCache.set_xform_view (mView); RCache.set_xform_project (mProject); // render-0 Device.Clear (); // clear-ZB RCache.set_Shader (V->shader); V->Render (1.f); // render-1 RImplementation.HWOCC.occq_begin (id[face]); V->Render (1.f); RImplementation.HWOCC.occq_end (id[face]); } // for (u32 it=0; it<6; it++) { float pixels = (float)RImplementation.HWOCC.occq_get (id[it]); float coeff = clampr(pixels/area,float(0),float(1)); Msg ("[%d]ssa_c: %1.3f,%f/%f",it,coeff,pixels,area); result.ssa [it]= (u8)clampr(iFloor(coeff*255.f+0.5f),int(0),int(255)); } return result ; }
bool CEditShape::FrustumPick(const CFrustum& frustum) { const Fmatrix& M = _Transform(); for (ShapeIt it=shapes.begin(); it!=shapes.end(); it++){ switch (it->type){ case cfSphere:{ Fvector C; Fsphere& T = it->data.sphere; M.transform_tiny(C,T.P); if (frustum.testSphere_dirty(C,T.R*FScale.x)) return true; }break; case cfBox:{ Fbox box; box.identity (); Fmatrix B = it->data.box; B.mulA_43 (_Transform()); box.xform (B); u32 mask = 0xff; if (frustum.testAABB(box.data(),mask)) return true; }break; } } return false; }
IC bool _IsBoxVisible(dxRender_Visual* visual, const Fmatrix& transform) { Fbox bb; bb.xform (visual->vis.box,transform); return ::Render->occ_visible(bb); }
void CActor::cam_Update(float dt, float fFOV) { if(m_holder) return; if(mstate_real & mcClimb&&cam_active!=eacFreeLook) camUpdateLadder(dt); Fvector point={0,CameraHeight(),0}, dangle={0,0,0}; Fmatrix xform,xformR; xform.setXYZ (0,r_torso.yaw,0); xform.translate_over(XFORM().c); // lookout if (this == Level().CurrentControlEntity()) { if (!fis_zero(r_torso_tgt_roll)){ Fvector src_pt,tgt_pt; float radius = point.y*0.5f; float alpha = r_torso_tgt_roll/2.f; float dZ = ((PI_DIV_2-((PI+alpha)/2))); calc_point (tgt_pt,radius,0,alpha); src_pt.set (0,tgt_pt.y,0); // init valid angle float valid_angle = alpha; // xform with roll xformR.setXYZ (-r_torso.pitch,r_torso.yaw,-dZ); Fmatrix33 mat; mat.i = xformR.i; mat.j = xformR.j; mat.k = xformR.k; // get viewport params float w,h; float c = viewport_near(w,h); w/=2.f;h/=2.f; // find tris Fbox box; box.invalidate (); box.modify (src_pt); box.modify (tgt_pt); box.grow (c); // query Fvector bc,bd ; Fbox xf ; xf.xform (box,xform) ; xf.get_CD (bc,bd) ; xrXRC xrc ; xrc.box_options (0) ; xrc.box_query (Level().ObjectSpace.GetStaticModel(), bc, bd) ; u32 tri_count = xrc.r_count(); if (tri_count) { float da = 0.f; BOOL bIntersect = FALSE; Fvector ext = {w,h,VIEWPORT_NEAR/2}; if (test_point(xrc,xform,mat,ext,radius,alpha)){ da = PI/1000.f; if (!fis_zero(r_torso.roll)) da *= r_torso.roll/_abs(r_torso.roll); float angle = 0.f; for (; _abs(angle)<_abs(alpha); angle+=da) if (test_point(xrc,xform,mat,ext,radius,angle)) { bIntersect=TRUE; break; } valid_angle = bIntersect?angle:alpha; } } r_torso.roll = valid_angle*2.f; r_torso_tgt_roll = r_torso.roll; } else { r_torso_tgt_roll = 0.f; r_torso.roll = 0.f; } } if (!fis_zero(r_torso.roll)) { float radius = point.y*0.5f; float valid_angle = r_torso.roll/2.f; calc_point (point,radius,0,valid_angle); dangle.z = (PI_DIV_2-((PI+valid_angle)/2)); } float flCurrentPlayerY = xform.c.y; // Smooth out stair step ups if ((character_physics_support()->movement()->Environment()==peOnGround) && (flCurrentPlayerY-fPrevCamPos>0)){ fPrevCamPos += dt*1.5f; if (fPrevCamPos > flCurrentPlayerY) fPrevCamPos = flCurrentPlayerY; if (flCurrentPlayerY-fPrevCamPos>0.2f) fPrevCamPos = flCurrentPlayerY-0.2f; point.y += fPrevCamPos-flCurrentPlayerY; }else{ fPrevCamPos = flCurrentPlayerY; } float _viewport_near = VIEWPORT_NEAR; // calc point xform.transform_tiny (point); CCameraBase* C = cam_Active(); if(eacFirstEye == cam_active) { // CCameraBase* C = cameras[eacFirstEye]; xrXRC xrc ; xrc.box_options (0) ; xrc.box_query (Level().ObjectSpace.GetStaticModel(), point, Fvector().set(VIEWPORT_NEAR,VIEWPORT_NEAR,VIEWPORT_NEAR) ); u32 tri_count = xrc.r_count(); if (tri_count) { _viewport_near = 0.01f; } else { xr_vector<ISpatial*> ISpatialResult; g_SpatialSpacePhysic->q_box(ISpatialResult, 0, STYPE_PHYSIC, point, Fvector().set(VIEWPORT_NEAR,VIEWPORT_NEAR,VIEWPORT_NEAR)); for (u32 o_it=0; o_it<ISpatialResult.size(); o_it++) { CPHShell* pCPHS= smart_cast<CPHShell*>(ISpatialResult[o_it]); if (pCPHS) { _viewport_near = 0.01f; break; } } } } /* { CCameraBase* C = cameras[eacFirstEye]; float oobox_size = 2*VIEWPORT_NEAR; Fmatrix _rot; _rot.k = C->vDirection; _rot.c = C->vPosition; _rot.i.crossproduct (C->vNormal, _rot.k); _rot.j.crossproduct (_rot.k, _rot.i); Fvector vbox; vbox.set (oobox_size, oobox_size, oobox_size); Level().debug_renderer().draw_aabb (C->vPosition, 0.05f, 0.051f, 0.05f, D3DCOLOR_XRGB(0,255,0)); Level().debug_renderer().draw_obb (_rot, Fvector().div(vbox,2.0f), D3DCOLOR_XRGB(255,0,0)); dMatrix3 d_rot; PHDynamicData::FMXtoDMX (_rot, d_rot); CPHActivationShape activation_shape; activation_shape.Create (point, vbox, this); dBodySetRotation (activation_shape.ODEBody(), d_rot); CPHCollideValidator::SetDynamicNotCollide(activation_shape); activation_shape.Activate (vbox,1,1.f,0.0F); point.set (activation_shape.Position()); activation_shape.Destroy (); } */ C->Update (point,dangle); C->f_fov = fFOV; if(eacFirstEye != cam_active) { cameras[eacFirstEye]->Update (point,dangle); cameras[eacFirstEye]->f_fov = fFOV; } if( psActorFlags.test(AF_PSP) ) { Cameras().Update (C); }else { Cameras().Update (cameras[eacFirstEye]); } fCurAVelocity = vPrevCamDir.sub(cameras[eacFirstEye]->vDirection).magnitude()/Device.fTimeDelta; vPrevCamDir = cameras[eacFirstEye]->vDirection; if (Level().CurrentEntity() == this) { Level().Cameras().Update (C); if(eacFirstEye == cam_active && !Level().Cameras().GetCamEffector(cefDemo)){ Cameras().ApplyDevice (_viewport_near); } } }
void CLightProjector::calculate () { #ifdef _GPA_ENABLED TAL_SCOPED_TASK_NAMED( "CLightProjector::calculate()" ); #endif // _GPA_ENABLED if (receivers.empty()) return; // perform validate / markup for (u32 r_it=0; r_it<receivers.size(); r_it++) { // validate BOOL bValid = TRUE; IRenderable* O = receivers[r_it]; CROS_impl* LT = (CROS_impl*)O->renderable_ROS(); int slot = LT->shadow_recv_slot; if (slot<0 || slot>=P_o_count) bValid = FALSE; // invalid slot else if (cache[slot].O!=O) bValid = FALSE; // not the same object else { // seems to be valid Fbox bb; bb.xform (O->renderable.visual->getVisData().box,O->renderable.xform); if (cache[slot].BB.contains(bb)) { // inside, but maybe timelimit exceeded? if (Device.dwTimeGlobal > cache[slot].dwTimeValid) bValid = FALSE; // timeout } else bValid = FALSE; // out of bounds } // if (bValid) { // Ok, use cached version cache[slot].dwFrame = Device.dwFrame; } else { taskid.push_back (r_it); } } if (taskid.empty()) return; // Begin Device.Statistic->RenderDUMP_Pcalc.Begin (); RCache.set_RT (RT->pRT); RCache.set_ZB (RImplementation.Target->pTempZB); CHK_DX(HW.pDevice->Clear (0,0, D3DCLEAR_ZBUFFER | (HW.Caps.bStencil?D3DCLEAR_STENCIL:0), 0,1,0 )); RCache.set_xform_world (Fidentity); // reallocate/reassociate structures + perform all the work for (u32 c_it=0; c_it<cache.size(); c_it++) { if (taskid.empty()) break; if (Device.dwFrame==cache[c_it].dwFrame) continue; // found not used slot int tid = taskid.back(); taskid.pop_back(); recv& R = cache [c_it]; IRenderable* O = receivers [tid]; const vis_data& vis = O->renderable.visual->getVisData(); CROS_impl* LT = (CROS_impl*)O->renderable_ROS(); VERIFY2 (_valid(O->renderable.xform),"Invalid object transformation"); VERIFY2 (_valid(vis.sphere.P),"Invalid object's visual sphere"); Fvector C; O->renderable.xform.transform_tiny (C,vis.sphere.P); R.O = O; R.C = C; R.C.y += vis.sphere.R*0.1f; //. YURA: 0.1 can be more R.BB.xform (vis.box,O->renderable.xform).scale(0.1f); R.dwTimeValid = Device.dwTimeGlobal + ::Random.randI(time_min,time_max); LT->shadow_recv_slot = c_it; // Msg ("[%f,%f,%f]-%f",C.C.x,C.C.y,C.C.z,C.O->renderable.visual->vis.sphere.R); // calculate projection-matrix Fmatrix mProject; float p_R = R.O->renderable.visual->getVisData().sphere.R * 1.1f; //VERIFY2 (p_R>EPS_L,"Object has no physical size"); VERIFY3 (p_R>EPS_L,"Object has no physical size", R.O->renderable.visual->getDebugName().c_str()); float p_hat = p_R/P_cam_dist; float p_asp = 1.f; float p_near = P_cam_dist-EPS_L; float p_far = P_cam_dist+p_R+P_cam_range; mProject.build_projection_HAT (p_hat,p_asp,p_near,p_far); RCache.set_xform_project (mProject); // calculate view-matrix Fmatrix mView; Fvector v_C, v_Cs, v_N; v_C.set (R.C); v_Cs = v_C; v_C.y += P_cam_dist; v_N.set (0,0,1); VERIFY (_valid(v_C) && _valid(v_Cs) && _valid(v_N)); // validate Fvector v; v.sub (v_Cs,v_C);; #ifdef DEBUG if ((v.x*v.x+v.y*v.y+v.z*v.z)<=flt_zero) { CObject* OO = dynamic_cast<CObject*>(R.O); Msg("Object[%s] Visual[%s] has invalid position. ",*OO->cName(),*OO->cNameVisual()); Fvector cc; OO->Center(cc); Log("center=",cc); Log("visual_center=",OO->Visual()->getVisData().sphere.P); Log("full_matrix=",OO->XFORM()); Log ("v_N",v_N); Log ("v_C",v_C); Log ("v_Cs",v_Cs); Log("all bones transform:--------"); CKinematics* K = dynamic_cast<CKinematics*>(OO->Visual()); for(u16 ii=0; ii<K->LL_BoneCount();++ii){ Fmatrix tr; tr = K->LL_GetTransform(ii); Log("bone ",K->LL_BoneName_dbg(ii)); Log("bone_matrix",tr); } Log("end-------"); } #endif // handle invalid object-bug if ((v.x*v.x+v.y*v.y+v.z*v.z)<=flt_zero) { // invalidate record, so that object will be unshadowed, but doesn't crash R.dwTimeValid = Device.dwTimeGlobal; LT->shadow_recv_frame = Device.dwFrame-1; LT->shadow_recv_slot = -1; continue ; } mView.build_camera (v_C,v_Cs,v_N); RCache.set_xform_view (mView); // Select slot, set viewport int s_x = c_it%P_o_line; int s_y = c_it/P_o_line; D3DVIEWPORT9 VP = {s_x*P_o_size,s_y*P_o_size,P_o_size,P_o_size,0,1 }; CHK_DX (HW.pDevice->SetViewport(&VP)); // Clear color to ambience Fvector& cap = LT->get_approximate(); CHK_DX (HW.pDevice->Clear(0,0, D3DCLEAR_TARGET, color_rgba_f(cap.x,cap.y,cap.z, (cap.x+cap.y+cap.z)/4.f), 1, 0 )); // calculate uv-gen matrix and clamper Fmatrix mCombine; mCombine.mul (mProject,mView); Fmatrix mTemp; float fSlotSize = float(P_o_size)/float(P_rt_size); float fSlotX = float(s_x*P_o_size)/float(P_rt_size); float fSlotY = float(s_y*P_o_size)/float(P_rt_size); float fTexelOffs = (.5f / P_rt_size); Fmatrix m_TexelAdjust = { 0.5f/*x-scale*/, 0.0f, 0.0f, 0.0f, 0.0f, -0.5f/*y-scale*/, 0.0f, 0.0f, 0.0f, 0.0f, 1.0f/*z-range*/, 0.0f, 0.5f/*x-bias*/, 0.5f + fTexelOffs/*y-bias*/, 0.0f/*z-bias*/, 1.0f }; R.UVgen.mul (m_TexelAdjust,mCombine); mTemp.scale (fSlotSize,fSlotSize,1); R.UVgen.mulA_44 (mTemp); mTemp.translate (fSlotX+fTexelOffs,fSlotY+fTexelOffs,0); R.UVgen.mulA_44 (mTemp); // Build bbox and render Fvector min,max; Fbox BB; min.set (R.C.x-p_R, R.C.y-(p_R+P_cam_range), R.C.z-p_R); max.set (R.C.x+p_R, R.C.y+0, R.C.z+p_R); BB.set (min,max); R.UVclamp_min.set (min).add (.05f); // shrink a little R.UVclamp_max.set (max).sub (.05f); // shrink a little ISpatial* spatial = dynamic_cast<ISpatial*> (O); if (spatial) { spatial->spatial_updatesector (); if (spatial->spatial.sector) RImplementation.r_dsgraph_render_R1_box (spatial->spatial.sector,BB,SE_R1_LMODELS); } //if (spatial) RImplementation.r_dsgraph_render_subspace (spatial->spatial.sector,mCombine,v_C,FALSE); } // Blur /* { // Fill vertex buffer u32 Offset; FVF::TL4uv* pv = (FVF::TL4uv*) RCache.Vertex.Lock (4,geom_Blur.stride(),Offset); RImplementation.ApplyBlur4 (pv,P_rt_size,P_rt_size,P_blur_kernel); RCache.Vertex.Unlock (4,geom_Blur.stride()); // Actual rendering (pass0, temp2real) RCache.set_RT (RT->pRT); RCache.set_ZB (NULL); RCache.set_Shader (sh_BlurTR ); RCache.set_Geometry (geom_Blur ); RCache.Render (D3DPT_TRIANGLELIST,Offset,0,4,0,2); } */ // Finita la comedia Device.Statistic->RenderDUMP_Pcalc.End (); RCache.set_xform_project (Device.mProject); RCache.set_xform_view (Device.mView); }
void dx103DFluidRenderer::CalculateLighting(const dx103DFluidData &FluidData, FogLighting &LightData) { m_lstRenderables.clear_not_free(); LightData.Reset(); const dx103DFluidData::Settings &VolumeSettings = FluidData.GetSettings(); Fvector4 hemi_color = g_pGamePersistent->Environment().CurrentEnv->hemi_color; //hemi_color.mul(0.2f); hemi_color.mul(VolumeSettings.m_fHemi); LightData.m_vLightIntencity.set(hemi_color.x, hemi_color.y, hemi_color.z); LightData.m_vLightIntencity.add(g_pGamePersistent->Environment().CurrentEnv->ambient); const Fmatrix &Transform = FluidData.GetTransform(); Fbox box; box.min = Fvector3().set(-0.5f, -0.5f, -0.5f); box.max = Fvector3().set( 0.5f, 0.5f, 0.5f); box.xform(Transform); Fvector3 center; Fvector3 size; box.getcenter(center); box.getradius(size); // Traverse object database g_SpatialSpace->q_box ( m_lstRenderables, 0, //ISpatial_DB::O_ORDERED, STYPE_LIGHTSOURCE, center, size ); u32 iNumRenderables = m_lstRenderables.size(); // Determine visibility for dynamic part of scene for (u32 i=0; i<iNumRenderables; ++i) { ISpatial* spatial = m_lstRenderables[i]; // Light light* pLight = (light*) spatial->dcast_Light(); VERIFY(pLight); if (pLight->flags.bStatic) continue; float d = pLight->position.distance_to(Transform.c); float R = pLight->range + _max( size.x, _max( size.y, size.z ) ); if ( d >= R ) continue; Fvector3 LightIntencity; LightIntencity.set(pLight->color.r, pLight->color.g, pLight->color.b); //LightIntencity.mul(0.5f); //if (!pLight->flags.bStatic) // LightIntencity.mul(0.5f); float r = pLight->range; float a = clampr(1.f - d/(r+EPS),0.f,1.f)*(pLight->flags.bStatic?1.f:2.f); LightIntencity.mul(a); LightData.m_vLightIntencity.add(LightIntencity); } //LightData.m_vLightIntencity.set( 1.0f, 0.5f, 0.0f); //LightData.m_vLightIntencity.set( 1.0f, 1.0f, 1.0f); }