Path: blob/master/3rdparty/openexr/IlmImf/ImfEnvmap.h
16337 views
///////////////////////////////////////////////////////////////////////////1//2// Copyright (c) 2004, Industrial Light & Magic, a division of Lucas3// Digital Ltd. LLC4//5// All rights reserved.6//7// Redistribution and use in source and binary forms, with or without8// modification, are permitted provided that the following conditions are9// met:10// * Redistributions of source code must retain the above copyright11// notice, this list of conditions and the following disclaimer.12// * Redistributions in binary form must reproduce the above13// copyright notice, this list of conditions and the following disclaimer14// in the documentation and/or other materials provided with the15// distribution.16// * Neither the name of Industrial Light & Magic nor the names of17// its contributors may be used to endorse or promote products derived18// from this software without specific prior written permission.19//20// THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS21// "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT22// LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR23// A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT24// OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,25// SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT26// LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,27// DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY28// THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT29// (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE30// OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.31//32///////////////////////////////////////////////////////////////////////////333435#ifndef INCLUDED_IMF_ENVMAP_H36#define INCLUDED_IMF_ENVMAP_H3738//-----------------------------------------------------------------------------39//40// Environment maps41//42// Environment maps define a mapping from 3D directions to 2D43// pixel space locations. Environment maps are typically used44// in 3D rendering, for effects such as quickly approximating45// how shiny surfaces reflect their environment.46//47// Environment maps can be stored in scanline-based or in tiled48// OpenEXR files. The fact that an image is an environment map49// is indicated by the presence of an EnvmapAttribute whose name50// is "envmap". (Convenience functions to access this attribute51// are defined in header file ImfStandardAttributes.h.)52// The attribute's value defines the mapping from 3D directions53// to 2D pixel space locations.54//55// This header file defines the set of possible EnvmapAttribute56// values.57//58// For each possible EnvmapAttribute value, this header file also59// defines a set of convienience functions to convert between 3D60// directions and 2D pixel locations.61//62// Most of the convenience functions defined below require a63// dataWindow parameter. For scanline-based images, and for64// tiled images with level mode ONE_LEVEL, the dataWindow65// parameter should be set to the image's data window, as66// defined in the image header. For tiled images with level67// mode MIPMAP_LEVELS or RIPMAP_LEVELS, the data window of the68// image level that is being accessed should be used instead.69// (See the dataWindowForLevel() methods in ImfTiledInputFile.h70// and ImfTiledOutputFile.h.)71//72//-----------------------------------------------------------------------------7374#include "ImathBox.h"7576namespace Imf {7778//--------------------------------79// Supported environment map types80//--------------------------------8182enum Envmap83{84ENVMAP_LATLONG = 0, // Latitude-longitude environment map85ENVMAP_CUBE = 1, // Cube map8687NUM_ENVMAPTYPES // Number of different environment map types88};899091//-------------------------------------------------------------------------92// Latitude-Longitude Map:93//94// The environment is projected onto the image using polar coordinates95// (latitude and longitude). A pixel's x coordinate corresponds to96// its longitude, and the y coordinate corresponds to its latitude.97// Pixel (dataWindow.min.x, dataWindow.min.y) has latitude +pi/2 and98// longitude +pi; pixel (dataWindow.max.x, dataWindow.max.y) has99// latitude -pi/2 and longitude -pi.100//101// In 3D space, latitudes -pi/2 and +pi/2 correspond to the negative and102// positive y direction. Latitude 0, longitude 0 points into positive103// z direction; and latitude 0, longitude pi/2 points into positive x104// direction.105//106// The size of the data window should be 2*N by N pixels (width by height),107// where N can be any integer greater than 0.108//-------------------------------------------------------------------------109110namespace LatLongMap111{112//----------------------------------------------------113// Convert a 3D direction to a 2D vector whose x and y114// components represent the corresponding latitude115// and longitude.116//----------------------------------------------------117118Imath::V2f latLong (const Imath::V3f &direction);119120121//--------------------------------------------------------122// Convert the position of a pixel to a 2D vector whose123// x and y components represent the corresponding latitude124// and longitude.125//--------------------------------------------------------126127Imath::V2f latLong (const Imath::Box2i &dataWindow,128const Imath::V2f &pixelPosition);129130131//-------------------------------------------------------------132// Convert a 2D vector, whose x and y components represent133// longitude and latitude, into a corresponding pixel position.134//-------------------------------------------------------------135136Imath::V2f pixelPosition (const Imath::Box2i &dataWindow,137const Imath::V2f &latLong);138139140//-----------------------------------------------------141// Convert a 3D direction vector into a corresponding142// pixel position. pixelPosition(dw,dir) is equivalent143// to pixelPosition(dw,latLong(dw,dir)).144//-----------------------------------------------------145146Imath::V2f pixelPosition (const Imath::Box2i &dataWindow,147const Imath::V3f &direction);148149150//--------------------------------------------------------151// Convert the position of a pixel in a latitude-longitude152// map into a corresponding 3D direction.153//--------------------------------------------------------154155Imath::V3f direction (const Imath::Box2i &dataWindow,156const Imath::V2f &pixelPosition);157}158159160//--------------------------------------------------------------161// Cube Map:162//163// The environment is projected onto the six faces of an164// axis-aligned cube. The cube's faces are then arranged165// in a 2D image as shown below.166//167// 2-----------3168// / /|169// / / | Y170// / / | |171// 6-----------7 | |172// | | | |173// | | | |174// | 0 | 1 *------- X175// | | / /176// | | / /177// | |/ /178// 4-----------5 Z179//180// dataWindow.min181// /182// /183// +-----------+184// |3 Y 7|185// | | |186// | | |187// | ---+---Z | +X face188// | | |189// | | |190// |1 5|191// +-----------+192// |6 Y 2|193// | | |194// | | |195// | Z---+--- | -X face196// | | |197// | | |198// |4 0|199// +-----------+200// |6 Z 7|201// | | |202// | | |203// | ---+---X | +Y face204// | | |205// | | |206// |2 3|207// +-----------+208// |0 1|209// | | |210// | | |211// | ---+---X | -Y face212// | | |213// | | |214// |4 Z 5|215// +-----------+216// |7 Y 6|217// | | |218// | | |219// | X---+--- | +Z face220// | | |221// | | |222// |5 4|223// +-----------+224// |2 Y 3|225// | | |226// | | |227// | ---+---X | -Z face228// | | |229// | | |230// |0 1|231// +-----------+232// /233// /234// dataWindow.max235//236// The size of the data window should be N by 6*N pixels237// (width by height), where N can be any integer greater238// than 0.239//240//--------------------------------------------------------------241242//------------------------------------243// Names for the six faces of the cube244//------------------------------------245246enum CubeMapFace247{248CUBEFACE_POS_X, // +X face249CUBEFACE_NEG_X, // -X face250CUBEFACE_POS_Y, // +Y face251CUBEFACE_NEG_Y, // -Y face252CUBEFACE_POS_Z, // +Z face253CUBEFACE_NEG_Z // -Z face254};255256namespace CubeMap257{258//---------------------------------------------259// Width and height of a cube's face, in pixels260//---------------------------------------------261262int sizeOfFace (const Imath::Box2i &dataWindow);263264265//------------------------------------------266// Compute the region in the environment map267// that is covered by the specified face.268//------------------------------------------269270Imath::Box2i dataWindowForFace (CubeMapFace face,271const Imath::Box2i &dataWindow);272273274//----------------------------------------------------275// Convert the coordinates of a pixel within a face276// [in the range from (0,0) to (s-1,s-1), where277// s == sizeOfFace(dataWindow)] to pixel coordinates278// in the environment map.279//----------------------------------------------------280281Imath::V2f pixelPosition (CubeMapFace face,282const Imath::Box2i &dataWindow,283Imath::V2f positionInFace);284285286//--------------------------------------------------------------287// Convert a 3D direction into a cube face, and a pixel position288// within that face.289//290// If you have a 3D direction, dir, the following code fragment291// finds the position, pos, of the corresponding pixel in an292// environment map with data window dw:293//294// CubeMapFace f;295// V2f pif, pos;296//297// faceAndPixelPosition (dir, dw, f, pif);298// pos = pixelPosition (f, dw, pif);299//300//--------------------------------------------------------------301302void faceAndPixelPosition (const Imath::V3f &direction,303const Imath::Box2i &dataWindow,304CubeMapFace &face,305Imath::V2f &positionInFace);306307308// --------------------------------------------------------309// Given a cube face and a pixel position within that face,310// compute the corresponding 3D direction.311// --------------------------------------------------------312313Imath::V3f direction (CubeMapFace face,314const Imath::Box2i &dataWindow,315const Imath::V2f &positionInFace);316}317318319} // namespace Imf320321#endif322323324