// MakeProjection //------------------------------------------------------------------------------ void Mat44::MakeProjection( float yFOV, float aspect, float zNear, float zFar ) { const float ymax( zNear * Tan( yFOV * 0.5f ) ); const float xmax( ymax * aspect ); const float x( zNear / xmax ); const float y( zNear / ymax ); const float c( -( zFar + zNear ) / ( zFar - zNear ) ); const float d( -( 2.0f * zFar * zNear ) / ( zFar - zNear ) ); col0 = Vec4( x, 0.0f, 0.0f, 0.0f ); col1 = Vec4( 0.0f, y, 0.0f, 0.0f ); col2 = Vec4( 0.0f, 0.0f, c, -1.0f ); col3 = Vec4( 0.0f, 0.0f, d, 0.0f ); }
Plane Frustum::BottomPlane() const { if (type == PerspectiveFrustum) { vec bottomSide = front - Tan(verticalFov * 0.5f) * up; vec left = -WorldRight(); vec bottomSideNormal = ((handedness == FrustumRightHanded) ? Cross(left, bottomSide) : Cross(bottomSide, left)).Normalized(); return Plane(pos, bottomSideNormal); } else { return Plane(NearPlanePos(0.f, -1.f), -up); } }
Plane Frustum::TopPlane() const { if (type == PerspectiveFrustum) { vec topSide = front + Tan(verticalFov * 0.5f) * up; vec right = WorldRight(); vec topSideNormal = ((handedness == FrustumRightHanded) ? Cross(right, topSide) : Cross(topSide, right)).Normalized(); return Plane(pos, topSideNormal); } else { return Plane(NearPlanePos(0.f, 1.f), up); } }
//world -> perspective Matrix44 TransformHelper::CreatePerspective(Dfloat fov, Dfloat aspect, Dfloat nearZ, Dfloat farZ) { Dfloat d = 1.0f / Tan(fov * 0.5f); Dfloat recip = 1.0f / (nearZ - farZ); Matrix44 matPerspective; matPerspective(0, 0) = d / aspect; matPerspective(1, 1) = d; matPerspective(2, 2) = (nearZ + farZ)*recip; matPerspective(2, 3) = 2 * nearZ*farZ*recip; matPerspective(3, 2) = -1.0f; matPerspective(3, 3) = 0.0f; return matPerspective; }
/* Computes the coefficients for a second-order low-pass butterworth filter * @param r = ratio of cut-off frequncy to half of the sample frequency. * valid domain: 0.0001 < r < 0.9999 (coerced if out of bounds) */ void setFilterCoeff(FilterCoeff * FC, float r) { static float c; if (r < 0.0001) r = 0.0001; // Prevents a divide by zero if (r > 0.9999) r = 0.9999; // Cannot exceed Nyquist frequency c = Tan(0.5 * PI * (1.0 - r)); FC->b0 = 1.0 / (1.0 + SQRT_TWO * c + c * c); FC->b1 = 2.0 * (FC->b0); FC->b2 = (FC->b0); FC->a1 = -2.0 * (c * c - 1.0) * (FC->b0); FC->a2 = (1.0 - SQRT_TWO * c + c * c) * (FC->b0); }
Plane Frustum::RightPlane() const { if (type == PerspectiveFrustum) { vec right = WorldRight(); right.ScaleToLength(Tan(horizontalFov*0.5f)); vec rightSide = front + right; vec rightSideNormal = ((handedness == FrustumRightHanded) ? Cross(rightSide, up) : Cross(up, rightSide)).Normalized(); return Plane(pos, rightSideNormal); } else { vec right = WorldRight(); return Plane(NearPlanePos(1.f, 0.f), right.Normalized()); } }
Plane Frustum::LeftPlane() const { if (type == PerspectiveFrustum) { vec left = -WorldRight(); left.ScaleToLength(Tan(horizontalFov*0.5f)); vec leftSide = front + left; vec leftSideNormal = ((handedness == FrustumRightHanded) ? Cross(up, leftSide) : Cross(leftSide, up)).Normalized(); return Plane(pos, leftSideNormal); } else { vec left = -WorldRight(); return Plane(NearPlanePos(-1.f, 0.f), left.Normalized()); } }
float CBackImageManager::GetRatioCamera( float fFov, int nWidth, int nHeight ) { eRATIO eRatio = GetRatio(nWidth, nHeight); float fTan = fFov * 0.5f; // eRATIO_16_10 int nResolutionIdx = GetResolutionIndex(); float fDis = DEF_CAMERA_DISTANCE; if (eRatio == eRATIO_4_3) fDis = DEF_CAMERA_DISTANCE_4_3; if (eRatio == eRATIO_5_4) fDis = DEF_CAMERA_DISTANCE_5_4; float fl = 8.f + (fDis / Tan(fTan)); return fl; }
// // InfinitePerspectiveRH // http://www.gamasutra.com/features/20021011/lengyel_02.htm // bool Mat4::InfinitePerspectiveRH( float FOVy, float Aspect, float Near, float Far ) { if (Far - Near < EPSILON) { Identity(); return false; } float Top = Near * Tan( FOVy * PI / 360.0f ); float Bottom = -Top; float Left = Bottom * Aspect; float Right = Top * Aspect; if ((Right - Left < EPSILON) || (Top - Bottom < EPSILON)) { Identity(); return false; } m[ 0 ][ 0 ] = 2.0f * Near / (Right - Left); m[ 0 ][ 1 ] = 0.0f; m[ 0 ][ 2 ] = 0.0f; m[ 0 ][ 3 ] = 0.0f; m[ 1 ][ 0 ] = 0.0f; m[ 1 ][ 1 ] = 2.0f * Near / (Top - Bottom); m[ 1 ][ 2 ] = 0.0f; m[ 1 ][ 3 ] = 0.0f; m[ 2 ][ 0 ] = (Left + Right) / (Right - Left); m[ 2 ][ 1 ] = (Top + Bottom) / (Top - Bottom); m[ 2 ][ 2 ] = EPSILON - 1.0f; // Tweaked m[ 2 ][ 3 ] = -1.0f; m[ 3 ][ 0 ] = 0.0f; m[ 3 ][ 1 ] = 0.0f; m[ 3 ][ 2 ] = Near * (EPSILON - 2.0f); // Tweaked m[ 3 ][ 3 ] = 0.0f; return true; }
FullScreenBlur::FullScreenBlur(Camera* camera, float blurFactor) :_screenDistance(0.0f) ,_parentCamera(camera) ,_screenImage(NULL) ,_screenTexture(NULL) ,_screenQuad(NULL) { if( camera ) { World* world = WorldSingleton::Get(); Vector2f size = camera->GetViewportSize(); this->_screenImage = new Image( (unsigned int)(size.width*world->GetWindowSize().width), (unsigned int)(size.height*world->GetWindowSize().height), RGB8 ); this->_screenTexture = new Texture(this->_screenImage); this->_screenDistance = camera->GetNearDraw()+1.0f; this->_screenQuad = new Object(); this->_screenQuad->StartRecording(); glBegin(GL_QUADS); glNormal3f(0.0f, 0.0f, 1.0f); glTexCoord2f(0.0f, 0.0f); glVertex3f(-1.0f, -1.0f, 0.0f); glTexCoord2f(1.0f, 0.0f); glVertex3f(1.0f, -1.0f, 0.0f); glTexCoord2f(1.0f, 1.0f); glVertex3f(1.0f, 1.0f, 0.0f); glTexCoord2f(0.0f, 1.0f); glVertex3f(-1.0f, 1.0f, 0.0f); glEnd(); this->_screenQuad->StopRecording(); this->_screenQuad->SetPosition(0.0f, 0.0f, -this->_screenDistance/Tan(this->_parentCamera->GetFieldOfView()/2.0f)); this->_screenQuad->SetScale(this->_screenDistance, this->_screenDistance, 1.0f); this->_screenQuad->SetColor(Object::Diffuse, Vector4f(1.0f, 1.0f, 1.0f, blurFactor)); this->_screenQuad->SetColor(Object::Emission, Vector4f(1.0f, 1.0f, 1.0f, 0.0f)); this->_screenQuad->SetTexture(this->_screenTexture); this->_screenQuad->SetRenderOrder(Entity::Foreground); this->_screenQuad->Parent(camera); } }
//-------------------------------------------------------------------------------------------------------------- //获取屏幕坐标在世界空间的投影射线 bool Viewport::GetWorldRayFromScreenPoint( LONG nX, LONG nY, Ray3* pRay3 ) { if( nX < (LONG)mLeft || nY < (LONG)mTop ) return false; nX -= mLeft; nY -= mTop; if( nX > (LONG)mWidth || nY > (LONG)mHeight ) return false; //将屏幕坐标转换为以中心为原点的单位化坐标(投影转换) float fTanFOV2 = Tan( FK_PI * 0.125 ); // Tan( FK_DegreeToRadian( 45.0f / 2.0f ) float fX = fTanFOV2 * ( (float)nX / ( (float)mWidth * 0.5f ) - 1.0f ) * mAspect; float fY = fTanFOV2 * ( 1.0f - (float)nY / ( (float)mHeight * 0.5f ) ); //将经过投影转换的坐标值转换到世界空间坐标 static Matrix4 MatInvView; static Vector3 VectorEnd; MatInvView = mpCamera->mViewMatrix.GetInverse(); pRay3->mOrigin.x = fX * mpCamera->mViewNear; pRay3->mOrigin.y = fY * mpCamera->mViewNear; pRay3->mOrigin.z = mpCamera->mViewNear; VectorEnd.x = fX * mpCamera->mViewFar; VectorEnd.y = fY * mpCamera->mViewFar; VectorEnd.z = mpCamera->mViewFar; pRay3->mOrigin *= MatInvView; VectorEnd *= MatInvView; pRay3->mDirection = VectorEnd - pRay3->mOrigin; pRay3->mDirection.Normalize(); return true; }
void Frustum::SetVerticalFovAndAspectRatio(float vFov, float aspectRatio) { verticalFov = vFov; horizontalFov = 2.f * Atan(Tan(vFov*0.5f)*aspectRatio); }
void draw_line(void) { double m_x = min_x, m_y = min_y, M_x = max_x, M_y = max_y; double x[2], y[2], t, z; int i = 0; _line * l; l = POP(_line); check_path_settings(); if (local_part == HALF) { if ((local_dir == FORTH && (l->a > -90 && l->a <= 90)) || (local_dir == BACK && (l->a <= -90 || l->a > 90))) m_x = l->x; else M_x = l->x; if ((local_dir == FORTH && l->a > 0) || (local_dir == BACK && l->a <= 0)) m_y = l->y; else M_y = l->y; } if (l->a == 90 || l->a == -90) { if (l->x >= m_x && l->x <= M_x) { x[0] = x[1] = l->x; y[0] = m_y; y[1] = M_y; i = 2; } } else if (l->a == 0 || l->a == 180) { if (l->y >= m_y && l->y <= M_y) { y[0] = y[1] = l->y; x[0] = m_x; x[1] = M_x; i = 2; } } else { t = Tan(l->a); z = t*(m_x-l->x)+l->y; if (z >= m_y && z <= M_y) { x[i] = m_x; y[i] = z; i++; } z = t*(M_x-l->x)+l->y; if (z >= m_y && z <= M_y) { x[i] = M_x; y[i] = z; i++; } z =(m_y-l->y)/t+l->x; if (z > m_x && z < M_x && i < 2) { x[i] = z ; y[i] = m_y; i++; } z = (M_y-l->y)/t+l->x; if (z > m_x && z < M_x && i < 2) { x[i] = z; y[i] = M_y; i++; } } if (i == 2) { fprintf(output_file, "\\psline"); put_local(); fprintf(output_file, "{c-c}(%.4f,%.4f)(%.4f,%.4f)\n", x[0], y[0], x[1], y[1]); } }
void Frustum::SetHorizontalFovAndAspectRatio(float hFov, float aspectRatio) { horizontalFov = hFov; verticalFov = 2.f * Atan(Tan(hFov*0.5f)/aspectRatio); }
float Frustum::AspectRatio() const { return Tan(horizontalFov*0.5f) / Tan(verticalFov*0.5f); }
static base_t my_tan(const base_t& i) { return Tan(i); }
inline Big<Exponent, Mantissa> tan(Big<Exponent, Mantissa> const& v) { return Tan(v); }
inline float Cot(angle Angle) { return 1 / Tan(Angle); }