diff options
author | Hans Lambermont <hans@lambermont.dyndns.org> | 2002-10-12 15:37:38 +0400 |
---|---|---|
committer | Hans Lambermont <hans@lambermont.dyndns.org> | 2002-10-12 15:37:38 +0400 |
commit | 12315f4d0e0ae993805f141f64cb8c73c5297311 (patch) | |
tree | 59b45827cd8293cfb727758989c7a74b40183974 /source/gameengine/Rasterizer/RAS_FramingManager.cpp |
Initial revisionv2.25
Diffstat (limited to 'source/gameengine/Rasterizer/RAS_FramingManager.cpp')
-rw-r--r-- | source/gameengine/Rasterizer/RAS_FramingManager.cpp | 234 |
1 files changed, 234 insertions, 0 deletions
diff --git a/source/gameengine/Rasterizer/RAS_FramingManager.cpp b/source/gameengine/Rasterizer/RAS_FramingManager.cpp new file mode 100644 index 00000000000..af0499bd348 --- /dev/null +++ b/source/gameengine/Rasterizer/RAS_FramingManager.cpp @@ -0,0 +1,234 @@ +/** + * $Id$ + * ***** BEGIN GPL/BL DUAL LICENSE BLOCK ***** + * + * This program is free software; you can redistribute it and/or + * modify it under the terms of the GNU General Public License + * as published by the Free Software Foundation; either version 2 + * of the License, or (at your option) any later version. The Blender + * Foundation also sells licenses for use in proprietary software under + * the Blender License. See http://www.blender.org/BL/ for information + * about this. + * + * This program is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA. + * + * The Original Code is Copyright (C) 2001-2002 by NaN Holding BV. + * All rights reserved. + * + * The Original Code is: all of this file. + * + * Contributor(s): none yet. + * + * ***** END GPL/BL DUAL LICENSE BLOCK ***** + */ + +#include "RAS_FramingManager.h" + +#include "RAS_Rect.h" + + void +RAS_FramingManager:: +ComputeDefaultFrustum( + const float camnear, + const float camfar, + const float lens, + const float design_aspect_ratio, + RAS_FrameFrustum & frustum +){ + + /* + * Magic Blender calculation. + * Blender does not give a Field of View as lens but a size + * at 16 units away from the lens. + */ + float halfSize = 16.f * camnear / lens; + float sizeX; + float sizeY; + + if (design_aspect_ratio > 1.f) { + // halfsize defines the width + sizeX = halfSize; + sizeY = halfSize/design_aspect_ratio; + } else { + // halfsize defines the height + sizeX = halfSize * design_aspect_ratio; + sizeY = halfSize; + } + + frustum.x2 = sizeX; + frustum.x1 = -frustum.x2; + frustum.y2 = sizeY; + frustum.y1 = -frustum.y2; + frustum.camnear = camnear; + frustum.camfar = camfar; +} + + void +RAS_FramingManager:: +ComputeBestFitViewRect( + const RAS_Rect &availableViewport, + const float design_aspect_ratio, + RAS_Rect &viewport +){ + // try and honour the aspect ratio when setting the + // drawable area. If we don't do this we are liable + // to get a lot of distortion in the rendered image. + + int width = availableViewport.GetWidth(); + int height = availableViewport.GetHeight(); + float window_aspect = float(width)/float(height); + + if (window_aspect < design_aspect_ratio) { + int v_height = (int)(width / design_aspect_ratio); + int left_over = (height - v_height) / 2; + + viewport.SetLeft(availableViewport.GetLeft()); + viewport.SetBottom(availableViewport.GetBottom() + left_over); + viewport.SetRight(availableViewport.GetLeft() + width); + viewport.SetTop(availableViewport.GetBottom() + left_over + v_height); + + } else { + int v_width = (int)(height * design_aspect_ratio); + int left_over = (width - v_width) / 2; + + viewport.SetLeft(availableViewport.GetLeft() + left_over); + viewport.SetBottom(availableViewport.GetBottom()); + viewport.SetRight(availableViewport.GetLeft() + v_width + left_over); + viewport.SetTop(availableViewport.GetBottom() + height); + } +} + + void +RAS_FramingManager:: +ComputeViewport( + const RAS_FrameSettings &settings, + const RAS_Rect &availableViewport, + RAS_Rect &viewport +){ + + RAS_FrameSettings::RAS_FrameType type = settings.FrameType(); + const int winx = availableViewport.GetWidth(); + const int winy = availableViewport.GetHeight(); + + const float design_width = float(settings.DesignAspectWidth()); + const float design_height = float(settings.DesignAspectHeight()); + + float design_aspect_ratio = float(1); + + if (design_height == float(0)) { + // well this is ill defined + // lets just scale the thing + + type = RAS_FrameSettings::e_frame_scale; + } else { + design_aspect_ratio = design_width/design_height; + } + + switch (type) { + + case RAS_FrameSettings::e_frame_scale : + case RAS_FrameSettings::e_frame_extend: + { + viewport.SetLeft(availableViewport.GetLeft()); + viewport.SetBottom(availableViewport.GetBottom()); + viewport.SetRight(availableViewport.GetLeft() + int(winx)); + viewport.SetTop(availableViewport.GetBottom() + int(winy)); + + break; + } + + case RAS_FrameSettings::e_frame_bars: + { + ComputeBestFitViewRect( + availableViewport, + design_aspect_ratio, + viewport + ); + + break; + } + default : + break; + } +} + + void +RAS_FramingManager:: +ComputeFrustum( + const RAS_FrameSettings &settings, + const RAS_Rect &availableViewport, + const RAS_Rect &viewport, + const float lens, + const float camnear, + const float camfar, + RAS_FrameFrustum &frustum +){ + + const int winx = availableViewport.GetWidth(); + const int winy = availableViewport.GetHeight(); + + RAS_FrameSettings::RAS_FrameType type = settings.FrameType(); + + const float design_width = float(settings.DesignAspectWidth()); + const float design_height = float(settings.DesignAspectHeight()); + + float design_aspect_ratio = float(1); + + if (design_height == float(0)) { + // well this is ill defined + // lets just scale the thing + + type = RAS_FrameSettings::e_frame_scale; + } else { + design_aspect_ratio = design_width/design_height; + } + + ComputeDefaultFrustum( + camnear, + camfar, + lens, + design_aspect_ratio, + frustum + ); + + switch (type) { + + case RAS_FrameSettings::e_frame_extend: + { + RAS_Rect vt; + ComputeBestFitViewRect( + availableViewport, + design_aspect_ratio, + vt + ); + + // now scale the calculated frustum by the difference + // between vt and the viewport in each axis. + // These are always > 1 + + float x_scale = float(viewport.GetWidth())/float(vt.GetWidth()); + float y_scale = float(viewport.GetHeight())/float(vt.GetHeight()); + + frustum.x1 *= x_scale; + frustum.x2 *= x_scale; + frustum.y1 *= y_scale; + frustum.y2 *= y_scale; + + break; + } + case RAS_FrameSettings::e_frame_scale : + case RAS_FrameSettings::e_frame_bars: + default : + break; + } +} + + + |