void SunLightSource::UpdateSMCamera(Camera const & scene_camera) { float3 const dir = this->Direction(); float3 up_vec; if (abs(MathLib::dot(-dir, scene_camera.UpVec())) > 0.95f) { up_vec = scene_camera.RightVec(); } else { up_vec = scene_camera.UpVec(); } float4x4 light_view = MathLib::look_at_lh(-dir, float3(0, 0, 0), up_vec); AABBox const aabb = CalcFrustumExtents(scene_camera, scene_camera.NearPlane(), scene_camera.FarPlane(), light_view); float3 const & center = aabb.Center(); float3 view_pos = MathLib::transform_coord(float3(center.x(), center.y(), aabb.Min().z()), MathLib::inverse(light_view)); sm_camera_->ViewParams(view_pos, view_pos + dir, up_vec); float3 dimensions = aabb.Max() - aabb.Min(); sm_camera_->ProjOrthoParams(dimensions.x(), dimensions.y(), 0.0f, dimensions.z()); }
void OCTree::DivideNode(size_t index, uint32_t curr_depth) { if (octree_[index].obj_ptrs.size() > 1) { size_t const this_size = octree_.size(); AABBox const parent_bb = octree_[index].bb; float3 const parent_center = parent_bb.Center(); octree_[index].first_child_index = static_cast<int>(this_size); octree_[index].visible = BO_No; octree_.resize(this_size + 8); for (SceneObjsType::const_reference so : octree_[index].obj_ptrs) { AABBox const & aabb = *so->PosBoundWS(); int mark[6]; mark[0] = aabb.Min().x() >= parent_center.x() ? 1 : 0; mark[1] = aabb.Min().y() >= parent_center.y() ? 2 : 0; mark[2] = aabb.Min().z() >= parent_center.z() ? 4 : 0; mark[3] = aabb.Max().x() >= parent_center.x() ? 1 : 0; mark[4] = aabb.Max().y() >= parent_center.y() ? 2 : 0; mark[5] = aabb.Max().z() >= parent_center.z() ? 4 : 0; for (int j = 0; j < 8; ++ j) { if (j == ((j & 1) ? mark[3] : mark[0]) + ((j & 2) ? mark[4] : mark[1]) + ((j & 4) ? mark[5] : mark[2])) { octree_[this_size + j].obj_ptrs.push_back(so); } } } for (size_t j = 0; j < 8; ++ j) { octree_node_t& new_node = octree_[this_size + j]; new_node.first_child_index = -1; new_node.bb = AABBox(float3((j & 1) ? parent_center.x() : parent_bb.Min().x(), (j & 2) ? parent_center.y() : parent_bb.Min().y(), (j & 4) ? parent_center.z() : parent_bb.Min().z()), float3((j & 1) ? parent_bb.Max().x() : parent_center.x(), (j & 2) ? parent_bb.Max().y() : parent_center.y(), (j & 4) ? parent_bb.Max().z() : parent_center.z())); if (curr_depth < max_tree_depth_) { this->DivideNode(this_size + j, curr_depth + 1); } } SceneObjsType empty; octree_[index].obj_ptrs.swap(empty); } }