diff --git a/AUTHORS b/AUTHORS index a83c0b9d7..32891685c 100644 --- a/AUTHORS +++ b/AUTHORS @@ -4,20 +4,27 @@ # Feel free to add your name and change list. Robert Osfield - - osg and osgUtil. - - pfb, gif, jpeg, tiff, tga, pic plugins. + - osg, osgUtil and osgDB. + - pfb, 3ds, gif, jpeg, tiff, tga, pic, tgz & zip plugins. - sgv, various revisions, now most of code in osgGLUT. + - 2nd iteration of impostor implemtentation. - documentation?! - visual studio workspace files/unix makefiles. - project adim & lead. -Don Burns - - libosg (particularily OpenGL) +Don Burns + - osg (particularily OpenGL) - first version of sgv. - - fly database plugin. - - netscape plugin. + - fly database & osgtgz plugins. - unix makefiles. +Karsten Weiss + - 1st iteration of impostor implemtentation. + - autoconfiscation of the project (currently a seperate branch.) + - rpm spec file. + - documentation. + - bug fixes. + Graeme Harkness - osg::Vec2,Vec3,Vec4 & osg::Quat classes. - reworking of old sgv into osgGLUT and a slim line Demos/sgv. @@ -34,11 +41,47 @@ Brede Johansen - assistance on visual studio workspace files. Ben Discoe + - osgWX and wxsgv demos for integration of OSG with wxWindows. - png plugin. - - a couple of bug fixes and code submissions. -Karsten Weiss - - autoconfiscation of the project. - - rpm spec file. - - documentation. - - bug fixes. + +Byan Woods + - Port to MacOS, various code changes to support this. + - Metrowerks CodeWarrior makefiles. + +Randall Hopper + - port to FreeBSD. + - warning fixes to IRIX compilation. + +Ulrich Hertlein + - support for IBM Mirror Repeat extension in osg::Texture + - support for texture subloading in osg::Texture + - .lwo and .obj plugins. + +Axel Volley + - support for OBJECT_LINEAR and EYE_LINEAR TexGen modes. + - support for the Anistropic texture filter extension. + +Geoff Michel + - .dw (design workshop) loader plugin. + - OpenGL based stats reporting added to osgGLUT::Viewer. + +Indirect Contributors +--------------------- + +J.E. Hoffmann + - lib3ds library. + +Systems in Motion + Peder Blekken + Morten Eriksen + Marius Bugge Monsen + - simage library which provide base for gif,jpg,pic,tga,tiff image loaders. + +Janne Löf + - lw is a LightWave mesh reader, used to develop osgPlugins/lwo. + +Nate Robins - http://www.pobox.com/~ndr/ + - glm file format reader, usedf to develop osgPlugin/obj. + + diff --git a/ChangeLog b/ChangeLog index 922519eed..d0a20e230 100644 --- a/ChangeLog +++ b/ChangeLog @@ -1,6 +1,1026 @@ OSG Change log ============== +9th August 2001 - osg-0.8.42.tar.gz + + o Toned down the specular light values set by default in osgUtil::SceneView:: + setDefaults from 0.8 to .1, this reduces the effect of scaling of + normals on lighting - which was causing a bad flikering affect on + models contains scaling. This points to a need to automatically + scale the normals, but more on this in a future release. + o Removed WXFLAGS from Make/makedefs.* since it is nolonger required. + o From Randall Hopper - fixed compliations problems under IRIX on flt plugin. + o Fixed bugs in osg::Camera::calc_fovx() and calc_fovy() which causing + them to return incorrect values. + o Added code to osgimpostor demo to insert an Impostor above models + which don't have an osg::Group at their root. + o Fixed bug in osgUtil::VisualsRequirementsVisitor so that by default the + alpha and stencil buffers are not required. + o Added reporting of visuals requested in osgGLUT::Viewer::open(), accessible + only as INFO, so doesn't get reported by default. To see the reporting + set the environmental variable OSGNOTIFYLEVEL INFO + + 8th August 2001 - osg-20010808.tar.gz + + o Made the new flt loader the standard flt loader for the release, + deleted the old one. + o From Brede Johansen - fix to material sharing in new flt loader. + - new default values for the light source in + SceneView::setDefaults. + o From Randall Hopper - fixes to osgWX and wxsgv. + + 7th August 2001 - osg-20010807.tar.gz + + o Updated version numbers to reflect the imminent 0.8.42 release. + o Fixes to osg::Camera::calc_fovx() and calc_fovy() which were incorrectly + takening into account zNear in calculation of field of view. + o From Randall Hopper - fixes to warnings under IRIX in the .dw plugin. + o From Randall Hopper/Robert Osfield - fixes for the unix Makefile and + source files in src/Demos/wxsgv demo. + o From Karsten Weiss - bug fixes to osg::Group::removeChild and replaceChild. + + 6th August 2001 - osg-20010806.tar.gz + + o From Ben Discoe - integated osgWX library and Demos wxsgv viewer, which + demonstrates osg integration with wxWindows!!! + note, Unix Makefiles have not been tested yet, and the + the MS projects are not linked up by default. + o From Ben Discoe - fixed a misleading typo in src/osgUtil/Registry.cpp. + - added a guard into SceneView::draw() to prevent + a crash when no scene data is attached to the + scene view and the draw method is called. + o Fixed waning in osg::CullingVolume::operator = (..) related to a missing + return *this; + o Renamed osgUtil::BufferRequirementsVisitor to + osgUtil::VisualsRequirmentsVisitor to make it more in keeping with the + setting up of OpenGL 'visuals', and changed the apply(StateSet&) + method to applyStateSet(StateSet&) to prevent warnings under IRIX. + o Converted src/osgPlugin/newflt/Makefile from dos style text into unix + style text. + + 5th August 2001 - osg-20010805.tar.gz + + o Fixed culling bug related to having osg::Transform within the + scene graph which scale dramatically - the bug was in osg::Plane + which didn't renormalize the plane equation after transformation. + Renormalization is required for the isCulled(BoundingSphere&,..) + method. + o From Geoff Michel - primitive and depth complextity statistics added + to osgUtil::RenderBin/RenderStage and osgGLUT::Viewer. New class + osgUtil::Statistics records no of primitive etc per frame. + o Fixed bug in osgUtil::CullVisitor::pushCullViewState(..) where + the up vector was being incorrectly transformed, resulting in + sporadic impostor orientations. + o From Randall Hooper - fixes to CullVisitor to solve inappropriate warnings + which occured when the near and far values were calculated with the + range numerically rounding errors. Also fix to osg::Matrix::transform3x3 + which was implementated incorrectly. + o From Brede Johansen + - integrated update flt loader which will allow it + to handle old Open Flight file versions. + - also Integrated a small patch to osgPlugins/flt/flt2osg.cpp from + Judd Tracy w.r.t converting ConvertFromFLT::visitDOF(..) to use + osg::Transform instead or osg::Group. I have added a comment + to this method as it still isn't complete, and will need the + osg::Transform's matrix to be set up to refelct the DOFRecord. + - Testing with Berkleys dataset revealled that the new flt loader was + creating one triangle per geoset which causes a massive loss in performance, + I've look for an obvious cause for this, but don't understand the code + enough to track it down. I have reverted to the old flt (0.8.41) plugin + and moved the new flt plugin to src/osgPlugins/newflt. I will make it + the default once the problem has been fixed. RO. + o Added osg::Matrix::set(const float* ) implemention to src/osg/Matrix.cpp. + o Fixed typos of "spshere","albiet","overiden" & "completly" in include/osg. + + +25th July 2001 - osg-0.8.41 + + o Replaced osg::Camera::setModelTransform(..) with more flexible + osg::Camera::attachTransform(TransformMode,Matrix*) which allows + for setting of both a EYE_TO_MODEL or MODEL_TO_EYE transforms. + osg::Camera::getTransform(TransformMode) and dirtyTransform() + has also been added, the later to allow the Camera to know about + external modifications to attach transforms. + o Updated NEWS file. + o Removed second entry for png plugin from src/osgPlugins/Makefile. + + 24th July 2001 - osg-20010724.tar.gz + + o Updated the INSTALL file to include mention of make install and + make help. + o Fixed two bugs in the osg::Impostor implementation, the first related + to the handling of empty impostors, the second was the handling of + impostors composed of depth sorted bins. + + 23rd July 2001 - osg-20010723.tar.gz + + o Bumped version numbers up to 0.8.41 in preperation for the release. + o Fixed a bug in src/osgPlugin/pfb's conversion of Performer texture + filter modes into osg, the mag filter was being set with a invalid + enumerant. The bug resolved itself as OpenGL errors being reported + to the console on loading some .pfb files. + o Added osgUtil::RenderStageLighting to encapsulate the lighting + of the osgUtil::RenderStage, and to allow sharing of lighting + between RenderStages, such when using pre-rendering stages. + o Added osg::Drawable::s/getSupportDisplayList() which can be used + to prevent display lists from being used on specified drawables. + Typical use would be to protect dynamic drawables such as continous + level of details drawables from being encapsulated with a display + list. Attempts to turn on display lists on such a drawable will + now results in a warning, and will have no affect on the drawable. + o Added osgUtil::BufferRequirementsVisitor to traverse a scene graph + establishing the OpenGL buffers required to support rendering of + that scene graph. The results can then be used by applications to + set up there windows with the corret visuals. Modified osgGLUT:: + Viewer::open() to use the new visitor and set up the buffers + accordingly. The calls to gluInitDisplayString in the demos are + now redundent and have been removed. + + 21th July 2001 - osg-20010721.tar.gz + + o Added support for depth sorting of impostor sprites into + osgUtil::CullVisitor and added public methods to osg::CullVisitor + to allow the switching on or off or impostor depth sorting, and + the turning on or off of impostors. + o Added demo osgviews to demostrate multiple views of single scene, + not currently functional, will fix later. + o From Randall Hopper - support for multiple viewports in osgGLUT::Viewer. + o From Geoff Mitchel - new OpenGL based stats reporting added to + osgGLUT::Viewer. Similar in style to Performer's perfly stats. + o Fixed the osg::Camera::home() method so its sets to the OpenGL + defaults position of looking down the z axis, with the upvector + along the +ve y axis. + o Fixed a warning in osg::State. + + 18th July 2001 - osg-20010718.tar.gz + + o Further improvements to the osg::Impostor implementation, various + bugs have been fixed and out of date ImpostorSprite's can now be + reused via an osg::ImpostorSpriteManager, which is stored in the + osgUtil::CullVisitor. + o Added an osgUtil::InsertImpostorsVisitor which traverses the + scene graph inserting osg::Impostor nodes above osg::Group's + (and its subclasses such osg::Transform) and converts osg::LOD + nodes into osg::Impostor nodes. The demo osgimpostor has been + modified to use the new InsertImpostorsVisitor. + + 13th July 2001 - osg-20010713.tar.gz + + o Various improvements to the osg::Imposter implementation, now includes + pixel error calculation which will work for both perspective and + othographic projections. The Impostor doesn't currently support + texture reuse, but the much of the code to support is implemented, + yet have to tie up the loose ends for the next release now. + o Fixes to osg::Texture::copyTexSubImage2D to ensure that _mag_filter + was set to LINEAR, to ensure that mipmaps arn't used. + o Fixed Visual C++ workspace file for .dw plugin, to ensure under + debug build it correctly links to glu library. + + 12th July 2001 - osg-20010712.tar.gz + + o Added src/Demo/osgimpostor to demonstrate how to use the new osg::Imppostor + node and to test the impostor implementation. + o Implemented first cut of osg::Impostor, ImpostorSprite, + and RenderToTextureStage. Implemention not complete, and bugs exists + which prevent the textured quad appearing with its texture?! + o Fixed osg::Camera::zNear()/zFar() methods which returning the wrong values. + o Updated AUTHORS file. + o From Geoff Mitchel, .dw (design workshop) loader plugin. + o Fixed coordinate transformation in osgPlugins/obj - Alias Wave OBJ loader. + o Fixed minor unsigned to signed comparision warning in osg::Texture. + + 1st July 2001 - osg-20010701.tar.gz + + o Rewritten osg::Camera class to support Otho, Frustum and Perspective + projection modes. Significant API changes have been made, the new + Camera implementation is not backwards compatible. + o Added osg::ClippingVolume to represent a convex clipping volume. + o Added osg::Plane class to support view frustum clipping and other operations + requiring plane operations. + o Made corrections to osgtexture usage details. + o From Ulrich Hertlein - fixes to osg::Texture to prevent bind of textures + to NULL image data and added missing #include to + osgUtil::IntersectVistor. + o Removed the erroneous inline keyword from infront of + osg::StateSet::setRenderBinToInherit(..) which was causing compilation + errors under IRIX. + o Fixed file permission problems in include/osg/Object, and osgDB. + o Fixed a bug in osgGlut::Viewer where view frustum culling and small + feature culling could be toggled off, + o Fixed a bug in osg::Quat::makeRot(Vec3,Vec3) where the angle + calculated was incorrectly calculated. Also added a couple of + set methods and made the constructors inline. + o Added osg::Drawable::dirtyBound() which should be called when geometry + is updated. Note it does not dirty geodes above - this will have to be + done by caller. + + June 26th osg-20010626.tar.gz + + o Several changes related to making the NewCullVisitor now the + standard CullVisitor, since it now has greater functionalility, + performance and more robust than the previous incarnation of + CullVistor. + - Removed osgUtil::Renderer as this is now rendundent thanks to + the new RenderStage functionality. + - Replaced osgUtil::CullVisitor by osgUtil::NewCullVisitor and + removed NewCullVisitor references as these are nolnger needed. + - Moved osgUtil::CullViewState out of osgUtil::CullVisitor header + and into its only file header and source files. + - Updated osgUtil::SceneView to only refer to new standard CullVisitor. + - Updated Unix and VisualStudio files accordingly. + o Fixed problem related to calculation of the near far planes when + a non-uniform transformation exists in the scene graph. + o Fixed problem related to view fustum culling when a non-uniform + transformation exists in the scene graph. Solution was to use + the transpose of the inverse transformation matrix to transform + plane normals rather than the transformation matrix as used for + points. + o Fixed two bugs in osg::notify(), pinpointed by Randall Hooper. + The first was in osg::initNotifyLevel() - the check for DEBUG was + hidding the settings for DEBUG_FP and DEBUG_INFO since it was first + of these in the if/else code and all contain the word DEBUG. The + solution was to move DEBUG check to the last entry. + The second bug was related to osg::setNotifyLevel() - if this method + was called before the first call to osg::notify() then osg::notify + would automatically call initNotifyLevel and overwrite the + setNotifyLevel value. The fix was to make setNotifyLevel call + initNotifyLevel itself before setting the value, and add protection + into initNotifyLevel so that the internal code is never executed + more than once. + + June 22nd - osg-20010622.tar.gz + + o Added osgUtil::NewCullVisitor::createOrReuseMatrix() and + createOrReuseRenderLeaf() methods to allow reuse of what was temporary + memory from frame to frame. Combined with the new near and far + plane code, the cull traversal for models like Performer town is + now 40-60% faster, and on models with a large nuber of internal + transforms the figure can be 80+% faster :-) + o Changed the techinique for calculating the near and far planes inside + NewCullVsitor to be more efficient - now about up to and over 4 times + faster! Makes a particular difference on models with large numbers + of transform nodes. + o Changed osg::Draw::drawImmediateMode() so that it takes an osg::State + as a parameter. + o Changed the referencs to -glut in unix Makefiles so that is is specified + by a $(GLUTLIB) paramter, which is now set in the Make/makedefs.* files. + This allows the GLUTLIB to be changed to allow linking to static glut + libraries. It defaults still defaults to -glut as before, so no change + in standard behavior will be noticed. + o Added osgUtil::RenderToTextureStage in preperation for support for + Imposters. + o Added osg::Impostor, ImpostorSprite header and source files, these files + are simply shells for future integration work, and do not currently function + as Impostors. Modified osg::NodeVisitor and osg::CullVisitor so that + they now recognise the Impostor node. + + June 18th - osg-20010618.tar.gz + + o Reverted to the prev_ReaderWriterPNG.cpp since I was having problems + loading png files that used to work. This will break other png files + for which the new_ReaderWriterPNG.cpp was created to handle. Both + clearly arn't up to job and need a rewrite. Will do this later... + o Made osg::Camera::draw_PROJECTION() and osg::Camera::draw_MODELVIEW() + virtial functions to allow subclassing. + o Removed the references to opengl.lib and glu.lib from the lwo loaders + as they arn't required. + o Under Unix, changed the names of the jpeg and tiff plugins from libdb_jpg.so + and libdb_tif.so to libdb_jpeg.so and libdb_tiff.so respectively, and + used the new addFileExtensionAlias to alias the common file etension to + use these new names. This makes it consistent with the name of the + directories and source files in the distribution. Windows already used + this convention. + o Added osgDB::Registry::addFileExtensionAlias(,) to allow file extension + to be aliased to appropriate osgPlugins. Current default aliases are: + addFileExtensionAlias("rgba", "rgb"); + addFileExtensionAlias("int", "rgb"); + addFileExtensionAlias("inta", "rgb"); + addFileExtensionAlias("bw", "rgb"); + addFileExtensionAlias("jpg", "jpeg"); + addFileExtensionAlias("jpe", "jpeg"); + addFileExtensionAlias("tif", "tiff"); + addFileExtensionAlias("geo", "lwo"); + addFileExtensionAlias("lw", "lwo"); + o Pulled libtiff, libpng and libjpg win32 image libraries from the + OpenIL image library distrbution and placed them into a zip archive + for win32 users to install, instead of having to trawl the internet + for them. + + June 15th 2001 - osg-20010615.tar.gz + + o Updated the TARGET_INCLUDE_FILES to reflect current set of include + files so that make install works properly once more. + o Fixed the src/osgUtil/Tesselate.cpp so that it detects the + defination of GLU_VERSION_1_2 and use modern glu tesselation + functions rather than the old style deprecated glu tess functions. + This fixed compilation problems under recent versions of Mesa. + o Fixed the texture coordinates of the top of the tank in the hangglide + demo - the center point texture coords were not being initiliaed + o Fixed a crash in osg::Texture::apply() which occurred when it was + called without a valid image being attached. The fix is simply + to add an _image.valid() check at the begining of the method. + o Changed src/Demos/sgv/Makefile so that it defaulted to *not* linking + with Performer - the previous dev release had this as default which + it shouldn't have. + + + June 13th 2001 - osg-20010613.tar.gz + + o Added support osg::StateSet::RenderBinDetails into .osg + reader/writer plugin. This now allows multi-pass models to be saved + and loaded, such as osfreflect demo can now be reproduced in a .osg + file. + o Added support for osg::Stencil, osg::Depth, osg::ClipPlane and + osg::ColorMask classes to .osg reader/writer plugin. + o Added support osg::Drawable:UseDisplayList into .osg reader/writer plugin. + o Fixed the src/osgPlugins/pfb/ConvertFromPerformer.cpp so that is scales + the shininess value correctly when converting materials to osg. + o Added checks to osg::Material::set*(..) methods to use the new bounds + checking utilties to clamp values to valid ranges. + o Added include/osg/BoudingChecking header file with template definitions for + clamping paramters to specified ranges. template functions provided are: + clampGEQUAL(...), clampLEQUAL(..) amd clampBetweenRange(). + + + 11th June 2001 - osg-20010611.tar.gz + + o Went through library source adding, where required to suppress spurious + warnings in during MSVC++ debug compilation, pragma warning ( disable 4786) + o Changed the mapping of coordinates in the .obj and .lwo loaders from + +x east, +y upwards, +z north (as specified in file specs) to the OSG's + +x east,+y north,+z updwards. The windings of triangles has also been + flipped to handle this change. + o Added a RegistryPtr class to handle the destruction of the the + registry, assinging NULL to the pointer once the registry is + deleted. Subsequent calls to the get() of RegistryPtr will + return NULL, which can be used for testing whether the registry + still exists or not. This means that Registry::instance() will + now return NULL if the registry has been automatically deleted. + The RegisterDotOsgWrapperProxy and RegistryReaderWriterProxy have + been modified to use this new property to prevent the registry + being called once it has been deleted. This has been done to + prevent out of order destruction causes seg faults on exit. + o Added Tesselator to src/osgUtil to be used in for breaking up + concave polygons into triangles - uses the glu tesselator. + o Reimplemeted src/osgPlugins/lwo to use new tesselator and allocate + seperate vertex lists for each material type. + o From Randall Hopper - Added missing int from static definition in + src/GLUT/Viewer.cpp. + o Removed use to OSGHOME from src/osgPlugins/lwo & obj Makefiles, + replacing with normal relative include paths for makedefs and rules. + o Removed unnecessary glib reference from src/osgPlugins/lwo/Makefile. + + 7th June 20001 - osg-200010607.tar.gz + + o From Ulrich Hertlein - .obj and .lwo loaders. Various fixes and porting + to Windows done by Robert Osfield. + o Fixed bug in osgcube related to the color of the cube having an alpha + value of 0.0, which resulted in all OpenGL fragmennts failing the + AlphaFunc test which is now on by default. Changed the alpha to 1.0 + for opaque. + o Implemented a multi-pass reflection demo in src/Demos/osgreflect which + uses the stencil buffer to tag mirror bits, and 5 render bins to order rendering + as Mark Kilgard's paper "Improving Shadow and Reflections via the + Stencil Buffer" which can be download at the NVidia website. + o Moved osg::Stencil, osg::Depth and osg::ColorMask from src/Demos/osgreflect + into the core osg library. + o Added osg::ClipPlane StateAttribute subclass to encapsulate OpenGL's + glClipPlane function. + + + 31st May 2001 - osg-20010531.tar.gz + + o Added osg::Stencil, osg::Depth and osg::ColorMask StateAttribute + subclasses to the osgreflect demo to enable multi-pass use of the + stencil buffer. osgreflect.cpp has yet to be modified to take + advatange of these new state class or multi-bin functionality, + this will be done for the next dev release. The Stencil, Depth + and ColorMask classes will be added into the core osg for the + next release. + o Added beginings of osgUtil::NewCullVisitor which will support the + new multi-pass/stage functionality, and replace osgUtil::CullVisitor + once the functionality is finalised. osgUtil::SceneView has been + modified to use either NewCullVisitor & RenderBin etc or the + previous CullVisitor/Renderer functionality. SceneView defaults + to the NewCullVisitor. + o Added beginings of osgUtil::RenderBin,osgUtil::DepthSortedBin and + osg::RenderStage to support multi-pass and multi-stage rendering. + o Fixed bug in osg::Matrix::mult(const Matrix& lhs,const Matrix& rhs) + which occured when either the lhs or rhs paramters were the same + matrix and 'this'. The osg::Matrix::invert(const Matrix& m) also + sufferd the potential problem. In both methods I've added checks + against the 'this' pointer to trap these cases and create a temporary + copy of 'this' before proceeding. + o From Ulrich Hertlein - support for texture subloading in osg::Texture. + + 25th May 20001 - osg-20010525.tar.gz + + o Added new osgUtil::RenderLeaf class for storing drawable, matrix & + depth data and for rendering in conjunction with osgUtil::Renderer. + RenderLeaves are themselves stored inside the RenderGraph and + replace the previous pair which did a similar job. + The new class allows extension, via subclassing, of the data stored + in a RenderLeaf, such as id's for picking, and also override of + the local rendering behavior via a its virtual render(..) method. + o Changed the printing of frame rate stats so that it prints out + appropriately every second rather than every frame, therefore + reducing the overhead of printing out to the terminal. + o Added prioritizeTextures() method to osgUtil::Renderer which parses + the draw bins and calculates the most appropriate texture priotization. + o Added getTextureObject(..) and getTextureObjectSize() to osg::Texture + to allow details of the texture object to be publicly accessed. + o Implemented view frustum culling that switches of redundent checks + against the side sides of the view frustum when traversing children. + +19th May 2001 - osg-0.8.40 (minor updates made to release of 18th May) + + o Small correction to NEWS file. + o Small updates to index.html. + o Removed '-ldl' from makedefs.irix.* as it is not required. + + 18th May 2001 - osg-0.8.40 + + o Updated Make/makedefs.* to better support FreeBSD compilation. + o Updated index.html and doc/Doxyfiles/* to include references to + the osgDB library and osgtexture demo program. + o Changed the default IRIX make to make.std, and make.nonstd to + make irix.old. + o Added src/Demos/osgtexture - a demo to demostrate the various texture + modes possible with osg::Texture. + o Fixed CullVisitor::setCullingActive(..) so that it now sets + the current CullViewState's modes as it should, previously only the + CullVisitor::pushMatrix() was setting these values. + o From Zang Zong Shan - bug fix to osg::Group::removeChild() to ensure that + the parent is removed from its child properly. + o From Karsten Wiess (with small mods for to avoid sqrt by Robert Osfield) + added osg::BoundingSphere::intersects( const BoundingSphere& bs ) + o Add comments to methods include/osg/StateSet and StateAttribute. + o Added osg::Texture::readImageFromFramebuffer(...) from Karsten Weiss' + Imposter code. Note, name of method has been changed (from get..) and + State parameter added to allow the handling of multiple contexts. + o Changed the png plugin to use code from simage rather than previous + png code that the osg used, solving a crash reported on some png + files. + o Added temporary fixes into include/osg/StateSet, src/osg/StateSet.cpp + and src/osgPlugins/osg/StateSet.cpp to get round a crash under Windows + when saving a dot osg file. Actual problem has not been isolated, + so fix will be removed once real problem has been solved. + o From - added support for IMB_MIRROR_REPAT extension into + osg::Texture and .osg plugin. + o Added code to osgPlugins/osg/Texture.cpp to record the original + name of the image filename to be passed onto the image filename, + instead of the absolute path with name as recorded by the image + plugins themselves. This changes preserves the name from loaded + .osg through to any subsequent save .osg. + + 10th May 2001 - osg_20010510.tar.gz + + o Bumped version numbers up to 0.8.40 + o Added #include to osgUtil/SmoothingVisitor. + + 9th May 2001 - osg-20010509.tar.gz + + o From Randall Hooper - modifications to osg::Timer, Makefile's and + the addition of Makefile/makedefs.freebsd Makefile/makerules.freebsd + to add support for the FreeBSD flavor of Unix! + o From Axel Volley - fixes to FieldReader and RenderGraph headers and + to Make/makedefs.irix.* to fix compilation problems which have + occurred under IRIX with the latest dev versions. + o Added the ability to clean and reuse the RenderGraph tree from + frame to frame, thus reducing the memory overhead of allocation + and deleting on each frame. + + 8th May 2001 - osg-20010508.tar.gz + + o Added osg::StateAttribute::clone()=0 to the StateAttribute header file + to complete the overriding of osg::Object's virtual methods. + o Revised the StateAttribute/StateSet/State API a small amount to make + it more consistent. + o Fixed memory leak in new version of CullVisitor where more Matrices + were being allocated than required, and were left unreferenced. + o Fixed viewing bug in hangglide, introduced in osg-20010418.tar.gz + with the modifications to the osg::CameraManipulator base class. + o Added const and inline to methods in include/osg/* header files, + making it more explicit which methods are inline, and which paramters + and returns types are const. The later can help compilers produce + appropriate compiler errors when inappripriate things are done with + return types, which is good for compile error detection, and also + allows the compiler to more aggressive optimizer code. + o Fixed compilation error in osg::Output::open(,,,) under windows by + removing method. This is not a problem to end users since the + method was only added for absolute completness of overriding the + ofstream::open() method. + + 6th May 2001 - osg-20010506.tar.gz + + o Added osg::State::apply(const osg::StateSet*) to apply a StateSet + without requiring a pushStateSet(),apply(),popStateSet() as required + in previous dev version. Combined with the two changes changes + below draw traversal times have been reduced significantly on + models with large number of state changes (such as billboarded trees + in Performer town.) Both Cull and Draw traversal times are now + faster than previous releases. + o Moved the support for tranform Matrices in the osgUtil::RenderGraph + into a Drawable/Matrix pair rather than one per RenderGraph element. + Modifed osgUtil::CullVisitor and osgUtil::Renderer to reflect this + change. + o Added 'inline' keyword to numerous methods in osg and osgUtil header + files to give a less subtle hints to compilers than a inline method + is indeed inline. VisualC++ particularily seems to need inline + to specified explicitly. + o Added osgDB::Output::s/getPathNameHint() and Output::setPathNameHint(..) + to to help future support for absolute filepaths, relative file paths + in the .osg outout. Currently only implements AS_IS and FILENAME_ONLY. + + 3rd May 2001 - osg-20010503.tar.gz + + o Modified osgUtil::SceneView to reference the RenderGraph and Renderer's. + o Modified osgUtil::CullVisitor so it creates a RenderGraph instead on + the previous DrawBin. + o Added osg::StateSet::g/setRenderingHint(..) to allow hints to be passed + on to the Renderer to allow it place the drawables in the appropriate + rendering bin for rendering. This allows, for instance the rendering + transparent bin to be addressed independantly from the current GL_BLEND + mode. An int is used so more than just Opqaue or Transparent bins could + be referenced from within the scene graph (but these must be handled + by Renderer subclasses.) + o Replaced osgUtil::DrawBin by osg::Renderer which traverses a RenderGraph + to generate its own render bins, supports basic coursed grained state + sorting. Designed to subclassed to allow users to modify the rendering + behaviour. + o Implemented new osgUtil::RenderGraph class for storing state, matrix and + drawable data produced from a cull traversal (such as by CullVisitor.) + o Removed all osg::StateAttribute subclasses static void enable()/disable() + as these have been made redundent by the new osg::State/StateSet & + StateAttribute functionality. + o Removed osg::Lighting since it is now redundent thanks to new + functionality of osg::State/StateSet & StateAttribute functionality. + o Reworked the .osg, .pfb, .3ds and .flt loaders to use the new + osg::StateSet class. + o Reworked osgUtil, osgDB, osgGLUT, Demos/osgcube, osgreflect and hanglide + to use the new osg::StateSet class. + osg::StateSet class. + o Renamed osgUtil::GeoStateManipulator to osgUtil::StateSetManipulator + be consitent with GeoState's replacement. + o Replaced osg::GeoState with new more flexible osg::StateSet. + osg::GeoState nolonger exists so users will have to port to use the + new osg::StateSet. Functionality can easily be mapped across to the + StateSet so this should not be difficult task. + o Removed the deprecated RenderVisitor since it has now been replaced + by the more flexible and powerful CullVisitor/DrawBin pair (which + themselves may be replaced later by more flexible and powerful...:) + o Fixed osg:Geode::computeBound() method so that it handled empty geode's + correctly setting the Bounding Sphere to default initialized state to + represent and empty sphere. Previous (nan,nan,nan) was calculated for + the center of the bounding sphere for empty data. + o To fix a compliation collision when #define DEBUG is used and Notify is + included, have changed enum NotifySeverity { ... DEBUG=5, FP_DEBUG=6 } + to enum NotifySeverity { ... DEBUG_INFO=5, DEBUG_FP=6 } + + 18th April 2001 - osg-20010418.tar.gz + + o From Neil Salter, additions to osgUtil of new + osgUtil::GUIEventHandler, + osgUtil::SceneViewManipulator and + osgUtil::GeoStateManipulator. + o Fixed date problems in distribution which occured in osg-20010416.tar.gz. + o Added make stats option to the root Makefile to allow the number of lines + of code in each component of the OSG to be logged. + + 16th April 2001 - osg-20010416.tar.gz + + o Added Don Burns sgv key bindings documentaiton into doc/sgv.html + o Added s/getState() to osgUtil::DisplayListVisitor to provide state + for the compile display list method to use. Added new DisplayListMode + COMPILE_ON_DISPLAY_LISTS which is implemented so that if display + lists are already switched on in the traversed scene graph are + compiled. + o Added support for multiple OpenGL contexts (and hence multiple seperate + texture object and display lists) into osg::Texture::apply(State&) and + osg::Drawable::draw(State&). This allows the OSG to work in multipipe + systems. + o Added (State& state) parameter to both osg::StateAttribute::apply(State&) + and osg::Drawable::draw(State&) to allow the handling multiple OpenGL + context. All subclass' of StateAttribute and Drawable have been updated + to reflect this new paramter. + o Added s/getContextID() to osg::State to handle the specification of + a unique unsigned int to specifiy the current active OpenGL context. + This value is in turn used by osg::Texture and osg::Drawable to + manage multiple texture binds and display lists, one for each + OpenGL context, thus enabling multi-pipe support. + o Fixed the osgDB::Registry::writeObject() so that it supports the + writing of osg::Object UniqueID out to .osg. + + 7th April 2001 - osg-20010407.tar.gz + + o Added numerous get and set methods to a large proportion of classes in + the core osg library. Made methods const correct where appropriate. + Also modifed several enum type names to be more consistent from class + to class. + o From Karsten Wiess - added osg::Matrix::makeRot(Vec3,Vec3). + o Added ostream << operator to osg::Matrix for debugging purposes. + o Changed osg::Object::isSameKindAs(Object*) to be const correct i.e + isSameKindAs(const Object*) const. All subclasses of osg::Object + have been updated to reflect this change. + o Changed the osg::Billboard::get* functions so that they return + values rather than requiring the paramter passesing. This has been + done to be more consistent with the rest of the osg, make it easier + to use and improve the potential for compiler optimization. + o Moved loadObject/Image/NodeFile from include/osg/Registry into + include/osgDB/ReadFile, and renamed them readObject/Image/NodeFile + to keep consistency with ReaderWriter & Registry. + o Moved saveObject/Image/NodeFile from include/osg/Registry into + include/osgDB/ReadFile, and renamed them writeObject/Image/NodeFile + to keep consistency with ReaderWriter & Registry. + o Moved database & dynamic plugin support out of core osg library into + seperate osgDB library which is now an optional layer above the core osg. + o Moved osg ascii support & ReaderWriter out of core osg library and into + a seperate osgPlugins osg plugin. + o Moved rgb image reader out of core osg library and into a seperate + osgPlugins osg plugin. + o Removed osg::Scene since it is now redundent thanks to the new ability + to attach osg::GeoState to all internal nodes within the scene graph. + o Removed osg::Sequence as it was nothing more than a shell implemention, + which could be inappropriately used. Will implement properly later. + + 29th March 2001 - osg-20010329.tar.gz + + o renamed the following methods in osg::GeoSet for consistancy: + getNumIndices() -> getNumCoordIndices() + getCIndex() -> getCoordIndices() + getNumNIndices() -> getNumNormalIndices() + getNIndices() -> getNormalIndices() + getNumCIndices() -> getNumColorIndices() + getColIndex() -> getColorIndices() + getNumTIndices() -> getNumTextureIndices() + getTIndex() -> getTextureIndices() + o Itegrated changes from Bryan Woods for Mac port: + - include/osg/Timer - small macintosh #define comment out. + - src/osg/FileNameUtils.cpp - added using std::tolower,std::stlen + within #machintosh guards. + - src/osgGLUT/Viewier.cpp - #ifndef machintosh printing out + of library name and version in constructor. + - src/sgv.cpp & repsective files osgcube,osgreflect and hanglide have + moved the glutInit(,) call to the top of each main function. + - updated the Metroworks file + o Added a src/Demos/sgv/Makefile.performer and Makefile.standard to + all the direct linking to Performer hack to be easily applied to + sgv to get round the know problems with dynamically linking to + Peformer. + o Changed osgUtil::SceneViewer::draw() method so it would clear background + even if no model have been attached to the scene view. + o Changed include/osg/Notify to use #ifdef __GNUC__ instead of __linux + as guard for dummy code required to prevent a gcc warning. + + + +25th March 2001 - osg-0.8.39.tar.gz + + o Added option for uint indices in osg::GeoSet to allow very large models + to be represented. + o Moved the distribution version numbering from previous osg-0.8-39.tar.gz + style to more standard osg-0.8.39.tar.gz The distribution directory also + now reflects the new version numbering, so rather than the + OpenSceneGraph-0.8 the directory will be osg-0.8.39. These two changes + bring the OSG into line with established conventions in the open source + world. + o From Karsten Wiess - added small piece of dummy code into + include/osg/Notify to prevent inappropriate gcc warnings. + o From Neil Salter + - updated the doc/Doxyfiles directory to handle the + proposed version number i.e. osg-0.8.39 for next version. + - updated NEWS file to be compatibile with new automated scripts for + generating Doxygen documentation for distribution. + - updated osg banner in html pages to indicate documentation is + from the distribution. + o Fixed typo in src/osgPlugins/lib3ds/track.cpp which caused the lib3ds + to fail to build. + + 21st March 2001 - osg_src-20010321.tar.gz + + o Added osg::StateAttribute base class, changed all state attribute + classes so that they now inherit from osg::StateAttribute and + changed osg::GeoSet to work with osg::StateAttribute. All + StateAttrbute subclasses (Texture/TexGen...) all now register + with the osg::Registry, and all .osg file reading uses these + prototype as per image,node, and drawable prototypes. Although + osg::GeoState is still hardwired to certain state attributes + as before much of the infrastructure around it has be upgraded + to pave the way for a more flexible osg::GeoState. + o Removed _drawBin->reset() from CullVisitor::reset() since it + should be reset extrenal to the CullVisitor. + o Added osgUtil::SceneView::s/getDrawBin() methods. + o Changed the lib3ds includes to be local header paths and + changed lib3ds/float.h to lib3ds/lib3ds_float.h to avoid + collisions with the system float.h. Note, the changes to + path required changes to both the source, Unix Makefile and + VisualStudio lib3ds.dsp files. + o Changed the usage text to reflect the name of osgreflect. + o Removed app and cull traversal calls from osgGLUT::Viewer::draw(), + since there are now handled by their own app() and cull() methods. + + 18th March 2001 - osg_src-20010318.tar.gz + + o Implemented base class osg::Drawable from which osg::GeoSet is now + derived. osg::Geode now contains a list of osg::Drawables, and + osg::Registry and osg::Input have been extended to handle dynamic + exensions of osg::Drawable in file IO. Numerous files have been + modified to support the new structure, it is also likely to break + user code, look at the code with the plugins and demos to see how + adapt code to the new style. The changes are likely to be minimal - + for instance geode->addGeoSet(geoset) would change to + geode->addDrawable(geoset). Some .osg files no longer load due to + a bug introduced with the above changes - still investigating it, + likely to be just a typo somewhere... + o Renamed DCS -> Transform. + o Renamed Seg -> LineSegment. + + 15th March 2001 - osg_src-20010315.tar.gz + + o Added osgUtil::SceneView::setAppVisitor(), getAppVisitor() and + app() to support user defined app traversal. + o Added support for the new SceneView::app() traversal into osgGLUT/Viewer + and cleaned up the app(),cull() and draw() methods. + o Added an AppVisitor to the Demos/osgreflect which rotates the loaded + model about its center point. + o Added a osg::NodeVisitor::reset() to be called prior to each traversal + to allow subclasses to flush internal set for each traversal. + + 14th March 2001 - osg_src-20010314.tar.gz + + o Added reflection demo, which can be found in Demos/osgreflect. + o Made osg::Reference::_refCount mutable and the ref() & unref() const + methods, to faciliate the referencing of const objects. + o Added support for attaching osg::GeoState to internal nodes in the + scene graph. This enables subgraph's state to be overridden, which + enables several multipass techniques, such as planar reflections. + o Added src/osg/State.cpp to help manage pushing and popping of current + state. include/osg/State previously existed but was just a shell, + and has now been updated to provide funcitonal interface! + + o Fixed a typo in VisualStudio/Demos/osgcube/osgcube.dsp which caused debug + build link time errors - a space was missing between two library names. + o Added osg::FrontFace state attribute class for managing the OpenGL + glFrontFace(,) on a per osg::GeoState basis. + Added files include/osg/FrontFace and src/osg/FrontFace.cpp and + modified include/osg/GeoState, src/osg/GeoState.cpp. + o Added osg::GeoState::merge(osg::GeoState* lhs,osg::GeoState* rhs) + method to osg::GeoState, for use in the new osgUtil::DrawBin. + o Updated comments in include/osgUtil/SmoothingVisitor, TriStripVisitor + and include/osg/Scene. + o Corrected header guards in DisplayListVisitor to be consistent with rest + of library, and updated comments. + o Update NEWS with small revisions. + o Fixed crash in NvTriStrip due to TriStripVisitor calculating the + number of vertices one to small, which resulted in memory errors. + + 6th March 2001 - osg_src-20010306.tar.gz + + o Added new class osgUtil::CullVisitor and osgUtil::DrawBin which are + steps towards spliting up the osgUtil::RenderVisitor into its component + parts. + o Updated NvTriStripObject.cpp with patch from NVidia. + o Updated the NEWS information to allow automatic parsing of the file + for NEWS and headlines on the osg website implmented by Neil Salter. + o From Karsten Weiss - added comments and correct typo's in + include/osg/Scene and include/osg/Group + o Added osg::PolygonMode state attribute class for managing the OpenGL + glPolygonMode(,) on a per osg::GeoState basis. + Added files include/osg/PolygonMode and src/osg/PolygonMode.cpp and + modified include/osg/GeoState, src/osg/GeoState.cpp and + src/osgGLUT/Viewer.cpp to utilize the new class. + + + 4th March 2001 - osg_src-20010304.tar.gz + + o Changed osg::Scene and osg::DCS to use osg::ref_ptr<> instead of + directly managing dynamically memory. + o Fixed crash due memory errors in osgUtil::IntersectVistor. + o Updated NEWS with main items for ChangeLog dating back to the first + days of the ChangeLog. + o Changed the file extension checking methods in ReaderWriterOSG, + ReaderWriterRGB, ReaderWriterOSGTGZ, ReaderWriterTGZ, ReaderWriterZIP + to use use new function osg::equalCaseInsensitive(lhs,rhs). + o General purge of warnings in libs and plugins. + o From Neil Salter + - spelling corrections to include/osgGLUT/Viewer. + - updates to doc/Doxyfiles/*. + o Added extensions guard to src/Demos/hangglide/ReaderWriterFLY.cpp + which fixes the bug where the hangglide demo does can only read + .osg or .fly input files. + o Updated the index.html and doc/index.html with the OSG banner and + new text and various clean ups. Added doc/OpenSceneGraphBanner.jpg + o Fixes to get dev version below compiling under IRIX std and non std + compile options - FileNameUtils.cpp, Seg.cpp, NvTriStrip.cpp and + lib3ds/quat.cpp. + + 1st March 2001 - osg_src-20010301.tar.gz + + o Macintosh port of osg from Bryan with mods for integration by Robert. + - Added Metrowerks make files. + - Added strdup defintion into src/osg/FileUtils.cpp to ensure compatiblity + under mac. + - Added #defined(macintosh) into include/osg/Types to define M_PI etc. + - Integrated changes to src/osg/DynamicLibrary.cpp for macintosh port. + - Integrated changes to src/osg/FileNameUtils.cpp for macintosh port. + - Integrated changes to src/osg/FileUtils.cpp for macintosh port. + - Integrated changes to src/osg/Registry.cpp for macintosh port. + - Integrated changes to src/osg/Texture.cpp for macintosh port. + - Integrated changes to src/osg/Timer.cpp for macintosh port. + - Integrated changes to src/osg/GLExtensions.cpp for macintosh port. + - Integrated changes to src/osgUtil/RenderVisitor.cpp for macintosh port. + - Integrated changes to src/osgUtil/IntersectVisitor.cpp for macintosh port. + - Integrated changes to include/osgGLUT/Viewer for macintosh port. + - Integrated changes to src/osgGLUT/Viewer.cpp for macintosh port. + - Integrated macintosh timmer support into include/osg/Timer + - Modified src/osg/Texture.cpp to take account of the new file + name type in osg::Image. + - Converted osg::Image::_fileName from char* to std::string to + avoid issues with portability due to strdup not being availble + on mac. + + 28th Faburary 2001 - osg_src-20010228.tar.gz + + o Updated the osgUtil::TriStripVisitor to create seperate tri strips, + which fixes crashes which occured under Windows. Significant + speed up is can be achieved for many datasets by applying the + tri stripper. However, right now it can flip triangle orientation + which if back face culling is on may cause a model to apparantly + disapper... Turn off back face culling to see all surfaces. This + 'feature' will be fixed to maintain surface orientation before and + after tri stripping. + + 24th Feburary 2001 - osg_src-20010224.tar.gz + + o Modified osg::GeoSet to support sharing of the coord, normal, texture and + colour index list in both the .osg IO and the handling fast paths for + rendering. + o Added support for smoothing groups to 3ds plugin. + o Added support for beautify to unix makefiles and ran it on .cpp files. + o Added osgUtil::TriStripVisitor which use NvTriStrip to create + optimized triangular strips. Modified osgGLUT::Viewer to tri + strip when 'R' is pressed (for tRi strip). *Note* this is work in + progress and its is known to crash in certain circumstances. + o From Karsten Weiss - added comments to osg::Switch. + o Removed redundent src/Demos/hangglide/Trees.cpp. + o Added < operator to osg::Vec2,3 & 4. + o Changed the implementation of osgUtil::SmoothingVisitor to fix a bug + and to increase algorithm speed - now O(nlogn) rather than O(n^2). + +17th Feburary 2001 - osg_src-0.8-38.tar.gz + + o Added REPLACE to osg::TexEnv which supports the equivilant GL_REPLACE + texture environment mode. + o Fixed osg::GeoSet rendering bug which occurs when an coord index + list is mixed with normals (or colors) which are attached to the + geoset on a per vertex basis. + o Made appropriate osgUtil::RenderVisitor get methods const. + o Changed osg::Geode::getNumGeosets() to osg::Geode::getNumGeoSets() for + consistentcy and made it and several other osg::Geode methods const. + + 15th Feburary 2001 - osg_src-20010215.tar.gz + + o Added beginings of a 3ds loader, based on lib3ds, can now load meshes + and textures. + o Added file search function osg::findFileInDirectory(..) which has + the option of doing case insensitve comparisons of names. Useful for + handling dos mixed case filenames under unix. 3ds files are particularily + prone to incorret case between filename in .3ds file and file on disk, + this method allows these problem filename to be handled gracefully + under unix. Also add osg::equalCaseInsensitive() which takes two + strings and compares them for equality ignoring case to support the + above osg::findFileInDirectory(..) + o Added new demo app - osgconv which takes loads specified files, and then + writes out the resultant model to a specified file. + o Updated version number in doc/Doxyfiles/Doxyfile_all, src/osg/Version.cpp + src/osgUtil/Version.cpp and src/osgGLUT/Version.cpp. + o Added include/osgGLUT into the TARGET_DIRS list in Make/makedefs.linux + and Make/makedefs.irix.nonstd & makedefs.irix.std + +10th Feburary 2001 - osg_src-0.8-37.tar.gz + + o Moved camera manipulator registration from osgGLUT::Viewer::constructor, + and setting of home in osgGLUT::Viewer::init() to happen in + osgGLUT::Viewer::run() and only when not other initialized. This allows + programs with use the the osgGLUT::Viewer class can set up there own + camera manipulators as in src/Demos/hangglide. + o Moved src/osgPlugins/fly to src/Demos/hangglide and created a simply + hang glider flight simulator. + o Added support for ARB and S3TC texture compression into osg::Texture and + methods to control the way that the internalFormat is used for OpenGL + textures. + o Updated version numbers in src/osg/Version.cpp, osgUtil/Version.cpp, + osgGLUT/Version.cpp and doc/Doxyfile. + o Removed src/osgPlugins/matrix.h&.cpp,vector.h&.cpp,oldtrees.cpp. + o From Karsten Wies - fix to src/osg/Switch.cpp to solve IO bug, + corrections to comments in include/osg/Registry. + o From Neil Salter - changes to support both doc++ and doxygen documention. + + 29th January 2001 - osg_src-20010129.tar.gz + + o Moved src/Demos/cube to src/Demos/osgcube to remove install conflicts + under RH7, changed cube.cpp to osgcube.cpp, changed src/Demos/osgcube/Makefile + changed VisualStudio/VisualStudio.dsw and VisualStudio/Demos/cube etc.. + o Removed two obsolete object files in src/osg/{ExtensionSupported.o,OSG.o} + o Removed vi swp file OpenSceneGraph-0.8/dist/.osg.spec.swp + o Fixed file permission of in doc/MindMap and doc/UML. + o Removed comma's at end of enumerator list in include/osg/GeoState + and src/osgPlugins/FaceRecord.h + +28th January 2001 - osg_src-0.8-36.tar.gz + + o Rewrote the implementation of osg::notify() once again to solve + a crash under Windows when an int is passed to the absorb stream. + Have moved the ofstream to a local static definition in osg::notify() + rather than a global in Notify.cpp. Note, the absorb stream is + now always set to "nul" or "/dev/null" under Windows and Unix + respectively, and can no longer be set to a user file. + o Did spell check on include/osg/Notify, Notify.cpp, FAQ. + o Added a couple of comments to src/osg/Billboard.cpp to explain + current incomplete implementation. + o Fixed minor warning in include/osg/mem_ptr. + o Updated src/osg/Version.cpp, src/osgUtil/Version.cpp & src/osgGLUT/Version.cpp + to version 0.8.36. + +25th January 2001 - osg_src-0.8-35.tar.gz + + o Added basic comments to osgUtil::GUIActionAdapter explain a little of + how it might be used in. + o Added reading from .osg files of the "Axis x y z" for osg::Billboard, + previously osg::Billboard::readLocalData ignored the Axis paramter + even though it was saved. + o From Karsten Weiss : + - Spelling corrections to comments in include/osg/Object & Node. + - Extra comments to include/osg/Matrix. + o Fixed bug in osg::Image::ensureDimensionsArePowerOfTwo() where + message was being written out without guarding against the + image name being NULL. + o Fixed the osg::notify() messaging function under Windows, with + same functionality that has exisited under unix - allowing users + to absorb messages, send them to cerr, cout or to a nominated file, + controlled via environmental variables, or set functions with the + application. + o Went through all include/osg header files removing redundent + includes to minimize compile time. Removed include's + of glu.h and glx.h in the include/osg/GL header file as these + are only required in specific cases. + o Removed UnrefOp functor from inclide/osg/Referenced and changed + all dependent files to use osg::ref_ptr<> instead for handling memory. + o From Don Burns : + -code for smoothing normals on osg::GeoSet's, integrated code + into osgUtil::SmoothingVisitor (RO) + -Bug fix for for_each_triangle() to ensure that + orientation of triangles is correct. + o Added new osg::mem_ptr template class (include/osg/mem_ptr) for + refence counting with data which does not internally support + ref/unref themselves (as required my ref_ptr and supplied normally + by deriving form osg::Referenced) instead delagating the + responisbility of reference counting and deleting unreferenced + memory to an associated osg::MemoryAdapter. + o Moved osg::ref_ptr from include/osg/Referenced into its own + header file include/osg/ref_ptr. Cleaned up numerous files + to include the new header file. + o Moved osg::MemoryAdapter from osg::Node into its own file, + include/osg/MemoryAdapter, and moved osg::ReaderWriter from + osg::Registry into its own file include/osg/ReaderWriter. + o Clean up most warnings associated with the new -W -Wall pedantic + warnings option. + o Rename include/osg/OSG to FileUtils to reflect its now less central + role in the OSG scene graph, renamed osg::FindFile osg::findFile, + osg::SetFilePath to osg::setFilePath, added osg::getFilePath() and + add osg::getDirectoryContents. Removed most references to the + old include/osg/OSG as they wern't required! Renamed the references + which were required. + o Renamed osgUtil::GUIActionAdapter::needRedraw() to requestRedraw(), + needContinuousUpdate() to requestContinuousUpdate() and + needWarpPointer to requestWarpPointer. Removed the redundent bool + paramter from requestRedraw. Updated Trackball, Drive and Flight + manipulators and osgGLUT to reflect new names. + Changed the default drive mode so it uses left and right mouse + buttons for speed control instead of using the mouse y position. + Both are still availble via original 'A' and 'Q' keybindings. + o Moved contents of README to INSTALL, and made README a bare bones + readme. Updated index.html to link to both. + o Moved include/osg/ExtensionSupported to include/osg/GLExtensions. + Renamed osg::ExtensionSupported to osg::isGLExtensionSupported, + reimplemented osg::isGLExtensionSupported to use std::set's for + increased speed. Added osg::getGLExtensionFuncPtr() as a cross + platform way to get OpenGL extension functions. Updated Point.cpp + and Texture.cpp to use the new methods and clean up the support + for OpenGL extensions. Cleaned up include/OSG/GL. + o From Axel Volley: + Added support for OBJECT_LINEAR and EYE_LINEAR TexGen modes, + Added support for the Anistropic texture filter extension to + Texture.cpp. + o Moved the information about plugin dependancies from README to index.html + and made the links to the appropriate web sites. Added links for data + sources. + o Updated the FAQ in to reflect progress to beta and new documetation details. + o Moved the createNodeFromImage functionality from the image readers + into osg::Registry::readNode(), removing readers readNode() functions. + Added osg::Registry::setCreateNodeFromImage(bool flag) and equivilant + get function to support the switching on and off of this functionality. + This is then is by the new archieve functionality. o Added src/osgPlugins/tgz for general tarball models. o Added src/osgPlugins/zip for general zipped models. o From Don, src/osgPlugins/osgtgz for a osg tarball models. diff --git a/FAQ b/FAQ index 51e23ddab..48c417287 100644 --- a/FAQ +++ b/FAQ @@ -4,14 +4,14 @@ o API's feature set The scene graph is arranged with geometry nodes (osg::Geode's) as leaf nodes and internal nodes such as osg::DCS's/Groups/LOD etc for position the - geometry objects within the scene and organising scene behaviour. + geometry objects within the scene and organizing scene behavior. - culling techniques? Currently view frustum culling, small feature culling, and OpenGL's native backface culling. The OSG has been designed so it can be - easily extended, so if you have a favoured culling technique it - won't be difficult to utilise it in the OSG. + easily extended, so if you have a favored culling technique it + won't be difficult to utilize it in the OSG. - terrain / indoor support @@ -23,7 +23,9 @@ o API's feature set However, if you wish to take advantage of specific optimization such as adaptive meshing such as ROAM, or procedural culling such as when entering a room or when racing round a track then the OSG's could be - easily extend to achieve this. + easily extend to achieve this. This is demonstrated in VTP Enviro + which is is based on the OSG, extended osg::GeoSet to provide CLOD + for terrain. These features are not currently on the todo list for version 1.0 as we intend to keep the OSG focused on the core scene graph. However, @@ -59,13 +61,13 @@ o What is the design philosophy behind the OSG. - Channel configuration The Scene Graph is just that. It manages a tree structure of different - node types that allow management over the behaviour of graphical + node types that allow management over the behavior of graphical objects. The Traversers allow us to use the scene graph to render scenes in the most efficient manner, as well as providing maximum functionality for a real-time simulation. The stages are (taken from the Performer approach) : - App - This is the application part of the simulation that interfaces + App - This is the application part of the simulation that interfaces with the outside world, that is control devices, pilot input, animation engines, effects, event engines, etc, etc (there's much more). This is also the stage that determines what the viewpoint is and consequently @@ -111,7 +113,7 @@ o What is the design philosophy behind the OSG. The MP issues include, process (or thread) management and synchronization. Performer has several MP models. We also need to - consider that this software will probably run on seperate PCs + consider that this software will probably run on separate PCs altogether, so that the SGI concept of a single machine with multiple rendering pipes needs to be extended to include multiple PC's, which need to be synchronized across Ethernet or something. @@ -120,7 +122,7 @@ o What is the design philosophy behind the OSG. can be only one App for multiple Cull/Draw pairs. This model might extend quite nicely to a multiple PC environment, in which each PC runs a Cull/Draw pair, and one central machine runs App, broadcasting the - viewing frustums for each viewing channel and synchronizing all. + viewing frustum for each viewing channel and synchronizing all. Lastly, channel configuration. Currently we now do this by opening a window, choosing a visual, size, etc. It is often desirable to have @@ -155,7 +157,7 @@ o What is the design philosophy behind the OSG. use. -o Would the OSG be a good candidate for terrain visualisation. +o Would the OSG be a good candidate for terrain visualization. Terrain is one of the great candidates for scene graphs. Two management schemes will help you out : Level Of Detail management and Visibility @@ -221,12 +223,11 @@ o What are the intended target platforms? o What platforms are currently supported? - The OSG is currently developed under Windows95, Linux and Irix. Platform + The OSG is currently developed under Windows95, Linux,Irix and MacOS. Platform specific makedefs are provided for Linux and Irix, and VisualC++ 6.0 Workspace files for MS Windows platforms. - The OSG should also compile under Windows98/NT and 2000 but has not yet - been tested. + The OSG also compiles under Windows98/NT and 2000. o What further platforms will be supported in the near future? @@ -242,7 +243,7 @@ o I'm wondering when the OSG will be ready for release. Once the design converges to a stable API we will issue it as a beta, depending on the various factors one would hope to have the API nailed - down during summer 2000. + down during early-mid 2001. A full release with stable API and implementation will be available... Can't set any dates but we can be sure it'll be after then beta release :-) @@ -278,7 +279,7 @@ o What differentiation between the OSG and other OS projects such as OpenRM/ each of these scene graphs. DDG doesn't show quite the same heritage, and possibly loses a little cleanness of design with it. OpenRM is an attempt at a Object Orientated scene graph but it C... This is - about a close as I got with it, as IMHO C++ really is the best currently + about a close as I got with it, as IMHO C++ really is currently the best language for a modern scene graph The OSG is also strongly influenced by Performer, this a due to the @@ -311,6 +312,9 @@ o Is there a class diagram for the OSG, or white paper on the projects goals? The documentation in the distribution has been generated automatically using the excellent Open Source tool doc++, which creates class diagrams. + UML diagrams have been generated and can be found in the documentation + directory, along with mind maps on design patterns used in the osg, + and the mission/goals of the osg. We haven't written an official white paper on projects goals or a design overview yet. Knowledge of Performer will help in understanding some of the basics @@ -326,7 +330,7 @@ o Do you need C++ coding support? o Any recommendations for useful programming books to read to help understand and contribute to the OSG? - Good practices are suprisingly hard to come by. C and C++ give you so + Good practices are surprisingly hard to come by. C and C++ give you so much rope to hang yourself, but there's few books which really give a developers the rule book of good coding practices. I found Effective C++ a refreshing contribution to this end. The Design Patterns book can @@ -337,7 +341,7 @@ o Is there a mailing list? Yes indeed, hosted by source forge, so to subscribe head to : http://sourceforge.net/projects/openscenegraph and follow the - 'Lists' link and follow the intructions. + 'Lists' link and follow the instructions. o How do I submit my contributions? diff --git a/Make/makedefs.irix.nonstd b/Make/makedefs.irix.nonstd index 0f3e2ef3e..604a00cd5 100644 --- a/Make/makedefs.irix.nonstd +++ b/Make/makedefs.irix.nonstd @@ -8,8 +8,8 @@ DEPFILES = $(OBJS:.o=.d) C++ = CC YFLAGS = -d -#CFLAGS = -O2 -n32 -MDupdate $(MAKEDEPEND) -CFLAGS = -O2 -n32 -DOSG_USE_IO_DOT_H -OPT:Olimit=0 +#CFLAGS = -O2 -n32 -MDupdate $(MAKEDEPEND) -DOSG_USE_IO_DOT_H -OPT:Olimit=0 -DEBUG:woff=1682 -DEBUG:woff=3303 +CFLAGS = -O2 -n32 -DOSG_USE_IO_DOT_H -OPT:Olimit=0 -DEBUG:woff=1682 -DEBUG:woff=3303 C++FLAGS = ${CFLAGS} CPPFLAGS = ${CFLAGS} @@ -19,8 +19,9 @@ LDFLAGS = -O2 -n32 -OPT:Olimit=0 .cpp.o: $(C++) $(C++FLAGS) -c $< -PFLIBS = -lpfdu -lpfutil -lpf -limage - +DYNAMICLIBRARYLIB = +PFLIBS = -lpfdu -lpfutil -lpf -limage +GLUTLIB = -lglut # # TARGET_DIRS are directories that would not exist on the system except @@ -29,6 +30,8 @@ PFLIBS = -lpfdu -lpfutil -lpf -limage # TARGET_DIRS = \ /usr/include/osg \ + /usr/include/osgDB \ + /usr/include/osgGLUT \ /usr/include/osgUtil \ /usr/share/OpenSceneGraph\ /usr/share/OpenSceneGraph/data\ diff --git a/Make/makedefs.irix.std b/Make/makedefs.irix.std index f05944786..8ee008903 100644 --- a/Make/makedefs.irix.std +++ b/Make/makedefs.irix.std @@ -8,8 +8,8 @@ DEPFILES = $(OBJS:.o=.d) C++ = CC YFLAGS = -d -#CFLAGS = -O2 -n32 -MDupdate $(MAKEDEPEND) -CFLAGS = -O2 -n32 -LANG:std -OPT:Olimit=0 +#CFLAGS = -O2 -n32 -MDupdate $(MAKEDEPEND) -LANG:std -OPT:Olimit=0 -DEBUG:woff=1682 -DEBUG:woff=3303 +CFLAGS = -O2 -n32 -LANG:std -OPT:Olimit=0 -DEBUG:woff=1682 -DEBUG:woff=3303 C++FLAGS = ${CFLAGS} CPPFLAGS = ${CFLAGS} @@ -19,7 +19,9 @@ LDFLAGS = -O2 -n32 -LANG:std -OPT:Olimit=0 .cpp.o: $(C++) $(C++FLAGS) -c $< +DYNAMICLIBRARYLIB = PFLIBS = -lpfdu -lpfutil -lpf -limage +GLUTLIB = -lglut # # TARGET_DIRS are directories that would not exist on the system except @@ -28,6 +30,8 @@ PFLIBS = -lpfdu -lpfutil -lpf -limage # TARGET_DIRS = \ /usr/include/osg \ + /usr/include/osgDB \ + /usr/include/osgGLUT \ /usr/include/osgUtil \ /usr/share/OpenSceneGraph\ /usr/share/OpenSceneGraph/data\ diff --git a/Make/makedefs.linux b/Make/makedefs.linux index bc8989f83..997b5cd59 100644 --- a/Make/makedefs.linux +++ b/Make/makedefs.linux @@ -11,12 +11,16 @@ YFLAGS = -d LCINCS += -I/usr/X11R6/include LC++INCS += ${LCINCS} CFLAGS = -O2 -W -Wall $(LCINCS) +#CFLAGS = -g -W -Wall $(LCINCS) C++FLAGS = ${CFLAGS} CPPFLAGS = ${CFLAGS} -LDFLAGS = -O2 -W -Wall +LDFLAGS = -O2 -W -Wall -L/usr/X11R6/lib +#LDFLAGS = -g -W -Wall -L/usr/X11R6/lib +DYNAMICLIBRARYLIB = -ldl PFLIBS = -lpfdu -lpfutil -lpf -ldl +GLUTLIB = -lglut # @@ -26,6 +30,8 @@ PFLIBS = -lpfdu -lpfutil -lpf -ldl # TARGET_DIRS = \ /usr/include/osg \ + /usr/include/osgDB \ + /usr/include/osgGLUT \ /usr/include/osgUtil \ /usr/share/OpenSceneGraph\ /usr/share/OpenSceneGraph/data\ diff --git a/Make/makerules.irix b/Make/makerules.irix index 6304a7ab8..b18f75739 100644 --- a/Make/makerules.irix +++ b/Make/makerules.irix @@ -19,6 +19,10 @@ to_unix : for f in *.cpp ; do to_unix $$f $$f; done for f in *.h ; do to_unix $$f $$f; done +beautify : + for f in *.cpp ; do mv $$f $$f.bak; bcpp $$f.bak $$f; rm $$f.bak; done +# for f in *.h ; do mv $$f $$f.bak; bcpp $$f.bak $$f; rm $$f.bak; done + # force it depend : @@ -32,9 +36,9 @@ $(MAKEDEPEND) : $(C++FILES) $(CFILES) docs: [ "$(TARGET_BASENAME)" != "" ] && \ - mkdir -p ../../doc/$(TARGET_BASENAME) && \ - doc++ -d ../../doc/$(TARGET_BASENAME) -H -A ../../include/$(TARGET_BASENAME)/* && \ - echo $(TARGET_BASENAME) HTML documentation created in ../../doc/$(TARGET_BASENAME) + mkdir -p ../../doc/doc++/$(TARGET_BASENAME) && \ + doc++ -d ../../doc/doc++/$(TARGET_BASENAME) -H -A ../../include/$(TARGET_BASENAME)/* && \ + echo $(TARGET_BASENAME) HTML documentation created in ../../doc/doc++/$(TARGET_BASENAME) install : home @ make __install diff --git a/Make/makerules.linux b/Make/makerules.linux index bc539735f..f3e435335 100644 --- a/Make/makerules.linux +++ b/Make/makerules.linux @@ -18,6 +18,11 @@ to_unix : for f in *.cpp ; do to_unix $$f $$f; done for f in *.h ; do to_unix $$f $$f; done +beautify : + for f in *.cpp ; do mv $$f $$f.bak; bcpp $$f.bak $$f; rm $$f.bak; done + for f in *.h ; do mv $$f $$f.bak; bcpp $$f.bak $$f; rm $$f.bak; done + + # force it depend : $(C++) $(C++FLAGS) -M $(C++FILES) $(CFILES) > $(MAKEDEPEND) @@ -28,11 +33,14 @@ $(MAKEDEPEND) : $(C++FILES) $(CFILES) %.o : %.cpp $(C++) $(C++FLAGS) -c $*.cpp -o $*.o +%.o : %.c + $(C++) $(C++FLAGS) -c $*.c -o $*.o + docs: [ "$(TARGET_BASENAME)" != "" ] && \ - mkdir -p ../../doc/$(TARGET_BASENAME) && \ - doc++ -d ../../doc/$(TARGET_BASENAME) -H -A ../../include/$(TARGET_BASENAME)/* && \ - echo $(TARGET_BASENAME) HTML documentation created in ../../doc/$(TARGET_BASENAME) + mkdir -p ../../doc/doc++/$(TARGET_BASENAME) && \ + doc++ -d ../../doc/doc++/$(TARGET_BASENAME) -H -A ../../include/$(TARGET_BASENAME)/* && \ + echo $(TARGET_BASENAME) HTML documentation created in ../../doc/doc++/$(TARGET_BASENAME) install : home @ make __install diff --git a/Makefile b/Makefile index 92982acd3..2d96863ab 100644 --- a/Makefile +++ b/Makefile @@ -4,19 +4,20 @@ MAKE_PREP = Make/makedefs Make/makerules DIRS = src +VERSION = osg-0.8.42 all : $(MAKE_PREP) - for f in $(DIRS) ; do cd $$f; make; cd ..; done + for f in $(DIRS) ; do cd $$f; $(MAKE) || exit 1; cd ..; done docs : - cd src; make docs; + cd src; $(MAKE) docs; Make/makedefs : @ cd Make;\ case `uname` in\ IRIX|IRIX64) \ - ln -sf makedefs.irix.nonstd makedefs ;;\ + ln -sf makedefs.irix.std makedefs ;;\ Linux) \ ln -sf makedefs.linux makedefs;;\ esac @@ -34,65 +35,107 @@ linux: cd Make;\ ln -sf makedefs.linux makedefs;\ ln -sf makerules.linux makerules - make + $(MAKE) + +freebsd: + cd Make;\ + ln -sf makedefs.freebsd makedefs;\ + ln -sf makerules.freebsd makerules + $(MAKE) + irix: - cd Make;\ - ln -sf makedefs.irix.nonstd makedefs ;\ - ln -sf makerules.irix makerules - make - -irix.std: cd Make;\ ln -sf makedefs.irix.std makedefs ;\ ln -sf makerules.irix makerules - make + $(MAKE) + +irix.old: + cd Make;\ + ln -sf makedefs.irix.nonstd makedefs ;\ + ln -sf makerules.irix makerules + $(MAKE) help : @echo Usage : - @echo \ make - @echo \ make linux - @echo \ make irix.std - @echo \ make irix.nonstd - @echo \ make depend - @echo \ make clean - @echo \ make clobber - @echo \ make doc - @echo \ make snapshot - @echo \ make install - @echo \ make instlinks - @echo \ make instclean + @echo \ $(MAKE) + @echo \ $(MAKE) linux + @echo \ $(MAKE) irix + @echo \ $(MAKE) irix.old + @echo \ $(MAKE) depend + @echo \ $(MAKE) clean + @echo \ $(MAKE) clobber + @echo \ $(MAKE) doc + @echo \ $(MAKE) release + @echo \ $(MAKE) dev + @echo \ $(MAKE) install + @echo \ $(MAKE) instlinks + @echo \ $(MAKE) instclean clean : $(MAKE_PREP) - for f in $(DIRS) ; do cd $$f; make clean; cd ..; done + for f in $(DIRS) ; do cd $$f; $(MAKE) clean; cd ..; done find lib -type f -exec rm {} \; rm -f bin/* clobber : $(MAKE_PREP) clean - for f in $(DIRS) ; do cd $$f; make clobber; cd ..; done + for f in $(DIRS) ; do cd $$f; $(MAKE) clobber; cd ..; done rm -f $(MAKE_PREP) depend : $(MAKE_PREP) - for f in $(DIRS) ; do cd $$f; make depend; cd ..; done + for f in $(DIRS) ; do cd $$f; $(MAKE) depend; cd ..; done to_unix : for f in $(DIRS) ; do cd $$f; to_unix Makefile Makefile; cd ..; done - for f in $(DIRS) ; do cd $$f; make to_unix; cd ..; done - cd include/OSG; for f in *.h ; do to_unix $$f $$f; done + for f in $(DIRS) ; do cd $$f; $(MAKE) to_unix; cd ..; done + cd include/osg; for f in * ; do to_unix $$f $$f; done + cd include/osgUtil; for f in * ; do to_unix $$f $$f; done + cd include/osgGLUT; for f in * ; do to_unix $$f $$f; done -snapshot: - make doc; - make clobber; - (cd ..; tar cvf - OpenSceneGraph-0.8 | gzip > osg_src-`date "+%Y%m%d"`.tar.gz) +beautify : + for f in $(DIRS) ; do cd $$f; $(MAKE) beautify; cd ..; done +# cd include/osg; for f in * ; do mv $$f $$f.bak; bcpp $$f.bak $$f; rm $$f.bak; done +# cd include/osgUtil; for f in * ; do mv $$f $$f.bak; bcpp $$f.bak $$f; rm $$f.bak; done +# cd include/osgGLUT; for f in * ; do mv $$f $$f.bak; bcpp $$f.bak $$f; rm $$f.bak; done +release: $(MAKE_PREP) + $(MAKE) docs; + $(MAKE) clobber; + (cd ..; tar cvf - $(VERSION) | gzip > $(VERSION).tar.gz) + +dev: $(MAKE_PREP) + $(MAKE) docs; + $(MAKE) clobber; + (cd ..; tar cvf - $(VERSION) | gzip > osg-`date "+%Y%m%d"`.tar.gz) install : - for f in $(DIRS) ; do cd $$f; make install; cd ..; done + for f in $(DIRS) ; do cd $$f; $(MAKE) install; cd ..; done instlinks : - for f in $(DIRS) ; do cd $$f; make instlinks; cd ..; done + for f in $(DIRS) ; do cd $$f; $(MAKE) instlinks; cd ..; done instclean : - for f in $(DIRS) ; do cd $$f; make instclean; cd ..; done + for f in $(DIRS) ; do cd $$f; $(MAKE) instclean; cd ..; done +instcheck : + diff -q include/osg/ /usr/include/osg/ + diff -q include/osgUtil/ /usr/include/osgUtil/ + diff -q include/osgDB/ /usr/include/osgDB/ + diff -q include/osgGLUT/ /usr/include/osgGLUT/ + diff -q lib/libosg.so /usr/lib/libosg.so + diff -q lib/libosgUtil.so /usr/lib/libosgUtil.so + diff -q lib/libosgDB.so /usr/lib/libosgDB.so + diff -q lib/libosgGLUT.so /usr/lib/libosgGLUT.so + diff -q lib/osgPlugins/ /usr/lib/osgPlugins/ + +stats : + @echo stats : + cat include/osg/* src/osg/*.cpp | wc -l + cat include/osgUtil/* src/osgUtil/*.cpp | wc -l + cat include/osgDB/* src/osgDB/*.cpp | wc -l + cat include/osgGLUT/* src/osgGLUT/*.cpp | wc -l + cat include/osgWX/* src/osgWX/*.cpp | wc -l + cat include/*/* src/*/*.cpp | wc -l + cat src/Demos/*/*.cpp | wc -l + cat src/osgPlugins/*/*.cpp src/osgPlugins/*/*.h | wc -l + cat include/*/* src/*/*.cpp src/Demos/*/*.cpp src/osgPlugins/*/*.cpp src/osgPlugins/*/*.h | wc -l diff --git a/Metrowerks/OpenSceneGraph.mcp b/Metrowerks/OpenSceneGraph.mcp new file mode 100644 index 000000000..fb084c164 Binary files /dev/null and b/Metrowerks/OpenSceneGraph.mcp differ diff --git a/NEWS b/NEWS index a8e7c29c4..013c97050 100644 --- a/NEWS +++ b/NEWS @@ -1,22 +1,194 @@ OSG News (most significant items from ChangeLog) ================================================ +9th August 2001 - osg-0.8.42.tar.gz -6th December 2000 - osg_src-0.8-34.tar.gz + >>> New osgWX library for integration of OSG with wxWindows apps. - o New osgGLUT library assist writing of osg demos. - o New cube demo. - o Improved handling of image sizes which arn't a power of 2. - o Performer plugin can now work as of plugin to Performer or the - OSG (with a few caveates:) + This release sees a relatively minor number of enhancements over + 0.8.41, the most significant being the new osgWX library and wxsgv + demo written by Ben Discoe. + Also from Brede Johansen in this release is the improvements in support for older + .flt (Open Flight) files such versions 12 & 13. Previously only version + 15.6 files had been tested and developed to. + + Last but by no means least, several bug fixes related to view frustum + culling have been made. + + +25th July 2001 - osg-0.8.41.tar.gz + + >>> Support added for multi-pass and multi-stage rendering including Impostors. + + The key feature developed is a highly flexible framework for multi-pass and + multi-stage rendering techniques. Unlike most scene graphs and games + engines the OSG has as dynamic framework which automatically configures + itself at runtime. + + Building ontop of the new framework's multi-stage rendering capabilities, + support for Impostors (hirachical image caching) has been integrated into + the core scene graph library making extremely easy to take advantage of + this advanced rendering techinque - normally only seen in research papers. + Check out osgimpostor demo to see how easy it is to add osg::Impostor + nodes to your own models. Impostors are particularily effective are + reducing scene complexity whilest minimizing the visual impact, making it + ideal for scenes with large numbers of complex objects such as a city + scene, or a dense forest. + + Taking advantage of the new framework's multi-pass rendering capabilities + is osgreflect demo which illustrates how to achieve planar relfections + using the stencil buffer and multi-pass rendering. + + The cool thing about both the osgreflect and osgimpostor demos is that + there is no hardwiring to achieve the results, the scene graph stores + all the information neccessary to specify the number and type of rendering + passes, and the framework handles the rest behind the scenes. This also + makes it very easy to add these advanced rendering techinques to your + own applications as everything is cleanly encapsulated with + osgUtil::SceneView. + + New loaders have been added to support .lwo (Light Wave), .obj + (Alias Wavefront) and .dw (Design Workshop) 3D file formats making it + even easier to compose your own worlds from models sourced from the + web or your own. + + osg::Camera has been totally revamped and now supports asymetric + and othographics projections in addition to the symetrical perspective + projections. + + And finally, support for texture subloading has been added to osg::Texture + and osg::Image. This allows textures to be updated dynamically, and + has already been used for mpeg video playback! + + +19th May 2001 - osg-0.8.40.tar.gz + + >>> Project lead, Robert Osfield, makes full-time commitment to OSG. + + This is the first full release since project lead, Robert Osfield, made + a move to pursue the OSG's development full-time. This commitment has + been made to bring the API rapidly towards maturity, and to provide + high quality support and consultancy services. Please contact + robert@openscenegraph.com if you have any queries. + + This release marks a significant step forward in the maturity of the + API, with several major changes to the library in the areas of state + handling, database support, and portability. + + To improve the extensibility of the OSG's handling of OpenGL state, + new classes have been introduced to replace the previous hardwired + state handling classes. The new classes also allow improved state + sorting and lazy state updating which boosts both cull traversal + and particularly draw traversal performance. + + To improve the modularity, interopability and conceptual clarity the + support classes for database loading have been moved from the core + osg library into their own osgDB library. Support for the .osg + ASCII native database format and the .rgb reader has moved into its own + osgPlugins library to further the cleanliness of the core library. + + Support has be added for multiple OpenGL context's and hence multi-pipe + systems such as sgi's Onyx2, allowing each context to have its own + display list and texture objects. + + The culler and rendering support in osgUtil has also been improved, and + significantly speeded up for complex models. + + Also just in, thanks to Randall Hopper for adding support for FreeBSD :-) + + +23rd March 2001 - osg-0.8.39.tar.gz + + >>> Port of OSG to MacOS underway + + The first steps towards support of MacOS have been taken by Bryan Woods, + adding Metrowerks project files and adding support for MacOS into the + core scene graph. Work still in progress so assistance welcome to + complete the task. + + Other major developments have been the addition of two new base classes + osg::StateAttribute and osg::Drawable which are designed to allow greater + extensibility of OpenGL state management and primitives. + + +17th Feburary 2001 - osg-0.8.38.tar.gz + + >>> New 3DS loader added + + The OpenSceneGraph now supports the 3DS file format. This makes + available a huge range of potential models. Check out + http://www.3dcafe.com or http://www.3drocketfuel.com for some juice. + +10th Feburary 2001 - osg_src-0.8-37.tar.gz + + >>> Texture compression now supported + + The OpenSceneGraph now provides support for ARB and S3TC texture + compression. This allows more textures to be loaded onto graphics + card memory, resulting in happier users and a better world in which + to live. + + This release also sees the addition of a simple hang gliding flight sim + demo. + +25th January 2001 - osg_src-0.8-35.tar.gz + + >>> Anisotropic texturing now supported and loading of gzip compressed files + + Anisotropic texturing provides for the next step in quality texturing + filtering above tri-linear and is especially effective when viewing + texture surfaces at shallow angles. + + Also added in this release is on-the-fly support for loading gzipped + (.osgtgz, .tgz) and zipped (.zip) database files. This features allows + users to store whole databases (models and textures) in a single + tar ball and unpack them automatically on running the osg. This + is ideal for browsing the web. 22nd December 2000 - osg_src-0.8-33.tar.gz - o Integrated Don's work on adding glVertexArrays etc to osg::GeoSet. - o Incorportated the following image loaders from the simage library. - src/osgPlugins/gif - /jpeg - /pic - /tga - /tiff + >>> Support added for OpenGL vertex arrays, and several key image loaders. + + Support for OpenGL vertex arrays has been added to improve performance, + particularly accelerating PC based graphics. + + Also added is support gif, jpeg, pic, tga, tiff image formats via + dynamic plugins. + +8th Decemeber 2000 - osg_src-0.8-32.tar.gz + + >>> New high resolution, low latency timer class - osg::Timer. + + Real-time graphics relies upon accurate timers for updating physics + simulations and managing constant framerates. The OSG now provides + osg::Timer which, when supported, takes advantage of hardware timers. + + +18th November 2000 - osg_src-0.8-29.tar.gz + + >>> Support for detail drawing with osg::PolygonOffset. + + Rendering of polygons which overlay underlying geometry, such + as white lines on a runway, can now be achieved utilizing the + new osg::PolygonOffset which encapsulates glPolygonOffset to + avoid z fighting which otherwise hampers such detailing. + +10th November 2000 - osg_src-0.8-28.tar.gz + + >>> New Open Flight .flt loader! + + Thanks to Brede Johansen submission of .flt loader, the OSG can now + read Open Flight .flt databases. + +3rd November 2000 - osg_src-0.8-26.tar.gz + + >>> Driving and Flight modes have been added to viewers. + + osgUtil::DriveManipulator and osgUtil::FlightManipulator have been + added to allow the scene graph viewer (sgv) and other viewers to + support a drive and flying modes. These modes can be accessed + in sgv by pressing '2' and '3' respectively ('1' returns to + trackball manipulator). Left mouse button accelerates forward, + middle stops motion and right deccelerates. + diff --git a/README b/README index 5a80c5b26..738245882 100644 --- a/README +++ b/README @@ -1,178 +1,13 @@ -The following is a very basic intro of how to get the OSG going under Linux, -IRIX and Windows. Each intro mentions OpenSceneGraph-Data, it is recommended -that you also download it alongside this source distribution. +Welcome to the Open Scene Graph (OSG). -The scene graph depends upon Standard C++, STL and OpenGL so you need a C++ -compiler up to the task and OpenGL or Mesa installed. The viewer depends upon -GLUT which you'll need to download and install from the GLUT website. The -OSG has it own native ascii file format, and .rgb image reader inbuilt which -allows you read the example data with any dependancies othe then C++, STL and -OpenGL. +For compiling the OSG under all platforms (Linux, FreeBSD, IRIX, Windows +and Mac) please read INSTALL. -The OSG also has several plug-ins which support non-native 3d database and -image formats, several have no dependancies on external libraries (flt,fly, -tga & pic), while others (pfb,jpeg,gif,tiff) require other libraries to be -installed to compile them. If you don't already have them installed then -don't worry, you'll still be able to use the OSG. The core osg library and -viewer is designed has been designed to load the plug-ins at run-time only -and if they are required to load a specific data set. If you don't need them -for your datasets then it won't matter that you havn't been able to compile -all the plug-ins. A full list of dependancies and where to download the -required libraries are near the bottom of this file. - -If you're comming across the OSG for the first time and want to get started -quickly, go right ahead and follow the compilation instructions. You can always -later download the libraries which the plug-ins require if you eventually need -them. - -If you havn't already checked it out, for a list of distribution contents, -contacts and links to documentation check out index.html. - - -Compiling under Linux : ------------------------ - - Add the following to your .cshrc : - - setenv OSGHOME - setenv OSGDATA - setenv OSGFILEPATH ./:${OSGDATA}:${OSGDATA}/Images: - setenv LD_LIBRARY_PATH ${LD_LIBRARY_PATH}:${OSGHOME}/lib - setenv PATH ${PATH}:${OSGHOME}/bin - - Or the following if you're using a sh compatible shell : - - export OSGHOME= - export OSGDATA= - export OSGFILEPATH=./:${OSGDATA}:${OSGDATA}/Images: - export LD_LIBRARY_PATH=${LD_LIBRARY_PATH}:${OSGHOME}/lib - export PATH=${PATH}:${OSGHOME}/bin - - To compile, from the OSG root directory, type : - - make - - Note, make should automatically detect linux and copy the - Make/makerules.linux and Make/makedefs.linux over the - default Make/makerules and Make/makedefs. If autodetection - does not work type 'make linux'. - - -Compiling under IRIX : ----------------------- - - Add the following to your .cshrc : - - setenv OSGHOME - setenv OSGDATA - setenv OSGFILEPATH ./:${OSGDATA}:${OSGDATA}/Images: - setenv LD_LIBRARYN32_PATH ${LD_LIBRARYN32_PATH}:${OSGHOME}/lib - setenv PATH ${PATH}:$OSGHOME/bin - - Or the following if you're using a sh compatible shell : - - export OSGHOME= - export OSGDATA= - export OSGFILEPATH=./:${OSGDATA}:${OSGDATA}/Images: - export LD_LIBRARYN32_PATH=${LD_LIBRARYN32_PATH}:${OSGHOME}/lib - export PATH=${PATH}:$OSGHOME/bin - - Since the OSG uses Standard C++ features such as STL it is important - to have an up to date version of the MIPSPro compilers. The library - has been tested under MIPSPro7.3 & MIPSPro7.2.1, and *may* compile - under previous versions but has yet to be tested. It is recommened - to use MIPSPro7.3.1.1m. - - To compile, from the OSG root directory, type : - - make - - Note, make should automatically detect IRIX and copy the - Make/makerules.irix and Make/makedefs.irix over the - default Make/makerules and Make/makedefs. If autodetection - does not work type 'make linux'. - - -Compiling under Windows : -------------------------- - - The Microsoft Visual C++ 6.0 workspace file is VisualStudio.dsw located - in the VisualStudio\ below the OSG this root directory. The OSG will - compile with the basic VisualC++6.0, but its recommended that you use - Service Pack 4 to fix MS compiler bugs which affect the OSG. - - To execute the viewer the file path for the .dll's and .exe, both compiled - into the OSG's bin directory, need to be setup, such as by adding the PATH - to your autoexec.bat, its also useful to add the OSGFILEPATH to your - autoexec.bat to help the location of datafiles. For example : - - SET OSGFILEPATH=D:\OpenSceneGraph-Data;D:\OpenSceneGraph-Data\Images - SET PATH=C:\WINDOWS;C:\WINDOWS\COMMAND;C:\Oglsdk\lib;D:\OpenSceneGraph-0.8\bin; - - -Running the viewer ------------------- - To run the viewer demo type (you made need to type rehash first under Unix) : - - sgv dumptruck.osg - sgv cow.osg - sgv e-s-bike.osg - sgv flight_park.fly - sgv lz.rgb - - Other run other demos type - - cube - - (Note: the file is picked up by checking the directories pointed to - by $OSGFILEPATH) - - -Plug-in dependancies --------------------- - - src/osgPlugins/pfb - - There is Peformer plugin in this distribution for converting from - Performer to OSG and from OSG to Performer. This plugin requires - Performer to be installed and therefore is not compiled by default. - If you have Performer (available under Linux and IRIX) then edit - src/osgPlugins/Make to compile under the plugin. Performer can be - downloaded from http://sgi.com - - For further information about the Performer plugin please read the - src/osgPlugin/pfb/READEME.txt. - - src/osgPlugins/png - - The png plugin depends upon the libpng and zlib (for compression) - libraries, if you don't already have it installed, you'll need to - download, compile and install it. - Project home pages are: - http://www.libpng.org/pub/png/libpng.html - http://www.info-zip.org/pub/infozip/zlib/ - - src/osgPlugins/gif - - The gif plugin depends upon the libungif library, if you don't already - have it installed, you'll need to download, compile and install it. - Project home page is: - http://prtr-13.ucsc.edu/~badger/software/libungif/ - Ftp download at : - ftp://prtr-13.ucsc.edu/pub/libungif/ - - - src/osgPlugins/jpeg - - The jpeg plugin depends upon the libjpeg library, if you don't already - have it installed, you'll need to download, compile and install it. - Project home page is: - http://www.ijg.org - - src/osgPlugins/tiff - - The tiff plugin depends upon the libtiff library, if you don't already - have it installed, you'll need to download, compile and install it. - Project home page is: - http://www.libtiff.org +For general documentation, distribution contents, and plugin +dependancies please read index.html in your prefered browser. +index.html also has links to INSTALL, making it easier for Windows +users which might find the lack of file extensions on text files awkward. +Robert Osfield. +robert@openscenegraph.com +May 2001. diff --git a/TODO b/TODO index 9739e2e26..29544b75e 100644 --- a/TODO +++ b/TODO @@ -31,15 +31,13 @@ o Core OSG Library . osg::Plane class. - Nodes - . create a base class to provide interface to objects which can render, - derive osg::GeoSet from this. . add osg::Sequence for basic animation. . add osg::Morph for interpolating between geometries. + . add osg::Engine. . add support for Multi-texturing into osg::GeoSet/osg::GeoState. - . add support for multi-pass rendering. + . add support for pixel/vertex shaders into osg::GeoSet/osg::GeoState. . utilise stl vectors for osg::GeoSets? - . improve osg::GeoState. - . add osg::State for mainting image of the OpenGL state. + . add handling of memory of osg::GeoSet's attributes. . add osg::Terrain node. . add osg::EarthSky class for rendering earth and sky backgrounds. . add proxy node for lazy loading of nodes, when needed. @@ -68,14 +66,10 @@ o Core OSG Library o Reader/writer plug-ins ======================= - .iv/.wrl Inventor/VRML ascii. - - .obj Alias wavefront's format. - .dxf Autocads ascii format. - - .3ds 3D Studio format. - .dem digital elevation map. - .d3d? MS's Direct 3D file formats if they have one.. - .bmp Windows Bitmap files. - - .gz Automatic unzipping of GNU zipped files. - - .zip Automatic unzipping of windows zipped files. - .Z Automatic unzipping of Unix Compress files. - .tar Automatic unpacking of directories and loading of contents. @@ -95,15 +89,20 @@ o Viewers & Application plug-ins o Under development ================= Sign up here if would like to take on a task :-) + - add osg::Billboard for trees etc. - - .pfb loader for Performer binary files. - full maths support in osg::Matrix class. - Netscape plug-in. - add osg::Channel/sgCamera class. - - .flt Open Flight format. + - .pfb loader for Performer binary files (functioning already.) + - .flt Open Flight format (functioning already.) + - .3ds 3D Studio format (functioning already.) - autoconf/configure support to aid portabilty to other unix's. - CVS support for when source is made fully public. - + - Mac port. + - tri stripping visitor. + - .obj Alias wavefront's format.(functioning already.) + - .lwo Light Waves's format.(functioning already.) o Work completed ============== @@ -139,3 +138,10 @@ o Work completed - add timing/timestamp class. - document how to get the OSG compiled and running under all platforms, Win32 being priority as it's the least obvious. + - .gz (as osgtgz and .tgz) Automatic unzipping of GNU zipped files. + - .zip Automatic unzipping of windows zipped files. + - add osg::State for mainting image of the OpenGL state. + - improve osg::GeoState -> improved version call osg::StateSet. + - create a base class to provide interface to objects which can render, + derive osg::GeoSet from this. + - add support for multi-pass rendering. diff --git a/VisualStudio/Demos/hangglide/hangglide.dsp b/VisualStudio/Demos/hangglide/hangglide.dsp new file mode 100755 index 000000000..aaca214f7 --- /dev/null +++ b/VisualStudio/Demos/hangglide/hangglide.dsp @@ -0,0 +1,147 @@ +# Microsoft Developer Studio Project File - Name="hangglide" - Package Owner=<4> +# Microsoft Developer Studio Generated Build File, Format Version 6.00 +# ** DO NOT EDIT ** + +# TARGTYPE "Win32 (x86) Console Application" 0x0103 + +CFG=hangglide - Win32 Debug +!MESSAGE This is not a valid makefile. To build this project using NMAKE, +!MESSAGE use the Export Makefile command and run +!MESSAGE +!MESSAGE NMAKE /f "hangglide.mak". +!MESSAGE +!MESSAGE You can specify a configuration when running NMAKE +!MESSAGE by defining the macro CFG on the command line. For example: +!MESSAGE +!MESSAGE NMAKE /f "hangglide.mak" CFG="hangglide - Win32 Debug" +!MESSAGE +!MESSAGE Possible choices for configuration are: +!MESSAGE +!MESSAGE "hangglide - Win32 Release" (based on "Win32 (x86) Console Application") +!MESSAGE "hangglide - Win32 Debug" (based on "Win32 (x86) Console Application") +!MESSAGE + +# Begin Project +# PROP AllowPerConfigDependencies 0 +# PROP Scc_ProjName "" +# PROP Scc_LocalPath "" +CPP=cl.exe +RSC=rc.exe + +!IF "$(CFG)" == "hangglide - Win32 Release" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 0 +# PROP BASE Output_Dir "Release" +# PROP BASE Intermediate_Dir "Release" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 0 +# PROP Output_Dir "Release" +# PROP Intermediate_Dir "Release" +# PROP Ignore_Export_Lib 0 +# PROP Target_Dir "" +# ADD BASE CPP /nologo /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /c +# ADD CPP /nologo /MD /W3 /GR /GX /O2 /I "../../../include" /D "WIN32" /D "NDEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /c +# ADD BASE RSC /l 0x809 /d "NDEBUG" +# ADD RSC /l 0x809 /d "NDEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LINK32=link.exe +# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /machine:I386 +# ADD LINK32 osgGLUT.lib osgUtil.lib osg.lib glut32.lib glu32.lib opengl32.lib wsock32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /machine:I386 /out:"../../../bin/hangglide.exe" /libpath:"../../../lib" + +!ELSEIF "$(CFG)" == "hangglide - Win32 Debug" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 1 +# PROP BASE Output_Dir "Debug" +# PROP BASE Intermediate_Dir "Debug" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 1 +# PROP Output_Dir "Debug" +# PROP Intermediate_Dir "Debug" +# PROP Ignore_Export_Lib 0 +# PROP Target_Dir "" +# ADD BASE CPP /nologo /W3 /Gm /GX /Zi /Od /D "WIN32" /D "_DEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /c +# ADD CPP /nologo /MDd /W3 /Gm /vd0 /GR /GX /ZI /Od /I "../../../include" /D "_CONSOLE" /D "_MBCS" /D "WIN32" /D "_DEBUG" /D "FL_DLL" /FR /YX /FD /c +# ADD BASE RSC /l 0x809 /d "_DEBUG" +# ADD RSC /l 0x809 /d "_DEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LINK32=link.exe +# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /debug /machine:I386 /pdbtype:sept +# ADD LINK32 osgGLUTd.lib osgUtild.lib osgd.lib glut32.lib glu32.lib opengl32.lib wsock32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /debug /machine:I386 /nodefaultlib:"libcmt" /out:"../../../bin/hangglided.exe" /pdbtype:sept /libpath:"../../../lib" +# SUBTRACT LINK32 /incremental:no + +!ENDIF + +# Begin Target + +# Name "hangglide - Win32 Release" +# Name "hangglide - Win32 Debug" +# Begin Group "Source Files" + +# PROP Default_Filter "cpp;c;cxx;rc;def;r;odl;idl;hpj;bat" +# Begin Source File + +SOURCE=..\..\..\Src\Demos\hangglide\Base.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\Demos\hangglide\GliderManipulator.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\Demos\hangglide\hangglide.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\Demos\hangglide\Hat.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\Demos\hangglide\ReaderWriterFLY.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\Demos\hangglide\Sky.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\Demos\hangglide\Tank.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\Demos\hangglide\Terrain.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\Demos\hangglide\Trees.cpp +# End Source File +# End Group +# Begin Group "Header Files" + +# PROP Default_Filter ";h;hpp;hxx;hm;inl" +# Begin Source File + +SOURCE=..\..\..\Src\Demos\hangglide\GliderManipulator.h +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\Demos\hangglide\Hat.h +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\Demos\hangglide\terrain_data.h +# End Source File +# End Group +# Begin Group "Resource Files" + +# PROP Default_Filter "" +# End Group +# End Target +# End Project diff --git a/VisualStudio/Demos/osgconv/osgconv.dsp b/VisualStudio/Demos/osgconv/osgconv.dsp new file mode 100755 index 000000000..010b225bb --- /dev/null +++ b/VisualStudio/Demos/osgconv/osgconv.dsp @@ -0,0 +1,95 @@ +# Microsoft Developer Studio Project File - Name="osgconv" - Package Owner=<4> +# Microsoft Developer Studio Generated Build File, Format Version 6.00 +# ** DO NOT EDIT ** + +# TARGTYPE "Win32 (x86) Console Application" 0x0103 + +CFG=osgconv - Win32 Debug +!MESSAGE This is not a valid makefile. To build this project using NMAKE, +!MESSAGE use the Export Makefile command and run +!MESSAGE +!MESSAGE NMAKE /f "osgconv.mak". +!MESSAGE +!MESSAGE You can specify a configuration when running NMAKE +!MESSAGE by defining the macro CFG on the command line. For example: +!MESSAGE +!MESSAGE NMAKE /f "osgconv.mak" CFG="osgconv - Win32 Debug" +!MESSAGE +!MESSAGE Possible choices for configuration are: +!MESSAGE +!MESSAGE "osgconv - Win32 Release" (based on "Win32 (x86) Console Application") +!MESSAGE "osgconv - Win32 Debug" (based on "Win32 (x86) Console Application") +!MESSAGE + +# Begin Project +# PROP AllowPerConfigDependencies 0 +# PROP Scc_ProjName "" +# PROP Scc_LocalPath "" +CPP=cl.exe +RSC=rc.exe + +!IF "$(CFG)" == "osgconv - Win32 Release" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 0 +# PROP BASE Output_Dir "Release" +# PROP BASE Intermediate_Dir "Release" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 0 +# PROP Output_Dir "Release" +# PROP Intermediate_Dir "Release" +# PROP Ignore_Export_Lib 0 +# PROP Target_Dir "" +# ADD BASE CPP /nologo /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /c +# ADD CPP /nologo /MD /W3 /GR /GX /O2 /I "../../../include" /D "WIN32" /D "NDEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /c +# ADD BASE RSC /l 0x809 /d "NDEBUG" +# ADD RSC /l 0x809 /d "NDEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LINK32=link.exe +# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /machine:I386 +# ADD LINK32 osgGLUT.lib osgUtil.lib osg.lib glut32.lib glu32.lib opengl32.lib wsock32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /machine:I386 /out:"../../../bin/osgconv.exe" /libpath:"../../../lib" + +!ELSEIF "$(CFG)" == "osgconv - Win32 Debug" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 1 +# PROP BASE Output_Dir "Debug" +# PROP BASE Intermediate_Dir "Debug" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 1 +# PROP Output_Dir "Debug" +# PROP Intermediate_Dir "Debug" +# PROP Ignore_Export_Lib 0 +# PROP Target_Dir "" +# ADD BASE CPP /nologo /W3 /Gm /GX /Zi /Od /D "WIN32" /D "_DEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /c +# ADD CPP /nologo /MDd /W3 /Gm /vd0 /GR /GX /ZI /Od /I "../../../include" /D "_CONSOLE" /D "_MBCS" /D "WIN32" /D "_DEBUG" /D "FL_DLL" /FR /YX /FD /c +# ADD BASE RSC /l 0x809 /d "_DEBUG" +# ADD RSC /l 0x809 /d "_DEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LINK32=link.exe +# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /debug /machine:I386 /pdbtype:sept +# ADD LINK32 osgGLUTd.lib osgUtild.lib osgd.lib glut32.lib glu32.lib opengl32.lib wsock32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /debug /machine:I386 /nodefaultlib:"libcmt" /out:"../../../bin/osgconvd.exe" /pdbtype:sept /libpath:"../../../lib" +# SUBTRACT LINK32 /incremental:no + +!ENDIF + +# Begin Target + +# Name "osgconv - Win32 Release" +# Name "osgconv - Win32 Debug" +# Begin Source File + +SOURCE=..\..\..\src\Demos\osgconv\osgconv.cpp +# End Source File +# End Target +# Begin Group "Resource Files" + +# PROP Default_Filter "ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe" +# End Group +# End Project diff --git a/VisualStudio/Demos/osgcube/osgcube.dsp b/VisualStudio/Demos/osgcube/osgcube.dsp new file mode 100755 index 000000000..b2ce81625 --- /dev/null +++ b/VisualStudio/Demos/osgcube/osgcube.dsp @@ -0,0 +1,95 @@ +# Microsoft Developer Studio Project File - Name="osgcube" - Package Owner=<4> +# Microsoft Developer Studio Generated Build File, Format Version 6.00 +# ** DO NOT EDIT ** + +# TARGTYPE "Win32 (x86) Console Application" 0x0103 + +CFG=osgcube - Win32 Debug +!MESSAGE This is not a valid makefile. To build this project using NMAKE, +!MESSAGE use the Export Makefile command and run +!MESSAGE +!MESSAGE NMAKE /f "osgcube.mak". +!MESSAGE +!MESSAGE You can specify a configuration when running NMAKE +!MESSAGE by defining the macro CFG on the command line. For example: +!MESSAGE +!MESSAGE NMAKE /f "osgcube.mak" CFG="osgcube - Win32 Debug" +!MESSAGE +!MESSAGE Possible choices for configuration are: +!MESSAGE +!MESSAGE "osgcube - Win32 Release" (based on "Win32 (x86) Console Application") +!MESSAGE "osgcube - Win32 Debug" (based on "Win32 (x86) Console Application") +!MESSAGE + +# Begin Project +# PROP AllowPerConfigDependencies 0 +# PROP Scc_ProjName "" +# PROP Scc_LocalPath "" +CPP=cl.exe +RSC=rc.exe + +!IF "$(CFG)" == "osgcube - Win32 Release" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 0 +# PROP BASE Output_Dir "Release" +# PROP BASE Intermediate_Dir "Release" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 0 +# PROP Output_Dir "Release" +# PROP Intermediate_Dir "Release" +# PROP Ignore_Export_Lib 0 +# PROP Target_Dir "" +# ADD BASE CPP /nologo /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /c +# ADD CPP /nologo /MD /W3 /GR /GX /O2 /I "../../../include" /D "WIN32" /D "NDEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /c +# ADD BASE RSC /l 0x809 /d "NDEBUG" +# ADD RSC /l 0x809 /d "NDEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LINK32=link.exe +# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /machine:I386 +# ADD LINK32 osgGLUT.lib osgUtil.lib osg.lib glut32.lib glu32.lib opengl32.lib wsock32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /machine:I386 /out:"../../../bin/osgcube.exe" /libpath:"../../../lib" + +!ELSEIF "$(CFG)" == "osgcube - Win32 Debug" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 1 +# PROP BASE Output_Dir "Debug" +# PROP BASE Intermediate_Dir "Debug" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 1 +# PROP Output_Dir "Debug" +# PROP Intermediate_Dir "Debug" +# PROP Ignore_Export_Lib 0 +# PROP Target_Dir "" +# ADD BASE CPP /nologo /W3 /Gm /GX /Zi /Od /D "WIN32" /D "_DEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /c +# ADD CPP /nologo /MDd /W3 /Gm /vd0 /GR /GX /ZI /Od /I "../../../include" /D "_CONSOLE" /D "_MBCS" /D "WIN32" /D "_DEBUG" /D "FL_DLL" /FR /YX /FD /c +# ADD BASE RSC /l 0x809 /d "_DEBUG" +# ADD RSC /l 0x809 /d "_DEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LINK32=link.exe +# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /debug /machine:I386 /pdbtype:sept +# ADD LINK32 osgGLUTd.lib osgUtild.lib osgd.lib glut32.lib glu32.lib opengl32.lib wsock32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /debug /machine:I386 /nodefaultlib:"libcmt" /out:"../../../bin/osgcubed.exe" /pdbtype:sept /libpath:"../../../lib" +# SUBTRACT LINK32 /incremental:no + +!ENDIF + +# Begin Target + +# Name "osgcube - Win32 Release" +# Name "osgcube - Win32 Debug" +# Begin Source File + +SOURCE=..\..\..\src\Demos\osgcube\osgcube.cpp +# End Source File +# End Target +# Begin Group "Resource Files" + +# PROP Default_Filter "ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe" +# End Group +# End Project diff --git a/VisualStudio/Demos/osgimpostor/osgimpostor.dsp b/VisualStudio/Demos/osgimpostor/osgimpostor.dsp new file mode 100755 index 000000000..187c78ac0 --- /dev/null +++ b/VisualStudio/Demos/osgimpostor/osgimpostor.dsp @@ -0,0 +1,95 @@ +# Microsoft Developer Studio Project File - Name="osgimpostor" - Package Owner=<4> +# Microsoft Developer Studio Generated Build File, Format Version 6.00 +# ** DO NOT EDIT ** + +# TARGTYPE "Win32 (x86) Console Application" 0x0103 + +CFG=osgimpostor - Win32 Debug +!MESSAGE This is not a valid makefile. To build this project using NMAKE, +!MESSAGE use the Export Makefile command and run +!MESSAGE +!MESSAGE NMAKE /f "osgimpostor.mak". +!MESSAGE +!MESSAGE You can specify a configuration when running NMAKE +!MESSAGE by defining the macro CFG on the command line. For example: +!MESSAGE +!MESSAGE NMAKE /f "osgimpostor.mak" CFG="osgimpostor - Win32 Debug" +!MESSAGE +!MESSAGE Possible choices for configuration are: +!MESSAGE +!MESSAGE "osgimpostor - Win32 Release" (based on "Win32 (x86) Console Application") +!MESSAGE "osgimpostor - Win32 Debug" (based on "Win32 (x86) Console Application") +!MESSAGE + +# Begin Project +# PROP AllowPerConfigDependencies 0 +# PROP Scc_ProjName "" +# PROP Scc_LocalPath "" +CPP=cl.exe +RSC=rc.exe + +!IF "$(CFG)" == "osgimpostor - Win32 Release" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 0 +# PROP BASE Output_Dir "Release" +# PROP BASE Intermediate_Dir "Release" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 0 +# PROP Output_Dir "Release" +# PROP Intermediate_Dir "Release" +# PROP Ignore_Export_Lib 0 +# PROP Target_Dir "" +# ADD BASE CPP /nologo /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /c +# ADD CPP /nologo /MD /W3 /GR /GX /O2 /I "../../../include" /D "WIN32" /D "NDEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /c +# ADD BASE RSC /l 0x809 /d "NDEBUG" +# ADD RSC /l 0x809 /d "NDEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LINK32=link.exe +# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /machine:I386 +# ADD LINK32 osgGLUT.lib osgUtil.lib osg.lib glut32.lib glu32.lib opengl32.lib wsock32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /machine:I386 /out:"../../../bin/osgimpostor.exe" /libpath:"../../../lib" + +!ELSEIF "$(CFG)" == "osgimpostor - Win32 Debug" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 1 +# PROP BASE Output_Dir "Debug" +# PROP BASE Intermediate_Dir "Debug" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 1 +# PROP Output_Dir "Debug" +# PROP Intermediate_Dir "Debug" +# PROP Ignore_Export_Lib 0 +# PROP Target_Dir "" +# ADD BASE CPP /nologo /W3 /Gm /GX /Zi /Od /D "WIN32" /D "_DEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /c +# ADD CPP /nologo /MDd /W3 /Gm /vd0 /GR /GX /ZI /Od /I "../../../include" /D "_CONSOLE" /D "_MBCS" /D "WIN32" /D "_DEBUG" /D "FL_DLL" /FR /YX /FD /c +# ADD BASE RSC /l 0x809 /d "_DEBUG" +# ADD RSC /l 0x809 /d "_DEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LINK32=link.exe +# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /debug /machine:I386 /pdbtype:sept +# ADD LINK32 osgGLUTd.lib osgUtild.lib osgd.lib glut32.lib glu32.lib opengl32.lib wsock32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /debug /machine:I386 /nodefaultlib:"libcmt" /out:"../../../bin/osgimpostord.exe" /pdbtype:sept /libpath:"../../../lib" +# SUBTRACT LINK32 /incremental:no + +!ENDIF + +# Begin Target + +# Name "osgimpostor - Win32 Release" +# Name "osgimpostor - Win32 Debug" +# Begin Source File + +SOURCE=..\..\..\src\Demos\osgimpostor\osgimpostor.cpp +# End Source File +# End Target +# Begin Group "Resource Files" + +# PROP Default_Filter "ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe" +# End Group +# End Project diff --git a/VisualStudio/Demos/osgreflect/osgreflect.dsp b/VisualStudio/Demos/osgreflect/osgreflect.dsp new file mode 100755 index 000000000..f21e7061e --- /dev/null +++ b/VisualStudio/Demos/osgreflect/osgreflect.dsp @@ -0,0 +1,95 @@ +# Microsoft Developer Studio Project File - Name="osgreflect" - Package Owner=<4> +# Microsoft Developer Studio Generated Build File, Format Version 6.00 +# ** DO NOT EDIT ** + +# TARGTYPE "Win32 (x86) Console Application" 0x0103 + +CFG=osgreflect - Win32 Debug +!MESSAGE This is not a valid makefile. To build this project using NMAKE, +!MESSAGE use the Export Makefile command and run +!MESSAGE +!MESSAGE NMAKE /f "osgreflect.mak". +!MESSAGE +!MESSAGE You can specify a configuration when running NMAKE +!MESSAGE by defining the macro CFG on the command line. For example: +!MESSAGE +!MESSAGE NMAKE /f "osgreflect.mak" CFG="osgreflect - Win32 Debug" +!MESSAGE +!MESSAGE Possible choices for configuration are: +!MESSAGE +!MESSAGE "osgreflect - Win32 Release" (based on "Win32 (x86) Console Application") +!MESSAGE "osgreflect - Win32 Debug" (based on "Win32 (x86) Console Application") +!MESSAGE + +# Begin Project +# PROP AllowPerConfigDependencies 0 +# PROP Scc_ProjName "" +# PROP Scc_LocalPath "" +CPP=cl.exe +RSC=rc.exe + +!IF "$(CFG)" == "osgreflect - Win32 Release" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 0 +# PROP BASE Output_Dir "Release" +# PROP BASE Intermediate_Dir "Release" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 0 +# PROP Output_Dir "Release" +# PROP Intermediate_Dir "Release" +# PROP Ignore_Export_Lib 0 +# PROP Target_Dir "" +# ADD BASE CPP /nologo /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /c +# ADD CPP /nologo /MD /W3 /GR /GX /O2 /I "../../../include" /D "WIN32" /D "NDEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /c +# ADD BASE RSC /l 0x809 /d "NDEBUG" +# ADD RSC /l 0x809 /d "NDEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LINK32=link.exe +# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /machine:I386 +# ADD LINK32 osgGLUT.lib osgUtil.lib osg.lib glut32.lib glu32.lib opengl32.lib wsock32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /machine:I386 /out:"../../../bin/osgreflect.exe" /libpath:"../../../lib" + +!ELSEIF "$(CFG)" == "osgreflect - Win32 Debug" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 1 +# PROP BASE Output_Dir "Debug" +# PROP BASE Intermediate_Dir "Debug" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 1 +# PROP Output_Dir "Debug" +# PROP Intermediate_Dir "Debug" +# PROP Ignore_Export_Lib 0 +# PROP Target_Dir "" +# ADD BASE CPP /nologo /W3 /Gm /GX /Zi /Od /D "WIN32" /D "_DEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /c +# ADD CPP /nologo /MDd /W3 /Gm /vd0 /GR /GX /ZI /Od /I "../../../include" /D "_CONSOLE" /D "_MBCS" /D "WIN32" /D "_DEBUG" /D "FL_DLL" /FR /YX /FD /c +# ADD BASE RSC /l 0x809 /d "_DEBUG" +# ADD RSC /l 0x809 /d "_DEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LINK32=link.exe +# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /debug /machine:I386 /pdbtype:sept +# ADD LINK32 osgGLUTd.lib osgUtild.lib osgd.lib glut32.lib glu32.lib opengl32.lib wsock32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /debug /machine:I386 /nodefaultlib:"libcmt" /out:"../../../bin/osgreflectd.exe" /pdbtype:sept /libpath:"../../../lib" +# SUBTRACT LINK32 /incremental:no + +!ENDIF + +# Begin Target + +# Name "osgreflect - Win32 Release" +# Name "osgreflect - Win32 Debug" +# Begin Source File + +SOURCE=..\..\..\src\Demos\osgreflect\osgreflect.cpp +# End Source File +# End Target +# Begin Group "Resource Files" + +# PROP Default_Filter "ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe" +# End Group +# End Project diff --git a/VisualStudio/Demos/osgtexture/osgtexture.dsp b/VisualStudio/Demos/osgtexture/osgtexture.dsp new file mode 100755 index 000000000..247a91b5f --- /dev/null +++ b/VisualStudio/Demos/osgtexture/osgtexture.dsp @@ -0,0 +1,95 @@ +# Microsoft Developer Studio Project File - Name="osgtexture" - Package Owner=<4> +# Microsoft Developer Studio Generated Build File, Format Version 6.00 +# ** DO NOT EDIT ** + +# TARGTYPE "Win32 (x86) Console Application" 0x0103 + +CFG=osgtexture - Win32 Debug +!MESSAGE This is not a valid makefile. To build this project using NMAKE, +!MESSAGE use the Export Makefile command and run +!MESSAGE +!MESSAGE NMAKE /f "osgtexture.mak". +!MESSAGE +!MESSAGE You can specify a configuration when running NMAKE +!MESSAGE by defining the macro CFG on the command line. For example: +!MESSAGE +!MESSAGE NMAKE /f "osgtexture.mak" CFG="osgtexture - Win32 Debug" +!MESSAGE +!MESSAGE Possible choices for configuration are: +!MESSAGE +!MESSAGE "osgtexture - Win32 Release" (based on "Win32 (x86) Console Application") +!MESSAGE "osgtexture - Win32 Debug" (based on "Win32 (x86) Console Application") +!MESSAGE + +# Begin Project +# PROP AllowPerConfigDependencies 0 +# PROP Scc_ProjName "" +# PROP Scc_LocalPath "" +CPP=cl.exe +RSC=rc.exe + +!IF "$(CFG)" == "osgtexture - Win32 Release" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 0 +# PROP BASE Output_Dir "Release" +# PROP BASE Intermediate_Dir "Release" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 0 +# PROP Output_Dir "Release" +# PROP Intermediate_Dir "Release" +# PROP Ignore_Export_Lib 0 +# PROP Target_Dir "" +# ADD BASE CPP /nologo /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /c +# ADD CPP /nologo /MD /W3 /GR /GX /O2 /I "../../../include" /D "WIN32" /D "NDEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /c +# ADD BASE RSC /l 0x809 /d "NDEBUG" +# ADD RSC /l 0x809 /d "NDEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LINK32=link.exe +# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /machine:I386 +# ADD LINK32 osgGLUT.lib osgUtil.lib osg.lib glut32.lib glu32.lib opengl32.lib wsock32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /machine:I386 /out:"../../../bin/osgtexture.exe" /libpath:"../../../lib" + +!ELSEIF "$(CFG)" == "osgtexture - Win32 Debug" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 1 +# PROP BASE Output_Dir "Debug" +# PROP BASE Intermediate_Dir "Debug" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 1 +# PROP Output_Dir "Debug" +# PROP Intermediate_Dir "Debug" +# PROP Ignore_Export_Lib 0 +# PROP Target_Dir "" +# ADD BASE CPP /nologo /W3 /Gm /GX /Zi /Od /D "WIN32" /D "_DEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /c +# ADD CPP /nologo /MDd /W3 /Gm /vd0 /GR /GX /ZI /Od /I "../../../include" /D "_CONSOLE" /D "_MBCS" /D "WIN32" /D "_DEBUG" /D "FL_DLL" /FR /YX /FD /c +# ADD BASE RSC /l 0x809 /d "_DEBUG" +# ADD RSC /l 0x809 /d "_DEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LINK32=link.exe +# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /debug /machine:I386 /pdbtype:sept +# ADD LINK32 osgGLUTd.lib osgUtild.lib osgd.lib glut32.lib glu32.lib opengl32.lib wsock32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /debug /machine:I386 /nodefaultlib:"libcmt" /out:"../../../bin/osgtextured.exe" /pdbtype:sept /libpath:"../../../lib" +# SUBTRACT LINK32 /incremental:no + +!ENDIF + +# Begin Target + +# Name "osgtexture - Win32 Release" +# Name "osgtexture - Win32 Debug" +# Begin Source File + +SOURCE=..\..\..\src\Demos\osgtexture\osgtexture.cpp +# End Source File +# End Target +# Begin Group "Resource Files" + +# PROP Default_Filter "ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe" +# End Group +# End Project diff --git a/VisualStudio/Demos/osgviews/osgviews.dsp b/VisualStudio/Demos/osgviews/osgviews.dsp new file mode 100755 index 000000000..3be247a94 --- /dev/null +++ b/VisualStudio/Demos/osgviews/osgviews.dsp @@ -0,0 +1,95 @@ +# Microsoft Developer Studio Project File - Name="osgviews" - Package Owner=<4> +# Microsoft Developer Studio Generated Build File, Format Version 6.00 +# ** DO NOT EDIT ** + +# TARGTYPE "Win32 (x86) Console Application" 0x0103 + +CFG=osgviews - Win32 Debug +!MESSAGE This is not a valid makefile. To build this project using NMAKE, +!MESSAGE use the Export Makefile command and run +!MESSAGE +!MESSAGE NMAKE /f "osgviews.mak". +!MESSAGE +!MESSAGE You can specify a configuration when running NMAKE +!MESSAGE by defining the macro CFG on the command line. For example: +!MESSAGE +!MESSAGE NMAKE /f "osgviews.mak" CFG="osgviews - Win32 Debug" +!MESSAGE +!MESSAGE Possible choices for configuration are: +!MESSAGE +!MESSAGE "osgviews - Win32 Release" (based on "Win32 (x86) Console Application") +!MESSAGE "osgviews - Win32 Debug" (based on "Win32 (x86) Console Application") +!MESSAGE + +# Begin Project +# PROP AllowPerConfigDependencies 0 +# PROP Scc_ProjName "" +# PROP Scc_LocalPath "" +CPP=cl.exe +RSC=rc.exe + +!IF "$(CFG)" == "osgviews - Win32 Release" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 0 +# PROP BASE Output_Dir "Release" +# PROP BASE Intermediate_Dir "Release" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 0 +# PROP Output_Dir "Release" +# PROP Intermediate_Dir "Release" +# PROP Ignore_Export_Lib 0 +# PROP Target_Dir "" +# ADD BASE CPP /nologo /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /c +# ADD CPP /nologo /MD /W3 /GR /GX /O2 /I "../../../include" /D "WIN32" /D "NDEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /c +# ADD BASE RSC /l 0x809 /d "NDEBUG" +# ADD RSC /l 0x809 /d "NDEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LINK32=link.exe +# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /machine:I386 +# ADD LINK32 osgGLUT.lib osgUtil.lib osg.lib glut32.lib glu32.lib opengl32.lib wsock32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /machine:I386 /out:"../../../bin/osgviews.exe" /libpath:"../../../lib" + +!ELSEIF "$(CFG)" == "osgviews - Win32 Debug" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 1 +# PROP BASE Output_Dir "Debug" +# PROP BASE Intermediate_Dir "Debug" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 1 +# PROP Output_Dir "Debug" +# PROP Intermediate_Dir "Debug" +# PROP Ignore_Export_Lib 0 +# PROP Target_Dir "" +# ADD BASE CPP /nologo /W3 /Gm /GX /Zi /Od /D "WIN32" /D "_DEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /c +# ADD CPP /nologo /MDd /W3 /Gm /vd0 /GR /GX /ZI /Od /I "../../../include" /D "_CONSOLE" /D "_MBCS" /D "WIN32" /D "_DEBUG" /D "FL_DLL" /FR /YX /FD /c +# ADD BASE RSC /l 0x809 /d "_DEBUG" +# ADD RSC /l 0x809 /d "_DEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LINK32=link.exe +# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /debug /machine:I386 /pdbtype:sept +# ADD LINK32 osgGLUTd.lib osgUtild.lib osgd.lib glut32.lib glu32.lib opengl32.lib wsock32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:console /debug /machine:I386 /nodefaultlib:"libcmt" /out:"../../../bin/osgviewsd.exe" /pdbtype:sept /libpath:"../../../lib" +# SUBTRACT LINK32 /incremental:no + +!ENDIF + +# Begin Target + +# Name "osgviews - Win32 Release" +# Name "osgviews - Win32 Debug" +# Begin Source File + +SOURCE=..\..\..\src\Demos\osgviews\osgviews.cpp +# End Source File +# End Target +# Begin Group "Resource Files" + +# PROP Default_Filter "ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe" +# End Group +# End Project diff --git a/VisualStudio/Demos/sgv/sgv.dsp b/VisualStudio/Demos/sgv/sgv.dsp index a37982bc0..8704286c8 100755 --- a/VisualStudio/Demos/sgv/sgv.dsp +++ b/VisualStudio/Demos/sgv/sgv.dsp @@ -42,7 +42,7 @@ RSC=rc.exe # PROP Ignore_Export_Lib 0 # PROP Target_Dir "" # ADD BASE CPP /nologo /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /c -# ADD CPP /nologo /W3 /GR /GX /O2 /I "../../../include" /D "WIN32" /D "NDEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /c +# ADD CPP /nologo /MD /W3 /GR /GX /O2 /I "../../../include" /D "WIN32" /D "NDEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /c # ADD BASE RSC /l 0x809 /d "NDEBUG" # ADD RSC /l 0x809 /d "NDEBUG" BSC32=bscmake.exe @@ -66,7 +66,7 @@ LINK32=link.exe # PROP Ignore_Export_Lib 0 # PROP Target_Dir "" # ADD BASE CPP /nologo /W3 /Gm /GX /Zi /Od /D "WIN32" /D "_DEBUG" /D "_CONSOLE" /D "_MBCS" /YX /FD /c -# ADD CPP /nologo /W3 /Gm /vd0 /GR /GX /ZI /Od /I "../../../include" /D "_CONSOLE" /D "_MBCS" /D "WIN32" /D "_DEBUG" /D "FL_DLL" /FR /YX /FD /c +# ADD CPP /nologo /MDd /W3 /Gm /vd0 /GR /GX /ZI /Od /I "../../../include" /D "_CONSOLE" /D "_MBCS" /D "WIN32" /D "_DEBUG" /D "FL_DLL" /FR /YX /FD /c # ADD BASE RSC /l 0x809 /d "_DEBUG" # ADD RSC /l 0x809 /d "_DEBUG" BSC32=bscmake.exe @@ -87,10 +87,9 @@ LINK32=link.exe SOURCE=..\..\..\src\Demos\sgv\sgv.cpp # End Source File -# End Group +# End Target # Begin Group "Resource Files" # PROP Default_Filter "ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe" # End Group -# End Target # End Project diff --git a/VisualStudio/Demos/wxsgv/wxsgv.dsp b/VisualStudio/Demos/wxsgv/wxsgv.dsp new file mode 100644 index 000000000..d256a8e2e --- /dev/null +++ b/VisualStudio/Demos/wxsgv/wxsgv.dsp @@ -0,0 +1,147 @@ +# Microsoft Developer Studio Project File - Name="wxsgv" - Package Owner=<4> +# Microsoft Developer Studio Generated Build File, Format Version 6.00 +# ** DO NOT EDIT ** + +# TARGTYPE "Win32 (x86) Application" 0x0101 + +CFG=wxsgv - Win32 Debug +!MESSAGE This is not a valid makefile. To build this project using NMAKE, +!MESSAGE use the Export Makefile command and run +!MESSAGE +!MESSAGE NMAKE /f "wxsgv.mak". +!MESSAGE +!MESSAGE You can specify a configuration when running NMAKE +!MESSAGE by defining the macro CFG on the command line. For example: +!MESSAGE +!MESSAGE NMAKE /f "wxsgv.mak" CFG="wxsgv - Win32 Debug" +!MESSAGE +!MESSAGE Possible choices for configuration are: +!MESSAGE +!MESSAGE "wxsgv - Win32 Release" (based on "Win32 (x86) Application") +!MESSAGE "wxsgv - Win32 Debug" (based on "Win32 (x86) Application") +!MESSAGE + +# Begin Project +# PROP AllowPerConfigDependencies 0 +# PROP Scc_ProjName "" +# PROP Scc_LocalPath "" +CPP=cl.exe +MTL=midl.exe +RSC=rc.exe + +!IF "$(CFG)" == "wxsgv - Win32 Release" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 0 +# PROP BASE Output_Dir "Release" +# PROP BASE Intermediate_Dir "Release" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 0 +# PROP Output_Dir "Release" +# PROP Intermediate_Dir "Release" +# PROP Ignore_Export_Lib 0 +# PROP Target_Dir "" +# ADD BASE CPP /nologo /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /YX /FD /c +# ADD CPP /nologo /MD /W3 /GR /GX /O2 /I "\APIs\wx2\include" /D "NDEBUG" /D "WIN32" /D "_WINDOWS" /D "_MBCS" /D "__WINDOWS__" /D "__WXMSW__" /D "__WIN95__" /D "__WIN32__" /D WINVER=0x0400 /D "STRICT" /D WXUSINGDLL=1 /YX"wx/wxprec.h" /FD /c +# ADD BASE MTL /nologo /D "NDEBUG" /mktyplib203 /win32 +# ADD MTL /nologo /D "NDEBUG" /mktyplib203 /win32 +# ADD BASE RSC /l 0x409 /d "NDEBUG" +# ADD RSC /l 0x409 /d "NDEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LINK32=link.exe +# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:windows /machine:I386 +# ADD LINK32 wx22_7.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib opengl32.lib glu32.lib netcdf.lib libpng.lib zlib.lib /nologo /subsystem:windows /machine:I386 /nodefaultlib:"libc.lib" /libpath:"\APIs\libpng-1.0.8" /libpath:"\APIs\netcdf-3.5.0.win32bin\lib" + +!ELSEIF "$(CFG)" == "wxsgv - Win32 Debug" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 1 +# PROP BASE Output_Dir "Debug" +# PROP BASE Intermediate_Dir "Debug" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 1 +# PROP Output_Dir "Debug" +# PROP Intermediate_Dir "Debug" +# PROP Ignore_Export_Lib 0 +# PROP Target_Dir "" +# ADD BASE CPP /nologo /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /YX /FD /GZ /c +# ADD CPP /nologo /MDd /W3 /Gm /GR /GX /ZI /Od /I "\APIs\wx2\include" /D "_DEBUG" /D "WIN32" /D "_WINDOWS" /D "_MBCS" /D "__WINDOWS__" /D "__WXMSW__" /D "__WIN95__" /D "__WIN32__" /D WINVER=0x0400 /D "STRICT" /D WXUSINGDLL=1 /FR /YX"wx/wxprec.h" /FD /GZ /c +# ADD BASE MTL /nologo /D "_DEBUG" /mktyplib203 /win32 +# ADD MTL /nologo /D "_DEBUG" /mktyplib203 /win32 +# ADD BASE RSC /l 0x409 /d "_DEBUG" +# ADD RSC /l 0x409 /d "_DEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LINK32=link.exe +# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /subsystem:windows /debug /machine:I386 /pdbtype:sept +# ADD LINK32 wx22_7d.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib opengl32.lib glu32.lib netcdf.lib libpng.lib zlib.lib /nologo /subsystem:windows /debug /machine:I386 /nodefaultlib:"libc.lib" /nodefaultlib:"libcd.lib" /nodefaultlib:"libcmt.lib" /out:"../../../bin/wxsgv.exe" /pdbtype:sept /libpath:"\APIs\libpng-1.0.8" /libpath:"\APIs\netcdf-3.5.0.win32bin\lib" + +!ENDIF + +# Begin Target + +# Name "wxsgv - Win32 Release" +# Name "wxsgv - Win32 Debug" +# Begin Group "Source Files" + +# PROP Default_Filter "cpp;c;cxx;rc;def;r;odl;idl;hpj;bat" +# Begin Source File + +SOURCE=..\..\..\src\Demos\wxsgv\app.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\Demos\wxsgv\canvas.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\Demos\wxsgv\frame.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\Demos\wxsgv\SceneGraphDlg.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\Demos\wxsgv\wxsgv_wdr.cpp +# End Source File +# End Group +# Begin Group "Header Files" + +# PROP Default_Filter "h;hpp;hxx;hm;inl" +# Begin Source File + +SOURCE=..\..\..\src\Demos\wxsgv\app.h +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\Demos\wxsgv\canvas.h +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\Demos\wxsgv\frame.h +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\Demos\wxsgv\SceneGraphDlg.h +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\Demos\wxsgv\wxsgv_wdr.h +# End Source File +# End Group +# Begin Group "Resource Files" + +# PROP Default_Filter "ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe" +# Begin Source File + +SOURCE=..\..\..\src\Demos\wxsgv\wxsgv.rc +# End Source File +# End Group +# End Target +# End Project diff --git a/VisualStudio/VisualStudio.dsw b/VisualStudio/VisualStudio.dsw index 9fe86346d..97ab436bd 100644 --- a/VisualStudio/VisualStudio.dsw +++ b/VisualStudio/VisualStudio.dsw @@ -3,7 +3,7 @@ Microsoft Developer Studio Workspace File, Format Version 6.00 ############################################################################### -Project: "sgv"=".\Demos\sgv\sgv.dsp" - Package Owner=<4> +Project: "osg"=".\osg\osg.dsp" - Package Owner=<4> Package=<5> {{{ @@ -11,156 +11,6 @@ Package=<5> Package=<4> {{{ - Begin Project Dependency - Project_Dep_Name osg - End Project Dependency - Begin Project Dependency - Project_Dep_Name osgUtil - End Project Dependency - Begin Project Dependency - Project_Dep_Name osgGLUT - End Project Dependency -}}} - -############################################################################### - -Project: "cube"=".\Demos\cube\cube.dsp" - Package Owner=<4> - -Package=<5> -{{{ -}}} - -Package=<4> -{{{ - Begin Project Dependency - Project_Dep_Name osg - End Project Dependency - Begin Project Dependency - Project_Dep_Name osgUtil - End Project Dependency - Begin Project Dependency - Project_Dep_Name osgGLUT - End Project Dependency -}}} - -############################################################################### - -Project: "flt"=".\osgPlugins\flt\flt.dsp" - Package Owner=<4> - -Package=<5> -{{{ -}}} - -Package=<4> -{{{ - Begin Project Dependency - Project_Dep_Name osg - End Project Dependency -}}} - -############################################################################### - -Project: "fly"=".\osgPlugins\fly\fly.dsp" - Package Owner=<4> - -Package=<5> -{{{ -}}} - -Package=<4> -{{{ - Begin Project Dependency - Project_Dep_Name osg - End Project Dependency -}}} - -############################################################################### - -Project: "gif"=".\osgPlugins\gif\gif.dsp" - Package Owner=<4> - -Package=<5> -{{{ -}}} - -Package=<4> -{{{ - Begin Project Dependency - Project_Dep_Name osg - End Project Dependency -}}} - -############################################################################### - -Project: "jpeg"=".\osgPlugins\jpeg\jpeg.dsp" - Package Owner=<4> - -Package=<5> -{{{ -}}} - -Package=<4> -{{{ - Begin Project Dependency - Project_Dep_Name osg - End Project Dependency -}}} - -############################################################################### - -Project: "pic"=".\osgPlugins\pic\pic.dsp" - Package Owner=<4> - -Package=<5> -{{{ -}}} - -Package=<4> -{{{ - Begin Project Dependency - Project_Dep_Name osg - End Project Dependency -}}} - -############################################################################### - -Project: "png"=".\osgPlugins\png\png.dsp" - Package Owner=<4> - -Package=<5> -{{{ -}}} - -Package=<4> -{{{ - Begin Project Dependency - Project_Dep_Name osg - End Project Dependency -}}} - -############################################################################### - -Project: "tga"=".\osgPlugins\tga\tga.dsp" - Package Owner=<4> - -Package=<5> -{{{ -}}} - -Package=<4> -{{{ - Begin Project Dependency - Project_Dep_Name osg - End Project Dependency -}}} - -############################################################################### - -Project: "tiff"=".\osgPlugins\tiff\tiff.dsp" - Package Owner=<4> - -Package=<5> -{{{ -}}} - -Package=<4> -{{{ - Begin Project Dependency - Project_Dep_Name osg - End Project Dependency }}} ############################################################################### @@ -179,6 +29,9 @@ Package=<4> Begin Project Dependency Project_Dep_Name osgUtil End Project Dependency + Begin Project Dependency + Project_Dep_Name osgDB + End Project Dependency }}} ############################################################################### @@ -198,7 +51,7 @@ Package=<4> ############################################################################### -Project: "osg"=".\osg\osg.dsp" - Package Owner=<4> +Project: "osgDB"=".\osgDB\osgDB.dsp" - Package Owner=<4> Package=<5> {{{ @@ -206,6 +59,492 @@ Package=<5> Package=<4> {{{ + Begin Project Dependency + Project_Dep_Name osg + End Project Dependency +}}} + +############################################################################### + +Project: "osgconv"=".\Demos\osgconv\osgconv.dsp" - Package Owner=<4> + +Package=<5> +{{{ +}}} + +Package=<4> +{{{ + Begin Project Dependency + Project_Dep_Name osg + End Project Dependency + Begin Project Dependency + Project_Dep_Name osgUtil + End Project Dependency + Begin Project Dependency + Project_Dep_Name osgDB + End Project Dependency +}}} + +############################################################################### + +Project: "sgv"=".\Demos\sgv\sgv.dsp" - Package Owner=<4> + +Package=<5> +{{{ +}}} + +Package=<4> +{{{ + Begin Project Dependency + Project_Dep_Name osg + End Project Dependency + Begin Project Dependency + Project_Dep_Name osgUtil + End Project Dependency + Begin Project Dependency + Project_Dep_Name osgDB + End Project Dependency + Begin Project Dependency + Project_Dep_Name osgGLUT + End Project Dependency +}}} + +############################################################################### + +Project: "osgcube"=".\Demos\osgcube\osgcube.dsp" - Package Owner=<4> + +Package=<5> +{{{ +}}} + +Package=<4> +{{{ + Begin Project Dependency + Project_Dep_Name osg + End Project Dependency + Begin Project Dependency + Project_Dep_Name osgUtil + End Project Dependency + Begin Project Dependency + Project_Dep_Name osgDB + End Project Dependency + Begin Project Dependency + Project_Dep_Name osgGLUT + End Project Dependency +}}} + +############################################################################### + +Project: "osgimpostor"=".\Demos\osgimpostor\osgimpostor.dsp" - Package Owner=<4> + +Package=<5> +{{{ +}}} + +Package=<4> +{{{ + Begin Project Dependency + Project_Dep_Name osg + End Project Dependency + Begin Project Dependency + Project_Dep_Name osgUtil + End Project Dependency + Begin Project Dependency + Project_Dep_Name osgDB + End Project Dependency + Begin Project Dependency + Project_Dep_Name osgGLUT + End Project Dependency +}}} + +############################################################################### + +Project: "osgviews"=".\Demos\osgviews\osgviews.dsp" - Package Owner=<4> + +Package=<5> +{{{ +}}} + +Package=<4> +{{{ + Begin Project Dependency + Project_Dep_Name osg + End Project Dependency + Begin Project Dependency + Project_Dep_Name osgUtil + End Project Dependency + Begin Project Dependency + Project_Dep_Name osgDB + End Project Dependency + Begin Project Dependency + Project_Dep_Name osgGLUT + End Project Dependency +}}} + +############################################################################### + +Project: "osgreflect"=".\Demos\osgreflect\osgreflect.dsp" - Package Owner=<4> + +Package=<5> +{{{ +}}} + +Package=<4> +{{{ + Begin Project Dependency + Project_Dep_Name osg + End Project Dependency + Begin Project Dependency + Project_Dep_Name osgUtil + End Project Dependency + Begin Project Dependency + Project_Dep_Name osgDB + End Project Dependency + Begin Project Dependency + Project_Dep_Name osgGLUT + End Project Dependency +}}} + +############################################################################### + +Project: "osgtexture"=".\Demos\osgtexture\osgtexture.dsp" - Package Owner=<4> + +Package=<5> +{{{ +}}} + +Package=<4> +{{{ + Begin Project Dependency + Project_Dep_Name osg + End Project Dependency + Begin Project Dependency + Project_Dep_Name osgUtil + End Project Dependency + Begin Project Dependency + Project_Dep_Name osgDB + End Project Dependency + Begin Project Dependency + Project_Dep_Name osgGLUT + End Project Dependency +}}} + +############################################################################### + +Project: "hangglide"=".\Demos\hangglide\hangglide.dsp" - Package Owner=<4> + +Package=<5> +{{{ +}}} + +Package=<4> +{{{ + Begin Project Dependency + Project_Dep_Name osg + End Project Dependency + Begin Project Dependency + Project_Dep_Name osgUtil + End Project Dependency + Begin Project Dependency + Project_Dep_Name osgDB + End Project Dependency + Begin Project Dependency + Project_Dep_Name osgGLUT + End Project Dependency +}}} + +############################################################################### + +Project: "3ds"=".\osgPlugins\lib3ds\lib3ds.dsp" - Package Owner=<4> + +Package=<5> +{{{ +}}} + +Package=<4> +{{{ + Begin Project Dependency + Project_Dep_Name osg + End Project Dependency + Begin Project Dependency + Project_Dep_Name osgDB + End Project Dependency +}}} + +############################################################################### + +Project: "flt"=".\osgPlugins\flt\flt.dsp" - Package Owner=<4> + +Package=<5> +{{{ +}}} + +Package=<4> +{{{ + Begin Project Dependency + Project_Dep_Name osg + End Project Dependency + Begin Project Dependency + Project_Dep_Name osgDB + End Project Dependency +}}} + +############################################################################### + +Project: "lwo"=".\osgPlugins\lwo\lwo.dsp" - Package Owner=<4> + +Package=<5> +{{{ +}}} + +Package=<4> +{{{ + Begin Project Dependency + Project_Dep_Name osg + End Project Dependency + Begin Project Dependency + Project_Dep_Name osgDB + End Project Dependency + Begin Project Dependency + Project_Dep_Name osgUtil + End Project Dependency +}}} + +############################################################################### + +Project: "dw"=".\osgPlugins\dw\dw.dsp" - Package Owner=<4> + +Package=<5> +{{{ +}}} + +Package=<4> +{{{ + Begin Project Dependency + Project_Dep_Name osg + End Project Dependency + Begin Project Dependency + Project_Dep_Name osgDB + End Project Dependency + Begin Project Dependency + Project_Dep_Name osgUtil + End Project Dependency +}}} + +############################################################################### + +Project: "obj"=".\osgPlugins\obj\obj.dsp" - Package Owner=<4> + +Package=<5> +{{{ +}}} + +Package=<4> +{{{ + Begin Project Dependency + Project_Dep_Name osg + End Project Dependency + Begin Project Dependency + Project_Dep_Name osgDB + End Project Dependency +}}} + +############################################################################### + +Project: "gif"=".\osgPlugins\gif\gif.dsp" - Package Owner=<4> + +Package=<5> +{{{ +}}} + +Package=<4> +{{{ + Begin Project Dependency + Project_Dep_Name osg + End Project Dependency + Begin Project Dependency + Project_Dep_Name osgDB + End Project Dependency +}}} + +############################################################################### + +Project: "jpeg"=".\osgPlugins\jpeg\jpeg.dsp" - Package Owner=<4> + +Package=<5> +{{{ +}}} + +Package=<4> +{{{ + Begin Project Dependency + Project_Dep_Name osg + End Project Dependency + Begin Project Dependency + Project_Dep_Name osgDB + End Project Dependency +}}} + +############################################################################### + +Project: "osgtgz"=".\osgPlugins\osgtgz\osgtgz.dsp" - Package Owner=<4> + +Package=<5> +{{{ +}}} + +Package=<4> +{{{ + Begin Project Dependency + Project_Dep_Name osg + End Project Dependency + Begin Project Dependency + Project_Dep_Name osgDB + End Project Dependency +}}} + +############################################################################### + +Project: "pic"=".\osgPlugins\pic\pic.dsp" - Package Owner=<4> + +Package=<5> +{{{ +}}} + +Package=<4> +{{{ + Begin Project Dependency + Project_Dep_Name osg + End Project Dependency + Begin Project Dependency + Project_Dep_Name osgDB + End Project Dependency +}}} + +############################################################################### + +Project: "png"=".\osgPlugins\png\png.dsp" - Package Owner=<4> + +Package=<5> +{{{ +}}} + +Package=<4> +{{{ + Begin Project Dependency + Project_Dep_Name osg + End Project Dependency + Begin Project Dependency + Project_Dep_Name osgDB + End Project Dependency +}}} + +############################################################################### + +Project: "tga"=".\osgPlugins\tga\tga.dsp" - Package Owner=<4> + +Package=<5> +{{{ +}}} + +Package=<4> +{{{ + Begin Project Dependency + Project_Dep_Name osg + End Project Dependency + Begin Project Dependency + Project_Dep_Name osgDB + End Project Dependency +}}} + +############################################################################### + +Project: "dot_osg"=".\osgPlugins\osg\dot_osg.dsp" - Package Owner=<4> + +Package=<5> +{{{ +}}} + +Package=<4> +{{{ + Begin Project Dependency + Project_Dep_Name osg + End Project Dependency + Begin Project Dependency + Project_Dep_Name osgDB + End Project Dependency +}}} + +############################################################################### + +Project: "rgb"=".\osgPlugins\rgb\rgb.dsp" - Package Owner=<4> + +Package=<5> +{{{ +}}} + +Package=<4> +{{{ + Begin Project Dependency + Project_Dep_Name osg + End Project Dependency + Begin Project Dependency + Project_Dep_Name osgDB + End Project Dependency +}}} + +############################################################################### + +Project: "tgz"=".\osgPlugins\tgz\tgz.dsp" - Package Owner=<4> + +Package=<5> +{{{ +}}} + +Package=<4> +{{{ + Begin Project Dependency + Project_Dep_Name osg + End Project Dependency + Begin Project Dependency + Project_Dep_Name osgDB + End Project Dependency +}}} + +############################################################################### + +Project: "tiff"=".\osgPlugins\tiff\tiff.dsp" - Package Owner=<4> + +Package=<5> +{{{ +}}} + +Package=<4> +{{{ + Begin Project Dependency + Project_Dep_Name osg + End Project Dependency + Begin Project Dependency + Project_Dep_Name osgDB + End Project Dependency +}}} + +############################################################################### + +Project: "zip"=".\osgPlugins\zip\zip.dsp" - Package Owner=<4> + +Package=<5> +{{{ +}}} + +Package=<4> +{{{ + Begin Project Dependency + Project_Dep_Name osg + End Project Dependency + Begin Project Dependency + Project_Dep_Name osgDB + End Project Dependency }}} ############################################################################### diff --git a/VisualStudio/osg/osg.dsp b/VisualStudio/osg/osg.dsp index 3346dd450..924237ccd 100755 --- a/VisualStudio/osg/osg.dsp +++ b/VisualStudio/osg/osg.dsp @@ -43,14 +43,14 @@ RSC=rc.exe # PROP Ignore_Export_Lib 0 # PROP Target_Dir "" # ADD BASE CPP /nologo /MT /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "LIBSCENEGRAPH_EXPORTS" /YX /FD /c -# ADD CPP /nologo /MT /W3 /GR /GX /O2 /I "../../include" /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "SG_LIBRARY" /YX /FD /c +# ADD CPP /nologo /MD /W3 /GR /GX /O2 /I "../../include" /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "SG_LIBRARY" /YX /FD /c # ADD BASE MTL /nologo /D "NDEBUG" /mktyplib203 /win32 # ADD MTL /nologo /D "NDEBUG" /mktyplib203 /win32 # ADD BASE RSC /l 0x409 /d "NDEBUG" # ADD RSC /l 0x409 /d "NDEBUG" BSC32=bscmake.exe # ADD BASE BSC32 /nologo -# ADD BSC32 /nologo /o"../../lib/osg.bsc" +# ADD BSC32 /nologo LINK32=link.exe # ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 # ADD LINK32 opengl32.lib glu32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /pdb:"../../bin/osg.pdb" /machine:I386 /out:"../../bin/osg.dll" @@ -70,14 +70,14 @@ LINK32=link.exe # PROP Ignore_Export_Lib 0 # PROP Target_Dir "" # ADD BASE CPP /nologo /MTd /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "LIBSCENEGRAPH_EXPORTS" /YX /FD /GZ /c -# ADD CPP /nologo /MTd /W3 /Gm /vmg /vd0 /GR /GX /ZI /Od /I "../../include" /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "SG_LIBRARY" /YX /FD /GZ /c +# ADD CPP /nologo /MDd /W3 /Gm /vmg /vd0 /GR /GX /ZI /Od /I "../../include" /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "SG_LIBRARY" /YX /FD /GZ /c # ADD BASE MTL /nologo /D "_DEBUG" /mktyplib203 /win32 # ADD MTL /nologo /D "_DEBUG" /mktyplib203 /win32 # ADD BASE RSC /l 0x409 /d "_DEBUG" # ADD RSC /l 0x409 /d "_DEBUG" BSC32=bscmake.exe # ADD BASE BSC32 /nologo -# ADD BSC32 /nologo /o"../../lib/osg.bsc" +# ADD BSC32 /nologo LINK32=link.exe # ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /pdbtype:sept # ADD LINK32 opengl32.lib glu32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /pdb:"../../bin/osgd.pdb" /debug /machine:I386 /out:"../../bin/osgd.dll" /pdbtype:sept @@ -94,139 +94,135 @@ LINK32=link.exe # PROP Default_Filter "cpp;c;cxx;rc;def;r;odl;idl;hpj;bat" # Begin Source File -SOURCE=..\..\Src\Osg\AlphaFunc.cpp +SOURCE=..\..\src\osg\AlphaFunc.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\Billboard.cpp +SOURCE=..\..\src\osg\Billboard.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\BoundingBox.cpp +SOURCE=..\..\src\osg\BoundingBox.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\BoundingSphere.cpp +SOURCE=..\..\src\osg\BoundingSphere.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\Camera.cpp +SOURCE=..\..\src\osg\Camera.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\CullFace.cpp +SOURCE=..\..\src\osg\ClipPlane.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\DCS.cpp +SOURCE=..\..\src\osg\ColorMask.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\DynamicLibrary.cpp +SOURCE=..\..\src\osg\CullFace.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\ExtensionSupported.cpp +SOURCE=..\..\src\osg\Depth.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\Field.cpp +SOURCE=..\..\src\osg\Drawable.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\FieldReader.cpp +SOURCE=..\..\src\osg\Fog.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\FieldReaderIterator.cpp +SOURCE=..\..\Src\Osg\FrontFace.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\FileNameUtils.cpp +SOURCE=..\..\src\osg\Geode.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\Fog.cpp +SOURCE=..\..\src\osg\GeoSet.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\Geode.cpp +SOURCE=..\..\src\osg\GeoSet_ogl.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\GeoSet.cpp +SOURCE=..\..\src\osg\StateSet.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\GeoSet_ogl.cpp +SOURCE=..\..\src\osg\GLExtensions.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\GeoState.cpp +SOURCE=..\..\src\osg\Group.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\Group.cpp +SOURCE=..\..\src\osg\Image.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\Image.cpp +SOURCE=..\..\src\osg\Impostor.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\Input.cpp +SOURCE=..\..\src\osg\ImpostorSprite.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\Light.cpp +SOURCE=..\..\src\osg\Light.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\LightSource.cpp +SOURCE=..\..\src\osg\LightSource.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\Lighting.cpp +SOURCE=..\..\src\osg\LineSegment.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\LOD.cpp +SOURCE=..\..\src\osg\LOD.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\Material.cpp +SOURCE=..\..\src\osg\Material.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\Matrix.cpp +SOURCE=..\..\src\osg\Matrix.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\Node.cpp +SOURCE=..\..\src\osg\Node.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\NodeVisitor.cpp +SOURCE=..\..\src\osg\NodeVisitor.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\Notify.cpp +SOURCE=..\..\src\osg\Notify.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\Object.cpp +SOURCE=..\..\src\osg\Object.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\OSG.cpp +SOURCE=..\..\src\osg\Point.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\Output.cpp -# End Source File -# Begin Source File - -SOURCE=..\..\Src\Osg\Point.cpp +SOURCE=..\..\src\osg\PolygonMode.cpp # End Source File # Begin Source File @@ -234,63 +230,51 @@ SOURCE=..\..\src\osg\PolygonOffset.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\Quat.cpp +SOURCE=..\..\src\osg\Quat.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\ReaderWriterOSG.cpp +SOURCE=..\..\src\osg\State.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\ReaderWriterRGB.cpp +SOURCE=..\..\src\osg\Stencil.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\Registry.cpp +SOURCE=..\..\src\osg\Switch.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\Scene.cpp +SOURCE=..\..\src\osg\TexEnv.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\Seg.cpp +SOURCE=..\..\src\osg\TexGen.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\Sequence.cpp +SOURCE=..\..\src\osg\TexMat.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\Switch.cpp +SOURCE=..\..\src\osg\Texture.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\TexEnv.cpp +SOURCE=..\..\src\osg\Timer.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\TexGen.cpp +SOURCE=..\..\src\osg\Transform.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\TexMat.cpp +SOURCE=..\..\src\osg\Transparency.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\Osg\Texture.cpp -# End Source File -# Begin Source File - -SOURCE=..\..\Src\Osg\Timer.cpp -# End Source File -# Begin Source File - -SOURCE=..\..\Src\Osg\Version.cpp -# End Source File -# Begin Source File - -SOURCE=..\..\Src\Osg\Transparency.cpp +SOURCE=..\..\src\osg\Version.cpp # End Source File # End Group # Begin Group "Header Files" @@ -318,15 +302,27 @@ SOURCE=..\..\Include\Osg\Camera # End Source File # Begin Source File +SOURCE=..\..\Include\Osg\ClipPlane +# End Source File +# Begin Source File + +SOURCE=..\..\Include\Osg\ClippingVolume +# End Source File +# Begin Source File + +SOURCE=..\..\Include\Osg\ColorMask +# End Source File +# Begin Source File + SOURCE=..\..\Include\Osg\CullFace # End Source File # Begin Source File -SOURCE=..\..\Include\Osg\Dcs +SOURCE=..\..\Include\Osg\Depth # End Source File # Begin Source File -SOURCE=..\..\Include\Osg\DynamicLibrary +SOURCE=..\..\Include\Osg\Drawable # End Source File # Begin Source File @@ -334,30 +330,14 @@ SOURCE=..\..\Include\Osg\Export # End Source File # Begin Source File -SOURCE=..\..\Include\Osg\ExtensionSupported -# End Source File -# Begin Source File - -SOURCE=..\..\Include\Osg\Field -# End Source File -# Begin Source File - -SOURCE=..\..\Include\Osg\FieldReader -# End Source File -# Begin Source File - -SOURCE=..\..\Include\Osg\FieldReaderIterator -# End Source File -# Begin Source File - -SOURCE=..\..\Include\Osg\FileNameUtils -# End Source File -# Begin Source File - SOURCE=..\..\Include\Osg\Fog # End Source File # Begin Source File +SOURCE=..\..\Include\Osg\FrontFace +# End Source File +# Begin Source File + SOURCE=..\..\Include\Osg\Geode # End Source File # Begin Source File @@ -366,7 +346,11 @@ SOURCE=..\..\Include\Osg\GeoSet # End Source File # Begin Source File -SOURCE=..\..\Include\Osg\GeoState +SOURCE=..\..\Include\Osg\StateSet +# End Source File +# Begin Source File + +SOURCE=..\..\Include\Osg\Stencil # End Source File # Begin Source File @@ -374,6 +358,10 @@ SOURCE=..\..\Include\Osg\Gl # End Source File # Begin Source File +SOURCE=..\..\Include\Osg\GLExtensions +# End Source File +# Begin Source File + SOURCE=..\..\Include\Osg\Group # End Source File # Begin Source File @@ -382,6 +370,14 @@ SOURCE=..\..\Include\Osg\Image # End Source File # Begin Source File +SOURCE=..\..\Include\Osg\Impostor +# End Source File +# Begin Source File + +SOURCE=..\..\Include\Osg\ImpostorSprite +# End Source File +# Begin Source File + SOURCE=..\..\Include\Osg\Input # End Source File # Begin Source File @@ -394,7 +390,7 @@ SOURCE=..\..\Include\Osg\LightSource # End Source File # Begin Source File -SOURCE=..\..\Include\Osg\Lighting +SOURCE=..\..\Include\Osg\LineSegment # End Source File # Begin Source File @@ -410,6 +406,14 @@ SOURCE=..\..\Include\Osg\Matrix # End Source File # Begin Source File +SOURCE=..\..\include\osg\mem_ptr +# End Source File +# Begin Source File + +SOURCE=..\..\include\osg\MemoryAdapter +# End Source File +# Begin Source File + SOURCE=..\..\Include\Osg\Node # End Source File # Begin Source File @@ -426,11 +430,7 @@ SOURCE=..\..\Include\Osg\Object # End Source File # Begin Source File -SOURCE=..\..\Include\Osg\Osg -# End Source File -# Begin Source File - -SOURCE=..\..\Include\Osg\Output +SOURCE=..\..\Include\Osg\Plane # End Source File # Begin Source File @@ -438,6 +438,10 @@ SOURCE=..\..\Include\Osg\Point # End Source File # Begin Source File +SOURCE=..\..\Include\Osg\PolygonMode +# End Source File +# Begin Source File + SOURCE=..\..\Include\Osg\PolygonOffset # End Source File # Begin Source File @@ -446,30 +450,22 @@ SOURCE=..\..\Include\Osg\Quat # End Source File # Begin Source File +SOURCE=..\..\include\osg\ref_ptr +# End Source File +# Begin Source File + SOURCE=..\..\Include\Osg\Referenced # End Source File # Begin Source File -SOURCE=..\..\Include\Osg\Registry -# End Source File -# Begin Source File - -SOURCE=..\..\Include\Osg\Scene -# End Source File -# Begin Source File - -SOURCE=..\..\Include\Osg\Seg -# End Source File -# Begin Source File - -SOURCE=..\..\Include\Osg\Sequence -# End Source File -# Begin Source File - SOURCE=..\..\Include\Osg\State # End Source File # Begin Source File +SOURCE=..\..\Include\Osg\StateAttribute +# End Source File +# Begin Source File + SOURCE=..\..\Include\Osg\Switch # End Source File # Begin Source File @@ -494,6 +490,10 @@ SOURCE=..\..\Include\Osg\Timer # End Source File # Begin Source File +SOURCE=..\..\Include\Osg\Transform +# End Source File +# Begin Source File + SOURCE=..\..\Include\Osg\Transparency # End Source File # Begin Source File @@ -510,11 +510,11 @@ SOURCE=..\..\Include\Osg\Vec3 # End Source File # Begin Source File -SOURCE=..\..\Include\Osg\Version +SOURCE=..\..\Include\Osg\Vec4 # End Source File # Begin Source File -SOURCE=..\..\Include\Osg\Vec4 +SOURCE=..\..\Include\Osg\Version # End Source File # End Group # Begin Group "Resource Files" diff --git a/VisualStudio/osgDB/osgDB.dsp b/VisualStudio/osgDB/osgDB.dsp new file mode 100755 index 000000000..eacb8f512 --- /dev/null +++ b/VisualStudio/osgDB/osgDB.dsp @@ -0,0 +1,217 @@ +# Microsoft Developer Studio Project File - Name="osgDB" - Package Owner=<4> +# Microsoft Developer Studio Generated Build File, Format Version 6.00 +# ** DO NOT EDIT ** + +# TARGTYPE "Win32 (x86) Dynamic-Link Library" 0x0102 + +CFG=osgDB - Win32 Debug +!MESSAGE This is not a valid makefile. To build this project using NMAKE, +!MESSAGE use the Export Makefile command and run +!MESSAGE +!MESSAGE NMAKE /f "osgDB.mak". +!MESSAGE +!MESSAGE You can specify a configuration when running NMAKE +!MESSAGE by defining the macro CFG on the command line. For example: +!MESSAGE +!MESSAGE NMAKE /f "osgDB.mak" CFG="osgDB - Win32 Debug" +!MESSAGE +!MESSAGE Possible choices for configuration are: +!MESSAGE +!MESSAGE "osgDB - Win32 Release" (based on "Win32 (x86) Dynamic-Link Library") +!MESSAGE "osgDB - Win32 Debug" (based on "Win32 (x86) Dynamic-Link Library") +!MESSAGE + +# Begin Project +# PROP AllowPerConfigDependencies 0 +# PROP Scc_ProjName "" +# PROP Scc_LocalPath "" +CPP=cl.exe +MTL=midl.exe +RSC=rc.exe + +!IF "$(CFG)" == "osgDB - Win32 Release" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 0 +# PROP BASE Output_Dir "../../lib" +# PROP BASE Intermediate_Dir "Release" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 0 +# PROP Output_Dir "../../lib" +# PROP Intermediate_Dir "Release" +# PROP Ignore_Export_Lib 0 +# PROP Target_Dir "" +# ADD BASE CPP /nologo /MT /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "LIBOSGDB_EXPORTS" /YX /FD /c +# ADD CPP /nologo /MD /W3 /GR /GX /O2 /I "../../include" /D "NDEBUG" /D "_MBCS" /D "_USRDLL" /D "LIBOSGDB_EXPORTS" /D "OSGDB_LIBRARY" /D "WIN32" /D "_WINDOWS" /YX /FD /c +# ADD BASE MTL /nologo /D "NDEBUG" /mktyplib203 /win32 +# ADD MTL /nologo /D "NDEBUG" /mktyplib203 /win32 +# ADD BASE RSC /l 0x809 /d "NDEBUG" +# ADD RSC /l 0x809 /d "NDEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LINK32=link.exe +# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 +# ADD LINK32 osg.lib opengl32.lib glu32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /pdb:"../../bin/osgDB.pdb" /machine:I386 /out:"../../bin/osgDB.dll" /libpath:"../../lib" +# SUBTRACT LINK32 /pdb:none + +!ELSEIF "$(CFG)" == "osgDB - Win32 Debug" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 1 +# PROP BASE Output_Dir "Debug" +# PROP BASE Intermediate_Dir "Debug" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 1 +# PROP Output_Dir "../../lib" +# PROP Intermediate_Dir "Debug" +# PROP Ignore_Export_Lib 0 +# PROP Target_Dir "" +# ADD BASE CPP /nologo /MTd /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "LIBOSGDB_EXPORTS" /YX /FD /GZ /c +# ADD CPP /nologo /MDd /W3 /Gm /vmg /vd0 /GR /GX /ZI /Od /I "../../include" /D "_DEBUG" /D "OSGDB_LIBRARY" /D "WIN32" /D "_WINDOWS" /YX /FD /GZ /c +# ADD BASE MTL /nologo /D "_DEBUG" /mktyplib203 /win32 +# ADD MTL /nologo /D "_DEBUG" /mktyplib203 /win32 +# ADD BASE RSC /l 0x809 /d "_DEBUG" +# ADD RSC /l 0x809 /d "_DEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LINK32=link.exe +# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /pdbtype:sept +# ADD LINK32 osgd.lib opengl32.lib glu32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /pdb:"../../bin/osgDBd.pdb" /debug /machine:I386 /out:"../../bin/osgDBd.dll" /pdbtype:sept /libpath:"../../lib" +# SUBTRACT LINK32 /pdb:none + +!ENDIF + +# Begin Target + +# Name "osgDB - Win32 Release" +# Name "osgDB - Win32 Debug" +# Begin Group "Source Files" + +# PROP Default_Filter "cpp;c;cxx;rc;def;r;odl;idl;hpj;bat" +# Begin Source File + +SOURCE=..\..\Src\osgDB\DotOsgWrapper.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\Src\osgDB\DynamicLibrary.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\Src\osgDB\Field.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\Src\osgDB\FieldReader.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\Src\osgDB\FieldReaderIterator.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\Src\osgDB\FileNameUtils.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\Src\osgDB\FileUtils.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\Src\osgDB\Input.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\Src\osgDB\Output.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\Src\osgDB\ReadFile.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\Src\osgDB\Registry.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\Src\osgDB\Version.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\Src\osgDB\WriteFile.cpp +# End Source File +# End Group +# Begin Group "Header Files" + +# PROP Default_Filter ";h;hpp;hxx;hm;inl" +# Begin Source File + +SOURCE=..\..\Include\osgDB\DotOsgWrapper +# End Source File +# Begin Source File + +SOURCE=..\..\Include\osgDB\DynamicLibrary +# End Source File +# Begin Source File + +SOURCE=..\..\Include\osgDB\Export +# End Source File +# Begin Source File + +SOURCE=..\..\Include\osgDB\Field +# End Source File +# Begin Source File + +SOURCE=..\..\Include\osgDB\FieldReader +# End Source File +# Begin Source File + +SOURCE=..\..\Include\osgDB\FieldReaderIterator +# End Source File +# Begin Source File + +SOURCE=..\..\Include\osgDB\FileNameUtils +# End Source File +# Begin Source File + +SOURCE=..\..\include\osgDB\FileUtils +# End Source File +# Begin Source File + +SOURCE=..\..\Include\osgDB\Input +# End Source File +# Begin Source File + +SOURCE=..\..\Include\osgDB\Output +# End Source File +# Begin Source File + +SOURCE=..\..\include\osgDB\ReaderWriter +# End Source File +# Begin Source File + +SOURCE=..\..\Include\osgDB\ReadFile +# End Source File +# Begin Source File + +SOURCE=..\..\Include\osgDB\Registry +# End Source File +# Begin Source File + +SOURCE=..\..\Include\osgDB\Version +# End Source File +# Begin Source File + +SOURCE=..\..\Include\osgDB\WriteFile +# End Source File +# End Group +# Begin Group "Resource Files" + +# PROP Default_Filter "ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe" +# End Group +# End Target +# End Project diff --git a/VisualStudio/osgGLUT/osgGLUT.dsp b/VisualStudio/osgGLUT/osgGLUT.dsp index e720a096a..5b3223024 100755 --- a/VisualStudio/osgGLUT/osgGLUT.dsp +++ b/VisualStudio/osgGLUT/osgGLUT.dsp @@ -43,7 +43,7 @@ RSC=rc.exe # PROP Ignore_Export_Lib 0 # PROP Target_Dir "" # ADD BASE CPP /nologo /MT /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "LIBOSGGLUT_EXPORTS" /YX /FD /c -# ADD CPP /nologo /MT /W3 /vd1 /GR /GX /O2 /I "../../include" /D "NDEBUG" /D "_MBCS" /D "_USRDLL" /D "LIBOSGGLUT_EXPORTS" /D "OSGGLUT_LIBRARY" /D "WIN32" /D "_WINDOWS" /YX /FD /c +# ADD CPP /nologo /MD /W3 /GR /GX /O2 /I "../../include" /D "NDEBUG" /D "_MBCS" /D "_USRDLL" /D "LIBOSGGLUT_EXPORTS" /D "OSGGLUT_LIBRARY" /D "WIN32" /D "_WINDOWS" /YX /FD /c # ADD BASE MTL /nologo /D "NDEBUG" /mktyplib203 /win32 # ADD MTL /nologo /D "NDEBUG" /mktyplib203 /win32 # ADD BASE RSC /l 0x809 /d "NDEBUG" @@ -53,7 +53,7 @@ BSC32=bscmake.exe # ADD BSC32 /nologo LINK32=link.exe # ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 -# ADD LINK32 osgUtil.lib osg.lib opengl32.lib glu32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /pdb:"../../bin/osgGLUT.pdb" /machine:I386 /out:"../../bin/osgGLUT.dll" /libpath:"../../lib" +# ADD LINK32 osgUtil.lib osgDB.lib osg.lib opengl32.lib glu32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /pdb:"../../bin/osgGLUT.pdb" /machine:I386 /out:"../../bin/osgGLUT.dll" /libpath:"../../lib" # SUBTRACT LINK32 /pdb:none !ELSEIF "$(CFG)" == "osgGLUT - Win32 Debug" @@ -70,7 +70,7 @@ LINK32=link.exe # PROP Ignore_Export_Lib 0 # PROP Target_Dir "" # ADD BASE CPP /nologo /MTd /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "LIBOSGGLUT_EXPORTS" /YX /FD /GZ /c -# ADD CPP /nologo /MTd /W3 /Gm /vmg /vd0 /GR /GX /ZI /Od /I "../../include" /D "_DEBUG" /D "OSGGLUT_LIBRARY" /D "WIN32" /D "_WINDOWS" /YX /FD /GZ /c +# ADD CPP /nologo /MDd /W3 /Gm /vmg /vd0 /GR /GX /ZI /Od /I "../../include" /D "_DEBUG" /D "OSGGLUT_LIBRARY" /D "WIN32" /D "_WINDOWS" /YX /FD /GZ /c # ADD BASE MTL /nologo /D "_DEBUG" /mktyplib203 /win32 # ADD MTL /nologo /D "_DEBUG" /mktyplib203 /win32 # ADD BASE RSC /l 0x809 /d "_DEBUG" @@ -80,7 +80,7 @@ BSC32=bscmake.exe # ADD BSC32 /nologo LINK32=link.exe # ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /pdbtype:sept -# ADD LINK32 osgUtild.lib osgd.lib opengl32.lib glu32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /pdb:"../../bin/osgGLUTd.pdb" /debug /machine:I386 /out:"../../bin/osgGLUTd.dll" /pdbtype:sept /libpath:"../../lib" +# ADD LINK32 osgUtild.lib osgDBd.lib osgd.lib opengl32.lib glu32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /pdb:"../../bin/osgGLUTd.pdb" /debug /machine:I386 /out:"../../bin/osgGLUTd.dll" /pdbtype:sept /libpath:"../../lib" # SUBTRACT LINK32 /pdb:none !ENDIF @@ -98,33 +98,32 @@ SOURCE=..\..\Src\osgGLUT\GLUTEventAdapter.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\osgGLUT\Viewer.cpp +SOURCE=..\..\Src\osgGLUT\Version.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\osgGLUT\Version.cpp +SOURCE=..\..\Src\osgGLUT\Viewer.cpp # End Source File # End Group - # Begin Group "Header Files" # PROP Default_Filter ";h;hpp;hxx;hm;inl" # Begin Source File -SOURCE=..\..\Include\osgGLUT\GLUTEventAdapter -# End Source File -# Begin Source File - -SOURCE=..\..\Include\osgGLUT\Viewer -# End Source File -# Begin Source File - SOURCE=..\..\Include\osgGLUT\Export # End Source File # Begin Source File +SOURCE=..\..\Include\osgGLUT\GLUTEventAdapter +# End Source File +# Begin Source File + SOURCE=..\..\Include\osgGLUT\Version # End Source File +# Begin Source File + +SOURCE=..\..\Include\osgGLUT\Viewer +# End Source File # End Group # Begin Group "Resource Files" @@ -132,4 +131,3 @@ SOURCE=..\..\Include\osgGLUT\Version # End Group # End Target # End Project - diff --git a/VisualStudio/osgPlugins/dw/dw.dsp b/VisualStudio/osgPlugins/dw/dw.dsp new file mode 100644 index 000000000..6a4de52ef --- /dev/null +++ b/VisualStudio/osgPlugins/dw/dw.dsp @@ -0,0 +1,114 @@ +# Microsoft Developer Studio Project File - Name="dw" - Package Owner=<4> +# Microsoft Developer Studio Generated Build File, Format Version 6.00 +# ** DO NOT EDIT ** + +# TARGTYPE "Win32 (x86) Dynamic-Link Library" 0x0102 + +CFG=dw - Win32 Debug +!MESSAGE This is not a valid makefile. To build this project using NMAKE, +!MESSAGE use the Export Makefile command and run +!MESSAGE +!MESSAGE NMAKE /f "dw.mak". +!MESSAGE +!MESSAGE You can specify a configuration when running NMAKE +!MESSAGE by defining the macro CFG on the command line. For example: +!MESSAGE +!MESSAGE NMAKE /f "dw.mak" CFG="dw - Win32 Debug" +!MESSAGE +!MESSAGE Possible choices for configuration are: +!MESSAGE +!MESSAGE "dw - Win32 Release" (based on "Win32 (x86) Dynamic-Link Library") +!MESSAGE "dw - Win32 Debug" (based on "Win32 (x86) Dynamic-Link Library") +!MESSAGE + +# Begin Project +# PROP AllowPerConfigDependencies 0 +# PROP Scc_ProjName "" +# PROP Scc_LocalPath "" +CPP=cl.exe +MTL=midl.exe +RSC=rc.exe + +!IF "$(CFG)" == "dw - Win32 Release" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 0 +# PROP BASE Output_Dir "Release" +# PROP BASE Intermediate_Dir "Release" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 0 +# PROP Output_Dir "../../../lib" +# PROP Intermediate_Dir "Release" +# PROP Ignore_Export_Lib 0 +# PROP Target_Dir "" +# ADD BASE CPP /nologo /MT /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "dw_EXPORTS" /YX /FD /c +# ADD CPP /nologo /MD /W3 /GR /GX /O2 /I "../../../include" /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "dw_EXPORTS" /YX /FD /c +# ADD BASE MTL /nologo /D "NDEBUG" /mktyplib203 /win32 +# ADD MTL /nologo /D "NDEBUG" /mktyplib203 /win32 +# ADD BASE RSC /l 0x809 /d "NDEBUG" +# ADD RSC /l 0x809 /d "NDEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LINK32=link.exe +# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 +# ADD LINK32 osgDB.lib osgUtil.lib osg.lib glu32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 /nodefaultlib:"LIBC" /out:"../../../bin/osgdb_dw.dll" /libpath:"../../../lib" +# SUBTRACT LINK32 /nodefaultlib + +!ELSEIF "$(CFG)" == "dw - Win32 Debug" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 1 +# PROP BASE Output_Dir "Debug" +# PROP BASE Intermediate_Dir "Debug" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 1 +# PROP Output_Dir "../../../lib" +# PROP Intermediate_Dir "Debug" +# PROP Ignore_Export_Lib 0 +# PROP Target_Dir "" +# ADD BASE CPP /nologo /MTd /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "dw_EXPORTS" /YX /FD /GZ /c +# ADD CPP /nologo /MDd /W3 /Gm /vmg /vd0 /GR /GX /ZI /Od /I "../../../include" /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "DW_EXPORTS" /YX /FD /GZ /c +# ADD BASE MTL /nologo /D "_DEBUG" /mktyplib203 /win32 +# ADD MTL /nologo /D "_DEBUG" /mktyplib203 /win32 +# ADD BASE RSC /l 0x809 /d "_DEBUG" +# ADD RSC /l 0x809 /d "_DEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LINK32=link.exe +# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /pdbtype:sept +# ADD LINK32 osgDBd.lib osgUtild.lib osgd.lib glu32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /nodefaultlib:"LIBC" /out:"../../../bin/osgdb_dwd.dll" /pdbtype:sept /libpath:"../../../lib" +# SUBTRACT LINK32 /pdb:none + +!ENDIF + +# Begin Target + +# Name "dw - Win32 Release" +# Name "dw - Win32 Debug" +# Begin Group "Source Files" + +# PROP Default_Filter "cpp;c;cxx;rc;def;r;odl;idl;hpj;bat" +# Begin Source File + +SOURCE=..\..\..\src\osgPlugins\dw\ReaderWriterDW.cpp +# End Source File +# End Group +# Begin Group "Header Files" + +# PROP Default_Filter "" + +# End Group +# End Target +# Begin Group "Header Files No. 1" + +# PROP Default_Filter "h;hpp;hxx;hm;inl" +# End Group +# Begin Group "Resource Files" + +# PROP Default_Filter "" +# End Group +# End Project diff --git a/VisualStudio/osgPlugins/flt/flt.dsp b/VisualStudio/osgPlugins/flt/flt.dsp index c6a3d863d..bbc5d23c4 100644 --- a/VisualStudio/osgPlugins/flt/flt.dsp +++ b/VisualStudio/osgPlugins/flt/flt.dsp @@ -43,7 +43,7 @@ RSC=rc.exe # PROP Ignore_Export_Lib 0 # PROP Target_Dir "" # ADD BASE CPP /nologo /MT /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "FLT_EXPORTS" /YX /FD /c -# ADD CPP /nologo /MT /W3 /GR /GX /O2 /I "../../../include" /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "FLT_LIBRARY" /YX /FD /c +# ADD CPP /nologo /MD /W3 /GR /GX /O2 /I "../../../include" /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "FLT_LIBRARY" /YX /FD /c # ADD BASE MTL /nologo /D "NDEBUG" /mktyplib203 /win32 # ADD MTL /nologo /D "NDEBUG" /mktyplib203 /win32 # ADD BASE RSC /l 0x414 /d "NDEBUG" @@ -53,7 +53,7 @@ BSC32=bscmake.exe # ADD BSC32 /nologo LINK32=link.exe # ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 -# ADD LINK32 osg.lib opengl32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /pdb:none /machine:I386 /out:"../../../bin/osgdb_flt.dll" /libpath:"../../../lib" +# ADD LINK32 osg.lib osgDB.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /pdb:none /machine:I386 /out:"../../../bin/osgdb_flt.dll" /libpath:"../../../lib" !ELSEIF "$(CFG)" == "flt - Win32 Debug" @@ -69,7 +69,7 @@ LINK32=link.exe # PROP Ignore_Export_Lib 0 # PROP Target_Dir "" # ADD BASE CPP /nologo /MTd /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "FLT_EXPORTS" /YX /FD /GZ /c -# ADD CPP /nologo /MTd /W3 /Gm /vmg /vd0 /GR /GX /ZI /Od /I "../../../include" /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "FLT_LIBRARY" /YX /FD /GZ /c +# ADD CPP /nologo /MDd /W3 /Gm /vmg /vd0 /GR /GX /ZI /Od /I "../../../include" /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "FLT_LIBRARY" /YX /FD /GZ /c # ADD BASE MTL /nologo /D "_DEBUG" /mktyplib203 /win32 # ADD MTL /nologo /D "_DEBUG" /mktyplib203 /win32 # ADD BASE RSC /l 0x414 /d "_DEBUG" @@ -79,7 +79,7 @@ BSC32=bscmake.exe # ADD BSC32 /nologo LINK32=link.exe # ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /pdbtype:sept -# ADD LINK32 osgd.lib glut32.lib glu32.lib opengl32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /pdb:"../../../bin/osgdb_fltd.pdb" /debug /machine:I386 /out:"../../../bin/osgdb_fltd.dll" /pdbtype:sept /libpath:"../../../lib" +# ADD LINK32 osgd.lib osgDBd.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /pdb:"../../../bin/osgdb_fltd.pdb" /debug /machine:I386 /out:"../../../bin/osgdb_fltd.dll" /pdbtype:sept /libpath:"../../../lib" # SUBTRACT LINK32 /pdb:none /incremental:no !ENDIF @@ -185,6 +185,10 @@ SOURCE=..\..\..\src\osgPlugins\flt\ObjectRecord.cpp # End Source File # Begin Source File +SOURCE=..\..\..\src\osgPlugins\flt\OldMaterialPaletteRecord.cpp +# End Source File +# Begin Source File + SOURCE=..\..\..\src\osgPlugins\flt\OldVertexRecords.cpp # End Source File # Begin Source File @@ -257,10 +261,6 @@ SOURCE=..\..\..\src\osgPlugins\flt\DofRecord.h # End Source File # Begin Source File -SOURCE=..\..\..\src\osgPlugins\flt\export.h -# End Source File -# Begin Source File - SOURCE=..\..\..\src\osgPlugins\flt\ExtensionRecord.h # End Source File # Begin Source File @@ -337,6 +337,10 @@ SOURCE=..\..\..\src\osgPlugins\flt\ObjectRecord.h # End Source File # Begin Source File +SOURCE=..\..\..\src\osgPlugins\flt\OldMaterialPaletteRecord.h +# End Source File +# Begin Source File + SOURCE=..\..\..\src\osgPlugins\flt\OldVertexRecords.h # End Source File # Begin Source File diff --git a/VisualStudio/osgPlugins/gif/gif.dsp b/VisualStudio/osgPlugins/gif/gif.dsp index bac94e1fb..49e867f65 100755 --- a/VisualStudio/osgPlugins/gif/gif.dsp +++ b/VisualStudio/osgPlugins/gif/gif.dsp @@ -43,7 +43,7 @@ RSC=rc.exe # PROP Ignore_Export_Lib 0 # PROP Target_Dir "" # ADD BASE CPP /nologo /MT /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "gif_EXPORTS" /YX /FD /c -# ADD CPP /nologo /MT /W3 /GR /GX /O2 /I "../../../include" /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "gif_EXPORTS" /YX /FD /c +# ADD CPP /nologo /MD /W3 /GR /GX /O2 /I "../../../include" /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "gif_EXPORTS" /YX /FD /c # ADD BASE MTL /nologo /D "NDEBUG" /mktyplib203 /win32 # ADD MTL /nologo /D "NDEBUG" /mktyplib203 /win32 # ADD BASE RSC /l 0x809 /d "NDEBUG" @@ -53,7 +53,7 @@ BSC32=bscmake.exe # ADD BSC32 /nologo LINK32=link.exe # ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 -# ADD LINK32 osg.lib /NODEFAULTLIB:LIBC ungif.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 /out:"../../../bin/osgdb_gif.dll" /libpath:"../../../lib" +# ADD LINK32 osgDB.lib osg.lib ungif.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 /nodefaultlib:"LIBC" /out:"../../../bin/osgdb_gif.dll" /libpath:"../../../lib" # SUBTRACT LINK32 /nodefaultlib !ELSEIF "$(CFG)" == "gif - Win32 Debug" @@ -70,7 +70,7 @@ LINK32=link.exe # PROP Ignore_Export_Lib 0 # PROP Target_Dir "" # ADD BASE CPP /nologo /MTd /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "gif_EXPORTS" /YX /FD /GZ /c -# ADD CPP /nologo /MTd /W3 /Gm /vmg /vd0 /GR /GX /ZI /Od /I "../../../include" /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "GIF_EXPORTS" /YX /FD /GZ /c +# ADD CPP /nologo /MDd /W3 /Gm /vmg /vd0 /GR /GX /ZI /Od /I "../../../include" /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "GIF_EXPORTS" /YX /FD /GZ /c # ADD BASE MTL /nologo /D "_DEBUG" /mktyplib203 /win32 # ADD MTL /nologo /D "_DEBUG" /mktyplib203 /win32 # ADD BASE RSC /l 0x809 /d "_DEBUG" @@ -80,7 +80,7 @@ BSC32=bscmake.exe # ADD BSC32 /nologo LINK32=link.exe # ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /pdbtype:sept -# ADD LINK32 osgd.lib /NODEFAULTLIB:LIBC ungif.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /out:"../../../bin/osgdb_gifd.dll" /pdbtype:sept /libpath:"../../../lib" +# ADD LINK32 osgd.lib ungif.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /nodefaultlib:"LIBC" /out:"../../../bin/osgdb_gifd.dll" /pdbtype:sept /libpath:"../../../lib" # SUBTRACT LINK32 /nodefaultlib !ENDIF diff --git a/VisualStudio/osgPlugins/jpeg/jpeg.dsp b/VisualStudio/osgPlugins/jpeg/jpeg.dsp index 58bd354dd..1e5ccc310 100755 --- a/VisualStudio/osgPlugins/jpeg/jpeg.dsp +++ b/VisualStudio/osgPlugins/jpeg/jpeg.dsp @@ -43,7 +43,7 @@ RSC=rc.exe # PROP Ignore_Export_Lib 0 # PROP Target_Dir "" # ADD BASE CPP /nologo /MT /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "jpeg_EXPORTS" /YX /FD /c -# ADD CPP /nologo /MT /W3 /GR /GX /O2 /I "../../../include" /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "jpeg_EXPORTS" /YX /FD /c +# ADD CPP /nologo /MD /W3 /GR /GX /O2 /I "../../../include" /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "jpeg_EXPORTS" /YX /FD /c # ADD BASE MTL /nologo /D "NDEBUG" /mktyplib203 /win32 # ADD MTL /nologo /D "NDEBUG" /mktyplib203 /win32 # ADD BASE RSC /l 0x809 /d "NDEBUG" @@ -53,7 +53,7 @@ BSC32=bscmake.exe # ADD BSC32 /nologo LINK32=link.exe # ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 -# ADD LINK32 osg.lib /NODEFAULTLIB:LIBC jpeg.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 /out:"../../../bin/osgdb_jpeg.dll" /libpath:"../../../lib" +# ADD LINK32 osgDB.lib osg.lib libjpeg.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 /nodefaultlib:"LIBC" /out:"../../../bin/osgdb_jpeg.dll" /libpath:"../../../lib" # SUBTRACT LINK32 /nodefaultlib !ELSEIF "$(CFG)" == "jpeg - Win32 Debug" @@ -70,7 +70,7 @@ LINK32=link.exe # PROP Ignore_Export_Lib 0 # PROP Target_Dir "" # ADD BASE CPP /nologo /MTd /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "jpeg_EXPORTS" /YX /FD /GZ /c -# ADD CPP /nologo /MTd /W3 /Gm /vmg /vd0 /GR /GX /ZI /Od /I "../../../include" /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "JPEG_EXPORTS" /YX /FD /GZ /c +# ADD CPP /nologo /MDd /W3 /Gm /vmg /vd0 /GR /GX /ZI /Od /I "../../../include" /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "JPEG_EXPORTS" /YX /FD /GZ /c # ADD BASE MTL /nologo /D "_DEBUG" /mktyplib203 /win32 # ADD MTL /nologo /D "_DEBUG" /mktyplib203 /win32 # ADD BASE RSC /l 0x809 /d "_DEBUG" @@ -80,7 +80,7 @@ BSC32=bscmake.exe # ADD BSC32 /nologo LINK32=link.exe # ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /pdbtype:sept -# ADD LINK32 osgd.lib /NODEFAULTLIB:LIBC jpeg.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /out:"../../../bin/osgdb_jpegd.dll" /pdbtype:sept /libpath:"../../../lib" +# ADD LINK32 osgDBd.lib osgd.lib libjpeg.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /nodefaultlib:"LIBC" /out:"../../../bin/osgdb_jpegd.dll" /pdbtype:sept /libpath:"../../../lib" # SUBTRACT LINK32 /nodefaultlib !ENDIF diff --git a/VisualStudio/osgPlugins/lib3ds/lib3ds.dsp b/VisualStudio/osgPlugins/lib3ds/lib3ds.dsp new file mode 100644 index 000000000..2fa719514 --- /dev/null +++ b/VisualStudio/osgPlugins/lib3ds/lib3ds.dsp @@ -0,0 +1,269 @@ +# Microsoft Developer Studio Project File - Name="3ds" - Package Owner=<4> +# Microsoft Developer Studio Generated Build File, Format Version 6.00 +# ** DO NOT EDIT ** + +# TARGTYPE "Win32 (x86) Dynamic-Link Library" 0x0102 + +CFG=3ds - Win32 Debug +!MESSAGE This is not a valid makefile. To build this project using NMAKE, +!MESSAGE use the Export Makefile command and run +!MESSAGE +!MESSAGE NMAKE /f "lib3ds.mak". +!MESSAGE +!MESSAGE You can specify a configuration when running NMAKE +!MESSAGE by defining the macro CFG on the command line. For example: +!MESSAGE +!MESSAGE NMAKE /f "lib3ds.mak" CFG="3ds - Win32 Debug" +!MESSAGE +!MESSAGE Possible choices for configuration are: +!MESSAGE +!MESSAGE "3ds - Win32 Release" (based on "Win32 (x86) Dynamic-Link Library") +!MESSAGE "3ds - Win32 Debug" (based on "Win32 (x86) Dynamic-Link Library") +!MESSAGE + +# Begin Project +# PROP AllowPerConfigDependencies 0 +# PROP Scc_ProjName "" +# PROP Scc_LocalPath "" +CPP=cl.exe +MTL=midl.exe +RSC=rc.exe + +!IF "$(CFG)" == "3ds - Win32 Release" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 0 +# PROP BASE Output_Dir "Release" +# PROP BASE Intermediate_Dir "Release" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 0 +# PROP Output_Dir "../../../lib" +# PROP Intermediate_Dir "Release" +# PROP Ignore_Export_Lib 0 +# PROP Target_Dir "" +# ADD BASE CPP /nologo /MT /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "3ds_EXPORTS" /YX /FD /c +# ADD CPP /nologo /MD /W3 /GR /GX /O2 /I "../../../include" /I "../../../src/osgPlugins/lib3ds" /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "3ds_EXPORTS" /YX /FD /c +# ADD BASE MTL /nologo /D "NDEBUG" /mktyplib203 /win32 +# ADD MTL /nologo /D "NDEBUG" /mktyplib203 /win32 +# ADD BASE RSC /l 0x809 /d "NDEBUG" +# ADD RSC /l 0x809 /d "NDEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LINK32=link.exe +# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 +# ADD LINK32 osgDB.lib osg.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 /nodefaultlib:"LIBC" /out:"../../../bin/osgdb_3ds.dll" /libpath:"../../../lib" +# SUBTRACT LINK32 /nodefaultlib + +!ELSEIF "$(CFG)" == "3ds - Win32 Debug" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 1 +# PROP BASE Output_Dir "Debug" +# PROP BASE Intermediate_Dir "Debug" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 1 +# PROP Output_Dir "../../../lib" +# PROP Intermediate_Dir "Debug" +# PROP Ignore_Export_Lib 0 +# PROP Target_Dir "" +# ADD BASE CPP /nologo /MTd /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "3ds_EXPORTS" /YX /FD /GZ /c +# ADD CPP /nologo /MDd /W3 /Gm /vmg /vd0 /GR /GX /ZI /Od /I "../../../include" /I "../../../src/osgPlugins/lib3ds" /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "3DS_EXPORTS" /YX /FD /GZ /c +# ADD BASE MTL /nologo /D "_DEBUG" /mktyplib203 /win32 +# ADD MTL /nologo /D "_DEBUG" /mktyplib203 /win32 +# ADD BASE RSC /l 0x809 /d "_DEBUG" +# ADD RSC /l 0x809 /d "_DEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LINK32=link.exe +# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /pdbtype:sept +# ADD LINK32 osgd.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /nodefaultlib:"LIBC" /out:"../../../bin/osgdb_3dsd.dll" /pdbtype:sept /libpath:"../../../lib" +# SUBTRACT LINK32 /nodefaultlib + +!ENDIF + +# Begin Target + +# Name "3ds - Win32 Release" +# Name "3ds - Win32 Debug" +# Begin Group "Source Files" + +# PROP Default_Filter "cpp;c;cxx;rc;def;r;odl;idl;hpj;bat" +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Lib3ds\atmosphere.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Lib3ds\background.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Lib3ds\Camera.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Lib3ds\Chunk.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Lib3ds\Ease.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Lib3ds\File.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Lib3ds\Lib3ds_float.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Lib3ds\Light.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Lib3ds\Material.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Lib3ds\Matrix.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Lib3ds\Mesh.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Lib3ds\Node.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Lib3ds\Quat.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Lib3ds\ReaderWriter3DS.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Lib3ds\readwrite.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Lib3ds\Shadow.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Lib3ds\Tcb.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Lib3ds\Tracks.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Lib3ds\Vector.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Lib3ds\Viewport.cpp +# End Source File +# End Group +# Begin Group "Header Files" + +# PROP Default_Filter "h;hpp;hxx;hm;inl" +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Lib3ds\atmosphere.h +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Lib3ds\background.h +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Lib3ds\Camera.h +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Lib3ds\Chunk.h +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Lib3ds\chunktable.h +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Lib3ds\Ease.h +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Lib3ds\File.h +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Lib3ds\Lib3ds_float.h +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Lib3ds\Light.h +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Lib3ds\Material.h +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Lib3ds\Matrix.h +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Lib3ds\Mesh.h +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Lib3ds\Node.h +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Lib3ds\Quat.h +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Lib3ds\readwrite.h +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Lib3ds\Shadow.h +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Lib3ds\Tcb.h +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Lib3ds\Tracks.h +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Lib3ds\Types.h +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Lib3ds\Vector.h +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Lib3ds\Viewport.h +# End Source File +# End Group +# Begin Group "Resource Files" + +# PROP Default_Filter "ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe" +# End Group +# End Target +# End Project diff --git a/VisualStudio/osgPlugins/lwo/lwo.dsp b/VisualStudio/osgPlugins/lwo/lwo.dsp new file mode 100644 index 000000000..a85e25bb8 --- /dev/null +++ b/VisualStudio/osgPlugins/lwo/lwo.dsp @@ -0,0 +1,121 @@ +# Microsoft Developer Studio Project File - Name="lwo" - Package Owner=<4> +# Microsoft Developer Studio Generated Build File, Format Version 6.00 +# ** DO NOT EDIT ** + +# TARGTYPE "Win32 (x86) Dynamic-Link Library" 0x0102 + +CFG=lwo - Win32 Debug +!MESSAGE This is not a valid makefile. To build this project using NMAKE, +!MESSAGE use the Export Makefile command and run +!MESSAGE +!MESSAGE NMAKE /f "lwo.mak". +!MESSAGE +!MESSAGE You can specify a configuration when running NMAKE +!MESSAGE by defining the macro CFG on the command line. For example: +!MESSAGE +!MESSAGE NMAKE /f "lwo.mak" CFG="lwo - Win32 Debug" +!MESSAGE +!MESSAGE Possible choices for configuration are: +!MESSAGE +!MESSAGE "lwo - Win32 Release" (based on "Win32 (x86) Dynamic-Link Library") +!MESSAGE "lwo - Win32 Debug" (based on "Win32 (x86) Dynamic-Link Library") +!MESSAGE + +# Begin Project +# PROP AllowPerConfigDependencies 0 +# PROP Scc_ProjName "" +# PROP Scc_LocalPath "" +CPP=cl.exe +MTL=midl.exe +RSC=rc.exe + +!IF "$(CFG)" == "lwo - Win32 Release" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 0 +# PROP BASE Output_Dir "Release" +# PROP BASE Intermediate_Dir "Release" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 0 +# PROP Output_Dir "../../../lib" +# PROP Intermediate_Dir "Release" +# PROP Ignore_Export_Lib 0 +# PROP Target_Dir "" +# ADD BASE CPP /nologo /MT /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "lwo_EXPORTS" /YX /FD /c +# ADD CPP /nologo /MD /W3 /GR /GX /O2 /I "../../../include" /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "lwo_EXPORTS" /YX /FD /c +# ADD BASE MTL /nologo /D "NDEBUG" /mktyplib203 /win32 +# ADD MTL /nologo /D "NDEBUG" /mktyplib203 /win32 +# ADD BASE RSC /l 0x809 /d "NDEBUG" +# ADD RSC /l 0x809 /d "NDEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LINK32=link.exe +# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 +# ADD LINK32 osgDB.lib osgUtil.lib osg.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 /nodefaultlib:"LIBC" /out:"../../../bin/osgdb_lwo.dll" /libpath:"../../../lib" +# SUBTRACT LINK32 /nodefaultlib + +!ELSEIF "$(CFG)" == "lwo - Win32 Debug" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 1 +# PROP BASE Output_Dir "Debug" +# PROP BASE Intermediate_Dir "Debug" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 1 +# PROP Output_Dir "../../../lib" +# PROP Intermediate_Dir "Debug" +# PROP Ignore_Export_Lib 0 +# PROP Target_Dir "" +# ADD BASE CPP /nologo /MTd /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "lwo_EXPORTS" /YX /FD /GZ /c +# ADD CPP /nologo /MDd /W3 /Gm /vmg /vd0 /GR /GX /ZI /Od /I "../../../include" /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "LWO_EXPORTS" /YX /FD /GZ /c +# ADD BASE MTL /nologo /D "_DEBUG" /mktyplib203 /win32 +# ADD MTL /nologo /D "_DEBUG" /mktyplib203 /win32 +# ADD BASE RSC /l 0x809 /d "_DEBUG" +# ADD RSC /l 0x809 /d "_DEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LINK32=link.exe +# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /pdbtype:sept +# ADD LINK32 osgDBd.lib osgUtild.lib osgd.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /nodefaultlib:"LIBC" /out:"../../../bin/osgdb_lwod.dll" /pdbtype:sept /libpath:"../../../lib" +# SUBTRACT LINK32 /pdb:none + +!ENDIF + +# Begin Target + +# Name "lwo - Win32 Release" +# Name "lwo - Win32 Debug" +# Begin Group "Source Files" + +# PROP Default_Filter "cpp;c;cxx;rc;def;r;odl;idl;hpj;bat" +# Begin Source File + +SOURCE=..\..\..\src\osgPlugins\lwo\lw.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\osgPlugins\lwo\ReaderWriterLWO.cpp +# End Source File +# End Group +# Begin Group "Header Files" + +# PROP Default_Filter "" +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\lwo\lw.h +# End Source File +# End Group +# End Target +# Begin Group "Header Files No. 1" + +# PROP Default_Filter "h;hpp;hxx;hm;inl" +# End Group +# Begin Group "Resource Files" + +# PROP Default_Filter "" +# End Group +# End Project diff --git a/VisualStudio/osgPlugins/obj/obj.dsp b/VisualStudio/osgPlugins/obj/obj.dsp new file mode 100644 index 000000000..8f6e453e3 --- /dev/null +++ b/VisualStudio/osgPlugins/obj/obj.dsp @@ -0,0 +1,117 @@ +# Microsoft Developer Studio Project File - Name="obj" - Package Owner=<4> +# Microsoft Developer Studio Generated Build File, Format Version 6.00 +# ** DO NOT EDIT ** + +# TARGTYPE "Win32 (x86) Dynamic-Link Library" 0x0102 + +CFG=obj - Win32 Debug +!MESSAGE This is not a valid makefile. To build this project using NMAKE, +!MESSAGE use the Export Makefile command and run +!MESSAGE +!MESSAGE NMAKE /f "obj.mak". +!MESSAGE +!MESSAGE You can specify a configuration when running NMAKE +!MESSAGE by defining the macro CFG on the command line. For example: +!MESSAGE +!MESSAGE NMAKE /f "obj.mak" CFG="obj - Win32 Debug" +!MESSAGE +!MESSAGE Possible choices for configuration are: +!MESSAGE +!MESSAGE "obj - Win32 Release" (based on "Win32 (x86) Dynamic-Link Library") +!MESSAGE "obj - Win32 Debug" (based on "Win32 (x86) Dynamic-Link Library") +!MESSAGE + +# Begin Project +# PROP AllowPerConfigDependencies 0 +# PROP Scc_ProjName "" +# PROP Scc_LocalPath "" +CPP=cl.exe +MTL=midl.exe +RSC=rc.exe + +!IF "$(CFG)" == "obj - Win32 Release" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 0 +# PROP BASE Output_Dir "Release" +# PROP BASE Intermediate_Dir "Release" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 0 +# PROP Output_Dir "../../../lib" +# PROP Intermediate_Dir "Release" +# PROP Ignore_Export_Lib 0 +# PROP Target_Dir "" +# ADD BASE CPP /nologo /MT /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "obj_EXPORTS" /YX /FD /c +# ADD CPP /nologo /MD /W3 /GR /GX /O2 /I "../../../include" /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "obj_EXPORTS" /YX /FD /c +# ADD BASE MTL /nologo /D "NDEBUG" /mktyplib203 /win32 +# ADD MTL /nologo /D "NDEBUG" /mktyplib203 /win32 +# ADD BASE RSC /l 0x809 /d "NDEBUG" +# ADD RSC /l 0x809 /d "NDEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LINK32=link.exe +# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 +# ADD LINK32 osgDB.lib osg.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 /nodefaultlib:"LIBC" /out:"../../../bin/osgdb_obj.dll" /libpath:"../../../lib" +# SUBTRACT LINK32 /nodefaultlib + +!ELSEIF "$(CFG)" == "obj - Win32 Debug" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 1 +# PROP BASE Output_Dir "Debug" +# PROP BASE Intermediate_Dir "Debug" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 1 +# PROP Output_Dir "../../../lib" +# PROP Intermediate_Dir "Debug" +# PROP Ignore_Export_Lib 0 +# PROP Target_Dir "" +# ADD BASE CPP /nologo /MTd /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "obj_EXPORTS" /YX /FD /GZ /c +# ADD CPP /nologo /MDd /W3 /Gm /vmg /vd0 /GR /GX /ZI /Od /I "../../../include" /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "OBJ_EXPORTS" /YX /FD /GZ /c +# ADD BASE MTL /nologo /D "_DEBUG" /mktyplib203 /win32 +# ADD MTL /nologo /D "_DEBUG" /mktyplib203 /win32 +# ADD BASE RSC /l 0x809 /d "_DEBUG" +# ADD RSC /l 0x809 /d "_DEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LINK32=link.exe +# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /pdbtype:sept +# ADD LINK32 osgd.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /nodefaultlib:"LIBC" /out:"../../../bin/osgdb_objd.dll" /pdbtype:sept /libpath:"../../../lib" +# SUBTRACT LINK32 /nodefaultlib + +!ENDIF + +# Begin Target + +# Name "obj - Win32 Release" +# Name "obj - Win32 Debug" +# Begin Group "Source Files" + +# PROP Default_Filter "cpp;c;cxx;rc;def;r;odl;idl;hpj;bat" +# Begin Source File + +SOURCE=..\..\..\src\osgPlugins\obj\ReaderWriterOBJ.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\osgPlugins\obj\glm.cpp +# End Source File +# End Group +# Begin Group "Header Files" + +# PROP Default_Filter "h;hpp;hxx;hm;inl" +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\obj\glm.h +# End Source File +# End Group +# Begin Group "Resource Files" + +# PROP Default_Filter "ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe" +# End Group +# End Target +# End Project diff --git a/VisualStudio/osgPlugins/osg/dot_osg.dsp b/VisualStudio/osgPlugins/osg/dot_osg.dsp new file mode 100755 index 000000000..9843c2e24 --- /dev/null +++ b/VisualStudio/osgPlugins/osg/dot_osg.dsp @@ -0,0 +1,241 @@ +# Microsoft Developer Studio Project File - Name="dot_osg" - Package Owner=<4> +# Microsoft Developer Studio Generated Build File, Format Version 6.00 +# ** DO NOT EDIT ** + +# TARGTYPE "Win32 (x86) Dynamic-Link Library" 0x0102 + +CFG=dot_osg - Win32 Release +!MESSAGE This is not a valid makefile. To build this project using NMAKE, +!MESSAGE use the Export Makefile command and run +!MESSAGE +!MESSAGE NMAKE /f "dot_osg.mak". +!MESSAGE +!MESSAGE You can specify a configuration when running NMAKE +!MESSAGE by defining the macro CFG on the command line. For example: +!MESSAGE +!MESSAGE NMAKE /f "dot_osg.mak" CFG="dot_osg - Win32 Release" +!MESSAGE +!MESSAGE Possible choices for configuration are: +!MESSAGE +!MESSAGE "dot_osg - Win32 Release" (based on "Win32 (x86) Dynamic-Link Library") +!MESSAGE "dot_osg - Win32 Debug" (based on "Win32 (x86) Dynamic-Link Library") +!MESSAGE + +# Begin Project +# PROP AllowPerConfigDependencies 0 +# PROP Scc_ProjName "" +# PROP Scc_LocalPath "" +CPP=cl.exe +MTL=midl.exe +RSC=rc.exe + +!IF "$(CFG)" == "dot_osg - Win32 Release" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 0 +# PROP BASE Output_Dir "Release" +# PROP BASE Intermediate_Dir "Release" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 0 +# PROP Output_Dir "../../../lib" +# PROP Intermediate_Dir "Release" +# PROP Ignore_Export_Lib 0 +# PROP Target_Dir "" +# ADD BASE CPP /nologo /MT /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "osg_EXPORTS" /YX /FD /c +# ADD CPP /nologo /MD /W3 /GR /GX /O2 /I "../../../include" /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "osg_EXPORTS" /YX /FD /c +# ADD BASE MTL /nologo /D "NDEBUG" /mktyplib203 /win32 +# ADD MTL /nologo /D "NDEBUG" /mktyplib203 /win32 +# ADD BASE RSC /l 0x809 /d "NDEBUG" +# ADD RSC /l 0x809 /d "NDEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LINK32=link.exe +# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 +# ADD LINK32 osgDB.lib osg.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 /nodefaultlib:"LIBC" /out:"../../../bin/osgdb_osg.dll" /libpath:"../../../lib" +# SUBTRACT LINK32 /nodefaultlib + +!ELSEIF "$(CFG)" == "dot_osg - Win32 Debug" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 1 +# PROP BASE Output_Dir "Debug" +# PROP BASE Intermediate_Dir "Debug" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 1 +# PROP Output_Dir "../../../lib" +# PROP Intermediate_Dir "Debug" +# PROP Ignore_Export_Lib 0 +# PROP Target_Dir "" +# ADD BASE CPP /nologo /MTd /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "osg_EXPORTS" /YX /FD /GZ /c +# ADD CPP /nologo /MDd /W3 /Gm /vmg /vd0 /GR /GX /ZI /Od /I "../../../include" /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "OSG_EXPORTS" /YX /FD /GZ /c +# ADD BASE MTL /nologo /D "_DEBUG" /mktyplib203 /win32 +# ADD MTL /nologo /D "_DEBUG" /mktyplib203 /win32 +# ADD BASE RSC /l 0x809 /d "_DEBUG" +# ADD RSC /l 0x809 /d "_DEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LINK32=link.exe +# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /pdbtype:sept +# ADD LINK32 osgd.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /nodefaultlib:"LIBC" /out:"../../../bin/osgdb_osgd.dll" /pdbtype:sept /libpath:"../../../lib" +# SUBTRACT LINK32 /nodefaultlib + +!ENDIF + +# Begin Target + +# Name "dot_osg - Win32 Release" +# Name "dot_osg - Win32 Debug" +# Begin Group "Source Files" + +# PROP Default_Filter "cpp;c;cxx;rc;def;r;odl;idl;hpj;bat" +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Osg\AlphaFunc.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Osg\Billboard.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Osg\ColorMask.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Osg\ClipPlane.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Osg\CullFace.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Osg\Depth.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Osg\Drawable.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Osg\Fog.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Osg\FrontFace.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Osg\Geode.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Osg\GeoSet.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Osg\StateSet.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Osg\Group.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Osg\Image.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Osg\Impostor.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Osg\Light.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Osg\LightSource.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Osg\LOD.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Osg\Material.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Osg\Matrix.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Osg\Node.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Osg\Object.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Osg\Point.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Osg\PolygonMode.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Osg\PolygonOffset.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\src\osgPlugins\osg\ReaderWriterOSG.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Osg\Switch.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Osg\Stencil.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Osg\TexEnv.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Osg\TexGen.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Osg\TexMat.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Osg\Texture.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Osg\Transform.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\..\Src\osgPlugins\Osg\Transparency.cpp +# End Source File +# End Group +# Begin Group "Header Files" + +# PROP Default_Filter "h;hpp;hxx;hm;inl" +# End Group +# Begin Group "Resource Files" + +# PROP Default_Filter "ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe" +# End Group +# End Target +# End Project diff --git a/VisualStudio/osgPlugins/osgtgz/osgtgz.dsp b/VisualStudio/osgPlugins/osgtgz/osgtgz.dsp new file mode 100644 index 000000000..93967eb9f --- /dev/null +++ b/VisualStudio/osgPlugins/osgtgz/osgtgz.dsp @@ -0,0 +1,109 @@ +# Microsoft Developer Studio Project File - Name="osgtgz" - Package Owner=<4> +# Microsoft Developer Studio Generated Build File, Format Version 6.00 +# ** DO NOT EDIT ** + +# TARGTYPE "Win32 (x86) Dynamic-Link Library" 0x0102 + +CFG=osgtgz - Win32 Debug +!MESSAGE This is not a valid makefile. To build this project using NMAKE, +!MESSAGE use the Export Makefile command and run +!MESSAGE +!MESSAGE NMAKE /f "osgtgz.mak". +!MESSAGE +!MESSAGE You can specify a configuration when running NMAKE +!MESSAGE by defining the macro CFG on the command line. For example: +!MESSAGE +!MESSAGE NMAKE /f "osgtgz.mak" CFG="osgtgz - Win32 Debug" +!MESSAGE +!MESSAGE Possible choices for configuration are: +!MESSAGE +!MESSAGE "osgtgz - Win32 Release" (based on "Win32 (x86) Dynamic-Link Library") +!MESSAGE "osgtgz - Win32 Debug" (based on "Win32 (x86) Dynamic-Link Library") +!MESSAGE + +# Begin Project +# PROP AllowPerConfigDependencies 0 +# PROP Scc_ProjName "" +# PROP Scc_LocalPath "" +CPP=cl.exe +MTL=midl.exe +RSC=rc.exe + +!IF "$(CFG)" == "osgtgz - Win32 Release" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 0 +# PROP BASE Output_Dir "Release" +# PROP BASE Intermediate_Dir "Release" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 0 +# PROP Output_Dir "../../../lib" +# PROP Intermediate_Dir "Release" +# PROP Ignore_Export_Lib 0 +# PROP Target_Dir "" +# ADD BASE CPP /nologo /MT /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "osgtgz_EXPORTS" /YX /FD /c +# ADD CPP /nologo /MD /W3 /GR /GX /O2 /I "../../../include" /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "osgtgz_EXPORTS" /YX /FD /c +# ADD BASE MTL /nologo /D "NDEBUG" /mktyplib203 /win32 +# ADD MTL /nologo /D "NDEBUG" /mktyplib203 /win32 +# ADD BASE RSC /l 0x809 /d "NDEBUG" +# ADD RSC /l 0x809 /d "NDEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LINK32=link.exe +# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 +# ADD LINK32 osgDB.lib osg.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 /nodefaultlib:"LIBC" /out:"../../../bin/osgdb_osgtgz.dll" /libpath:"../../../lib" +# SUBTRACT LINK32 /nodefaultlib + +!ELSEIF "$(CFG)" == "osgtgz - Win32 Debug" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 1 +# PROP BASE Output_Dir "Debug" +# PROP BASE Intermediate_Dir "Debug" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 1 +# PROP Output_Dir "../../../lib" +# PROP Intermediate_Dir "Debug" +# PROP Ignore_Export_Lib 0 +# PROP Target_Dir "" +# ADD BASE CPP /nologo /MTd /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "osgtgz_EXPORTS" /YX /FD /GZ /c +# ADD CPP /nologo /MDd /W3 /Gm /vmg /vd0 /GR /GX /ZI /Od /I "../../../include" /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "OSGTGZ_EXPORTS" /YX /FD /GZ /c +# ADD BASE MTL /nologo /D "_DEBUG" /mktyplib203 /win32 +# ADD MTL /nologo /D "_DEBUG" /mktyplib203 /win32 +# ADD BASE RSC /l 0x809 /d "_DEBUG" +# ADD RSC /l 0x809 /d "_DEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LINK32=link.exe +# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /pdbtype:sept +# ADD LINK32 osgd.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /nodefaultlib:"LIBC" /out:"../../../bin/osgdb_osgtgzd.dll" /pdbtype:sept /libpath:"../../../lib" +# SUBTRACT LINK32 /nodefaultlib + +!ENDIF + +# Begin Target + +# Name "osgtgz - Win32 Release" +# Name "osgtgz - Win32 Debug" +# Begin Group "Source Files" + +# PROP Default_Filter "cpp;c;cxx;rc;def;r;odl;idl;hpj;bat" +# Begin Source File + +SOURCE=..\..\..\src\osgPlugins\osgtgz\ReaderWriterOSGTGZ.cpp +# End Source File +# End Group +# Begin Group "Header Files" + +# PROP Default_Filter "h;hpp;hxx;hm;inl" +# End Group +# Begin Group "Resource Files" + +# PROP Default_Filter "ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe" +# End Group +# End Target +# End Project diff --git a/VisualStudio/osgPlugins/pic/pic.dsp b/VisualStudio/osgPlugins/pic/pic.dsp index cea44abcf..b7bf5b3ee 100755 --- a/VisualStudio/osgPlugins/pic/pic.dsp +++ b/VisualStudio/osgPlugins/pic/pic.dsp @@ -43,7 +43,7 @@ RSC=rc.exe # PROP Ignore_Export_Lib 0 # PROP Target_Dir "" # ADD BASE CPP /nologo /MT /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "pic_EXPORTS" /YX /FD /c -# ADD CPP /nologo /MT /W3 /GR /GX /O2 /I "../../../include" /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "pic_EXPORTS" /YX /FD /c +# ADD CPP /nologo /MD /W3 /GR /GX /O2 /I "../../../include" /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "pic_EXPORTS" /YX /FD /c # ADD BASE MTL /nologo /D "NDEBUG" /mktyplib203 /win32 # ADD MTL /nologo /D "NDEBUG" /mktyplib203 /win32 # ADD BASE RSC /l 0x809 /d "NDEBUG" @@ -53,7 +53,7 @@ BSC32=bscmake.exe # ADD BSC32 /nologo LINK32=link.exe # ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 -# ADD LINK32 osg.lib /NODEFAULTLIB:LIBC kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 /out:"../../../bin/osgdb_pic.dll" /libpath:"../../../lib" +# ADD LINK32 osgDB.lib osg.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 /nodefaultlib:"LIBC" /out:"../../../bin/osgdb_pic.dll" /libpath:"../../../lib" # SUBTRACT LINK32 /nodefaultlib !ELSEIF "$(CFG)" == "pic - Win32 Debug" @@ -70,7 +70,7 @@ LINK32=link.exe # PROP Ignore_Export_Lib 0 # PROP Target_Dir "" # ADD BASE CPP /nologo /MTd /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "pic_EXPORTS" /YX /FD /GZ /c -# ADD CPP /nologo /MTd /W3 /Gm /vmg /vd0 /GR /GX /ZI /Od /I "../../../include" /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "PIC_EXPORTS" /YX /FD /GZ /c +# ADD CPP /nologo /MDd /W3 /Gm /vmg /vd0 /GR /GX /ZI /Od /I "../../../include" /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "PIC_EXPORTS" /YX /FD /GZ /c # ADD BASE MTL /nologo /D "_DEBUG" /mktyplib203 /win32 # ADD MTL /nologo /D "_DEBUG" /mktyplib203 /win32 # ADD BASE RSC /l 0x809 /d "_DEBUG" @@ -80,7 +80,7 @@ BSC32=bscmake.exe # ADD BSC32 /nologo LINK32=link.exe # ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /pdbtype:sept -# ADD LINK32 osgd.lib /NODEFAULTLIB:LIBC kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /out:"../../../bin/osgdb_picd.dll" /pdbtype:sept /libpath:"../../../lib" +# ADD LINK32 osgd.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /nodefaultlib:"LIBC" /out:"../../../bin/osgdb_picd.dll" /pdbtype:sept /libpath:"../../../lib" # SUBTRACT LINK32 /nodefaultlib !ENDIF diff --git a/VisualStudio/osgPlugins/png/png.dsp b/VisualStudio/osgPlugins/png/png.dsp index 27e0a3ecf..e83ff17ce 100755 --- a/VisualStudio/osgPlugins/png/png.dsp +++ b/VisualStudio/osgPlugins/png/png.dsp @@ -43,7 +43,7 @@ RSC=rc.exe # PROP Ignore_Export_Lib 0 # PROP Target_Dir "" # ADD BASE CPP /nologo /MT /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "png_EXPORTS" /YX /FD /c -# ADD CPP /nologo /MT /W3 /GR /GX /O2 /I "../../../include" /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "png_EXPORTS" /YX /FD /c +# ADD CPP /nologo /MD /W3 /GR /GX /O2 /I "../../../include" /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "png_EXPORTS" /YX /FD /c # ADD BASE MTL /nologo /D "NDEBUG" /mktyplib203 /win32 # ADD MTL /nologo /D "NDEBUG" /mktyplib203 /win32 # ADD BASE RSC /l 0x809 /d "NDEBUG" @@ -53,7 +53,7 @@ BSC32=bscmake.exe # ADD BSC32 /nologo LINK32=link.exe # ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 -# ADD LINK32 osg.lib /NODEFAULTLIB:LIBC libpng.lib zlibstat.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 /out:"../../../bin/osgdb_png.dll" /libpath:"../../../lib" +# ADD LINK32 osgDB.lib osg.lib libpng.lib zlibstat.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 /nodefaultlib:"LIBC" /out:"../../../bin/osgdb_png.dll" /libpath:"../../../lib" # SUBTRACT LINK32 /nodefaultlib !ELSEIF "$(CFG)" == "png - Win32 Debug" @@ -70,7 +70,7 @@ LINK32=link.exe # PROP Ignore_Export_Lib 0 # PROP Target_Dir "" # ADD BASE CPP /nologo /MTd /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "png_EXPORTS" /YX /FD /GZ /c -# ADD CPP /nologo /MTd /W3 /Gm /vmg /vd0 /GR /GX /ZI /Od /I "../../../include" /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "PNG_EXPORTS" /YX /FD /GZ /c +# ADD CPP /nologo /MDd /W3 /Gm /vmg /vd0 /GR /GX /ZI /Od /I "../../../include" /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "PNG_EXPORTS" /YX /FD /GZ /c # ADD BASE MTL /nologo /D "_DEBUG" /mktyplib203 /win32 # ADD MTL /nologo /D "_DEBUG" /mktyplib203 /win32 # ADD BASE RSC /l 0x809 /d "_DEBUG" @@ -80,7 +80,7 @@ BSC32=bscmake.exe # ADD BSC32 /nologo LINK32=link.exe # ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /pdbtype:sept -# ADD LINK32 osgd.lib /NODEFAULTLIB:LIBC libpng.lib zlibstat.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /out:"../../../bin/osgdb_pngd.dll" /pdbtype:sept /libpath:"../../../lib" +# ADD LINK32 osgd.lib libpng.lib zlibstat.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /nodefaultlib:"LIBC" /out:"../../../bin/osgdb_pngd.dll" /pdbtype:sept /libpath:"../../../lib" # SUBTRACT LINK32 /nodefaultlib !ENDIF diff --git a/VisualStudio/osgPlugins/rgb/rgb.dsp b/VisualStudio/osgPlugins/rgb/rgb.dsp new file mode 100644 index 000000000..a43b93bae --- /dev/null +++ b/VisualStudio/osgPlugins/rgb/rgb.dsp @@ -0,0 +1,109 @@ +# Microsoft Developer Studio Project File - Name="rgb" - Package Owner=<4> +# Microsoft Developer Studio Generated Build File, Format Version 6.00 +# ** DO NOT EDIT ** + +# TARGTYPE "Win32 (x86) Dynamic-Link Library" 0x0102 + +CFG=rgb - Win32 Debug +!MESSAGE This is not a valid makefile. To build this project using NMAKE, +!MESSAGE use the Export Makefile command and run +!MESSAGE +!MESSAGE NMAKE /f "rgb.mak". +!MESSAGE +!MESSAGE You can specify a configuration when running NMAKE +!MESSAGE by defining the macro CFG on the command line. For example: +!MESSAGE +!MESSAGE NMAKE /f "rgb.mak" CFG="rgb - Win32 Debug" +!MESSAGE +!MESSAGE Possible choices for configuration are: +!MESSAGE +!MESSAGE "rgb - Win32 Release" (based on "Win32 (x86) Dynamic-Link Library") +!MESSAGE "rgb - Win32 Debug" (based on "Win32 (x86) Dynamic-Link Library") +!MESSAGE + +# Begin Project +# PROP AllowPerConfigDependencies 0 +# PROP Scc_ProjName "" +# PROP Scc_LocalPath "" +CPP=cl.exe +MTL=midl.exe +RSC=rc.exe + +!IF "$(CFG)" == "rgb - Win32 Release" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 0 +# PROP BASE Output_Dir "Release" +# PROP BASE Intermediate_Dir "Release" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 0 +# PROP Output_Dir "../../../lib" +# PROP Intermediate_Dir "Release" +# PROP Ignore_Export_Lib 0 +# PROP Target_Dir "" +# ADD BASE CPP /nologo /MT /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "rgb_EXPORTS" /YX /FD /c +# ADD CPP /nologo /MD /W3 /GR /GX /O2 /I "../../../include" /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "rgb_EXPORTS" /YX /FD /c +# ADD BASE MTL /nologo /D "NDEBUG" /mktyplib203 /win32 +# ADD MTL /nologo /D "NDEBUG" /mktyplib203 /win32 +# ADD BASE RSC /l 0x809 /d "NDEBUG" +# ADD RSC /l 0x809 /d "NDEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LINK32=link.exe +# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 +# ADD LINK32 osgDB.lib osg.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 /nodefaultlib:"LIBC" /out:"../../../bin/osgdb_rgb.dll" /libpath:"../../../lib" +# SUBTRACT LINK32 /nodefaultlib + +!ELSEIF "$(CFG)" == "rgb - Win32 Debug" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 1 +# PROP BASE Output_Dir "Debug" +# PROP BASE Intermediate_Dir "Debug" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 1 +# PROP Output_Dir "../../../lib" +# PROP Intermediate_Dir "Debug" +# PROP Ignore_Export_Lib 0 +# PROP Target_Dir "" +# ADD BASE CPP /nologo /MTd /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "rgb_EXPORTS" /YX /FD /GZ /c +# ADD CPP /nologo /MDd /W3 /Gm /vmg /vd0 /GR /GX /ZI /Od /I "../../../include" /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "RGB_EXPORTS" /YX /FD /GZ /c +# ADD BASE MTL /nologo /D "_DEBUG" /mktyplib203 /win32 +# ADD MTL /nologo /D "_DEBUG" /mktyplib203 /win32 +# ADD BASE RSC /l 0x809 /d "_DEBUG" +# ADD RSC /l 0x809 /d "_DEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LINK32=link.exe +# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /pdbtype:sept +# ADD LINK32 osgd.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /nodefaultlib:"LIBC" /out:"../../../bin/osgdb_rgbd.dll" /pdbtype:sept /libpath:"../../../lib" +# SUBTRACT LINK32 /nodefaultlib + +!ENDIF + +# Begin Target + +# Name "rgb - Win32 Release" +# Name "rgb - Win32 Debug" +# Begin Group "Source Files" + +# PROP Default_Filter "cpp;c;cxx;rc;def;r;odl;idl;hpj;bat" +# Begin Source File + +SOURCE=..\..\..\src\osgPlugins\rgb\ReaderWriterRGB.cpp +# End Source File +# End Group +# Begin Group "Header Files" + +# PROP Default_Filter "h;hpp;hxx;hm;inl" +# End Group +# Begin Group "Resource Files" + +# PROP Default_Filter "ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe" +# End Group +# End Target +# End Project diff --git a/VisualStudio/osgPlugins/tga/tga.dsp b/VisualStudio/osgPlugins/tga/tga.dsp index cb6730775..b1de8e20d 100755 --- a/VisualStudio/osgPlugins/tga/tga.dsp +++ b/VisualStudio/osgPlugins/tga/tga.dsp @@ -43,7 +43,7 @@ RSC=rc.exe # PROP Ignore_Export_Lib 0 # PROP Target_Dir "" # ADD BASE CPP /nologo /MT /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "tga_EXPORTS" /YX /FD /c -# ADD CPP /nologo /MT /W3 /GR /GX /O2 /I "../../../include" /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "tga_EXPORTS" /YX /FD /c +# ADD CPP /nologo /MD /W3 /GR /GX /O2 /I "../../../include" /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "tga_EXPORTS" /YX /FD /c # ADD BASE MTL /nologo /D "NDEBUG" /mktyplib203 /win32 # ADD MTL /nologo /D "NDEBUG" /mktyplib203 /win32 # ADD BASE RSC /l 0x809 /d "NDEBUG" @@ -53,7 +53,7 @@ BSC32=bscmake.exe # ADD BSC32 /nologo LINK32=link.exe # ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 -# ADD LINK32 osg.lib /NODEFAULTLIB:LIBC kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 /out:"../../../bin/osgdb_tga.dll" /libpath:"../../../lib" +# ADD LINK32 osgDB.lib osg.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 /nodefaultlib:"LIBC" /out:"../../../bin/osgdb_tga.dll" /libpath:"../../../lib" # SUBTRACT LINK32 /nodefaultlib !ELSEIF "$(CFG)" == "tga - Win32 Debug" @@ -70,7 +70,7 @@ LINK32=link.exe # PROP Ignore_Export_Lib 0 # PROP Target_Dir "" # ADD BASE CPP /nologo /MTd /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "tga_EXPORTS" /YX /FD /GZ /c -# ADD CPP /nologo /MTd /W3 /Gm /vmg /vd0 /GR /GX /ZI /Od /I "../../../include" /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "TGA_EXPORTS" /YX /FD /GZ /c +# ADD CPP /nologo /MDd /W3 /Gm /vmg /vd0 /GR /GX /ZI /Od /I "../../../include" /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "TGA_EXPORTS" /YX /FD /GZ /c # ADD BASE MTL /nologo /D "_DEBUG" /mktyplib203 /win32 # ADD MTL /nologo /D "_DEBUG" /mktyplib203 /win32 # ADD BASE RSC /l 0x809 /d "_DEBUG" @@ -80,7 +80,7 @@ BSC32=bscmake.exe # ADD BSC32 /nologo LINK32=link.exe # ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /pdbtype:sept -# ADD LINK32 osgd.lib /NODEFAULTLIB:LIBC kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /out:"../../../bin/osgdb_tgad.dll" /pdbtype:sept /libpath:"../../../lib" +# ADD LINK32 osgd.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /nodefaultlib:"LIBC" /out:"../../../bin/osgdb_tgad.dll" /pdbtype:sept /libpath:"../../../lib" # SUBTRACT LINK32 /nodefaultlib !ENDIF diff --git a/VisualStudio/osgPlugins/tgz/tgz.dsp b/VisualStudio/osgPlugins/tgz/tgz.dsp new file mode 100644 index 000000000..064397e47 --- /dev/null +++ b/VisualStudio/osgPlugins/tgz/tgz.dsp @@ -0,0 +1,109 @@ +# Microsoft Developer Studio Project File - Name="tgz" - Package Owner=<4> +# Microsoft Developer Studio Generated Build File, Format Version 6.00 +# ** DO NOT EDIT ** + +# TARGTYPE "Win32 (x86) Dynamic-Link Library" 0x0102 + +CFG=tgz - Win32 Debug +!MESSAGE This is not a valid makefile. To build this project using NMAKE, +!MESSAGE use the Export Makefile command and run +!MESSAGE +!MESSAGE NMAKE /f "tgz.mak". +!MESSAGE +!MESSAGE You can specify a configuration when running NMAKE +!MESSAGE by defining the macro CFG on the command line. For example: +!MESSAGE +!MESSAGE NMAKE /f "tgz.mak" CFG="tgz - Win32 Debug" +!MESSAGE +!MESSAGE Possible choices for configuration are: +!MESSAGE +!MESSAGE "tgz - Win32 Release" (based on "Win32 (x86) Dynamic-Link Library") +!MESSAGE "tgz - Win32 Debug" (based on "Win32 (x86) Dynamic-Link Library") +!MESSAGE + +# Begin Project +# PROP AllowPerConfigDependencies 0 +# PROP Scc_ProjName "" +# PROP Scc_LocalPath "" +CPP=cl.exe +MTL=midl.exe +RSC=rc.exe + +!IF "$(CFG)" == "tgz - Win32 Release" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 0 +# PROP BASE Output_Dir "Release" +# PROP BASE Intermediate_Dir "Release" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 0 +# PROP Output_Dir "../../../lib" +# PROP Intermediate_Dir "Release" +# PROP Ignore_Export_Lib 0 +# PROP Target_Dir "" +# ADD BASE CPP /nologo /MT /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "tgz_EXPORTS" /YX /FD /c +# ADD CPP /nologo /MD /W3 /GR /GX /O2 /I "../../../include" /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "tgz_EXPORTS" /YX /FD /c +# ADD BASE MTL /nologo /D "NDEBUG" /mktyplib203 /win32 +# ADD MTL /nologo /D "NDEBUG" /mktyplib203 /win32 +# ADD BASE RSC /l 0x809 /d "NDEBUG" +# ADD RSC /l 0x809 /d "NDEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LINK32=link.exe +# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 +# ADD LINK32 osgDB.lib osg.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 /nodefaultlib:"LIBC" /out:"../../../bin/osgdb_tgz.dll" /libpath:"../../../lib" +# SUBTRACT LINK32 /nodefaultlib + +!ELSEIF "$(CFG)" == "tgz - Win32 Debug" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 1 +# PROP BASE Output_Dir "Debug" +# PROP BASE Intermediate_Dir "Debug" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 1 +# PROP Output_Dir "../../../lib" +# PROP Intermediate_Dir "Debug" +# PROP Ignore_Export_Lib 0 +# PROP Target_Dir "" +# ADD BASE CPP /nologo /MTd /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "tgz_EXPORTS" /YX /FD /GZ /c +# ADD CPP /nologo /MDd /W3 /Gm /vmg /vd0 /GR /GX /ZI /Od /I "../../../include" /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "TGZ_EXPORTS" /YX /FD /GZ /c +# ADD BASE MTL /nologo /D "_DEBUG" /mktyplib203 /win32 +# ADD MTL /nologo /D "_DEBUG" /mktyplib203 /win32 +# ADD BASE RSC /l 0x809 /d "_DEBUG" +# ADD RSC /l 0x809 /d "_DEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LINK32=link.exe +# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /pdbtype:sept +# ADD LINK32 osgd.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /nodefaultlib:"LIBC" /out:"../../../bin/osgdb_tgzd.dll" /pdbtype:sept /libpath:"../../../lib" +# SUBTRACT LINK32 /nodefaultlib + +!ENDIF + +# Begin Target + +# Name "tgz - Win32 Release" +# Name "tgz - Win32 Debug" +# Begin Group "Source Files" + +# PROP Default_Filter "cpp;c;cxx;rc;def;r;odl;idl;hpj;bat" +# Begin Source File + +SOURCE=..\..\..\src\osgPlugins\tgz\ReaderWriterTGZ.cpp +# End Source File +# End Group +# Begin Group "Header Files" + +# PROP Default_Filter "h;hpp;hxx;hm;inl" +# End Group +# Begin Group "Resource Files" + +# PROP Default_Filter "ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe" +# End Group +# End Target +# End Project diff --git a/VisualStudio/osgPlugins/tiff/tiff.dsp b/VisualStudio/osgPlugins/tiff/tiff.dsp index d0cb831ea..2debeb354 100755 --- a/VisualStudio/osgPlugins/tiff/tiff.dsp +++ b/VisualStudio/osgPlugins/tiff/tiff.dsp @@ -43,7 +43,7 @@ RSC=rc.exe # PROP Ignore_Export_Lib 0 # PROP Target_Dir "" # ADD BASE CPP /nologo /MT /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "tiff_EXPORTS" /YX /FD /c -# ADD CPP /nologo /MT /W3 /GR /GX /O2 /I "../../../include" /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "tiff_EXPORTS" /YX /FD /c +# ADD CPP /nologo /MD /W3 /GR /GX /O2 /I "../../../include" /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "tiff_EXPORTS" /YX /FD /c # ADD BASE MTL /nologo /D "NDEBUG" /mktyplib203 /win32 # ADD MTL /nologo /D "NDEBUG" /mktyplib203 /win32 # ADD BASE RSC /l 0x809 /d "NDEBUG" @@ -53,7 +53,7 @@ BSC32=bscmake.exe # ADD BSC32 /nologo LINK32=link.exe # ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 -# ADD LINK32 osg.lib /NODEFAULTLIB:LIBC tiff.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 /out:"../../../bin/osgdb_tiff.dll" /libpath:"../../../lib" +# ADD LINK32 osgDB.lib osg.lib libtiff.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 /nodefaultlib:"LIBC" /out:"../../../bin/osgdb_tiff.dll" /libpath:"../../../lib" # SUBTRACT LINK32 /nodefaultlib !ELSEIF "$(CFG)" == "tiff - Win32 Debug" @@ -70,7 +70,7 @@ LINK32=link.exe # PROP Ignore_Export_Lib 0 # PROP Target_Dir "" # ADD BASE CPP /nologo /MTd /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "tiff_EXPORTS" /YX /FD /GZ /c -# ADD CPP /nologo /MTd /W3 /Gm /vmg /vd0 /GR /GX /ZI /Od /I "../../../include" /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "TIFF_EXPORTS" /YX /FD /GZ /c +# ADD CPP /nologo /MDd /W3 /Gm /vmg /vd0 /GR /GX /ZI /Od /I "../../../include" /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "TIFF_EXPORTS" /YX /FD /GZ /c # ADD BASE MTL /nologo /D "_DEBUG" /mktyplib203 /win32 # ADD MTL /nologo /D "_DEBUG" /mktyplib203 /win32 # ADD BASE RSC /l 0x809 /d "_DEBUG" @@ -80,8 +80,8 @@ BSC32=bscmake.exe # ADD BSC32 /nologo LINK32=link.exe # ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /pdbtype:sept -# ADD LINK32 osgd.lib /NODEFAULTLIB:LIBC tiff.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /out:"../../../bin/osgdb_tiffd.dll" /pdbtype:sept /libpath:"../../../lib" -# SUBTRACT LINK32 /nodefaultlib +# ADD LINK32 osgDBd.lib osgd.lib libtiff.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /nodefaultlib:"LIBC" /out:"../../../bin/osgdb_tiffd.dll" /pdbtype:sept /libpath:"../../../lib" +# SUBTRACT LINK32 /pdb:none !ENDIF diff --git a/VisualStudio/osgPlugins/zip/zip.dsp b/VisualStudio/osgPlugins/zip/zip.dsp new file mode 100644 index 000000000..13f728141 --- /dev/null +++ b/VisualStudio/osgPlugins/zip/zip.dsp @@ -0,0 +1,109 @@ +# Microsoft Developer Studio Project File - Name="zip" - Package Owner=<4> +# Microsoft Developer Studio Generated Build File, Format Version 6.00 +# ** DO NOT EDIT ** + +# TARGTYPE "Win32 (x86) Dynamic-Link Library" 0x0102 + +CFG=zip - Win32 Debug +!MESSAGE This is not a valid makefile. To build this project using NMAKE, +!MESSAGE use the Export Makefile command and run +!MESSAGE +!MESSAGE NMAKE /f "zip.mak". +!MESSAGE +!MESSAGE You can specify a configuration when running NMAKE +!MESSAGE by defining the macro CFG on the command line. For example: +!MESSAGE +!MESSAGE NMAKE /f "zip.mak" CFG="zip - Win32 Debug" +!MESSAGE +!MESSAGE Possible choices for configuration are: +!MESSAGE +!MESSAGE "zip - Win32 Release" (based on "Win32 (x86) Dynamic-Link Library") +!MESSAGE "zip - Win32 Debug" (based on "Win32 (x86) Dynamic-Link Library") +!MESSAGE + +# Begin Project +# PROP AllowPerConfigDependencies 0 +# PROP Scc_ProjName "" +# PROP Scc_LocalPath "" +CPP=cl.exe +MTL=midl.exe +RSC=rc.exe + +!IF "$(CFG)" == "zip - Win32 Release" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 0 +# PROP BASE Output_Dir "Release" +# PROP BASE Intermediate_Dir "Release" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 0 +# PROP Output_Dir "../../../lib" +# PROP Intermediate_Dir "Release" +# PROP Ignore_Export_Lib 0 +# PROP Target_Dir "" +# ADD BASE CPP /nologo /MT /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "zip_EXPORTS" /YX /FD /c +# ADD CPP /nologo /MD /W3 /GR /GX /O2 /I "../../../include" /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "zip_EXPORTS" /YX /FD /c +# ADD BASE MTL /nologo /D "NDEBUG" /mktyplib203 /win32 +# ADD MTL /nologo /D "NDEBUG" /mktyplib203 /win32 +# ADD BASE RSC /l 0x809 /d "NDEBUG" +# ADD RSC /l 0x809 /d "NDEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LINK32=link.exe +# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 +# ADD LINK32 osgDB.lib osg.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 /nodefaultlib:"LIBC" /out:"../../../bin/osgdb_zip.dll" /libpath:"../../../lib" +# SUBTRACT LINK32 /nodefaultlib + +!ELSEIF "$(CFG)" == "zip - Win32 Debug" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 1 +# PROP BASE Output_Dir "Debug" +# PROP BASE Intermediate_Dir "Debug" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 1 +# PROP Output_Dir "../../../lib" +# PROP Intermediate_Dir "Debug" +# PROP Ignore_Export_Lib 0 +# PROP Target_Dir "" +# ADD BASE CPP /nologo /MTd /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "zip_EXPORTS" /YX /FD /GZ /c +# ADD CPP /nologo /MDd /W3 /Gm /vmg /vd0 /GR /GX /ZI /Od /I "../../../include" /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "ZIP_EXPORTS" /YX /FD /GZ /c +# ADD BASE MTL /nologo /D "_DEBUG" /mktyplib203 /win32 +# ADD MTL /nologo /D "_DEBUG" /mktyplib203 /win32 +# ADD BASE RSC /l 0x809 /d "_DEBUG" +# ADD RSC /l 0x809 /d "_DEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LINK32=link.exe +# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /pdbtype:sept +# ADD LINK32 osgd.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /nodefaultlib:"LIBC" /out:"../../../bin/osgdb_zipd.dll" /pdbtype:sept /libpath:"../../../lib" +# SUBTRACT LINK32 /nodefaultlib + +!ENDIF + +# Begin Target + +# Name "zip - Win32 Release" +# Name "zip - Win32 Debug" +# Begin Group "Source Files" + +# PROP Default_Filter "cpp;c;cxx;rc;def;r;odl;idl;hpj;bat" +# Begin Source File + +SOURCE=..\..\..\src\osgPlugins\zip\ReaderWriterZIP.cpp +# End Source File +# End Group +# Begin Group "Header Files" + +# PROP Default_Filter "h;hpp;hxx;hm;inl" +# End Group +# Begin Group "Resource Files" + +# PROP Default_Filter "ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe" +# End Group +# End Target +# End Project diff --git a/VisualStudio/osgUtil/osgUtil.dsp b/VisualStudio/osgUtil/osgUtil.dsp index fa80b88ac..07494791f 100755 --- a/VisualStudio/osgUtil/osgUtil.dsp +++ b/VisualStudio/osgUtil/osgUtil.dsp @@ -43,7 +43,7 @@ RSC=rc.exe # PROP Ignore_Export_Lib 0 # PROP Target_Dir "" # ADD BASE CPP /nologo /MT /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "LIBOSGUTIL_EXPORTS" /YX /FD /c -# ADD CPP /nologo /MT /W3 /vd1 /GR /GX /O2 /I "../../include" /D "NDEBUG" /D "_MBCS" /D "_USRDLL" /D "LIBOSGUTIL_EXPORTS" /D "OSGUTIL_LIBRARY" /D "WIN32" /D "_WINDOWS" /YX /FD /c +# ADD CPP /nologo /MD /W3 /GR /GX /O2 /I "../../include" /D "NDEBUG" /D "_MBCS" /D "_USRDLL" /D "LIBOSGUTIL_EXPORTS" /D "OSGUTIL_LIBRARY" /D "WIN32" /D "_WINDOWS" /YX /FD /c # ADD BASE MTL /nologo /D "NDEBUG" /mktyplib203 /win32 # ADD MTL /nologo /D "NDEBUG" /mktyplib203 /win32 # ADD BASE RSC /l 0x809 /d "NDEBUG" @@ -70,7 +70,7 @@ LINK32=link.exe # PROP Ignore_Export_Lib 0 # PROP Target_Dir "" # ADD BASE CPP /nologo /MTd /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "LIBOSGUTIL_EXPORTS" /YX /FD /GZ /c -# ADD CPP /nologo /MTd /W3 /Gm /vmg /vd0 /GR /GX /ZI /Od /I "../../include" /D "_DEBUG" /D "OSGUTIL_LIBRARY" /D "WIN32" /D "_WINDOWS" /YX /FD /GZ /c +# ADD CPP /nologo /MDd /W3 /Gm /vmg /vd0 /GR /GX /ZI /Od /I "../../include" /D "_DEBUG" /D "OSGUTIL_LIBRARY" /D "WIN32" /D "_WINDOWS" /YX /FD /GZ /c # ADD BASE MTL /nologo /D "_DEBUG" /mktyplib203 /win32 # ADD MTL /nologo /D "_DEBUG" /mktyplib203 /win32 # ADD BASE RSC /l 0x809 /d "_DEBUG" @@ -94,11 +94,31 @@ LINK32=link.exe # PROP Default_Filter "cpp;c;cxx;rc;def;r;odl;idl;hpj;bat" # Begin Source File -SOURCE=..\..\Src\osgUtil\CameraManipulator.cpp +SOURCE=..\..\src\osgUtil\VisualsRequirementsVisitor.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\osgUtil\DisplayListVisitor.cpp +SOURCE=..\..\src\osgUtil\CameraManipulator.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\src\osgUtil\CullVisitor.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\src\osgUtil\CullViewState.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\src\osgUtil\DisplayListVisitor.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\src\osgUtil\DepthSortedBin.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\Src\osgUtil\StateSetManipulator.cpp # End Source File # Begin Source File @@ -110,23 +130,67 @@ SOURCE=..\..\src\osgUtil\FlightManipulator.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\osgUtil\IntersectVisitor.cpp +SOURCE=..\..\src\osgUtil\InsertImpostorsVisitor.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\osgUtil\RenderVisitor.cpp +SOURCE=..\..\src\osgUtil\IntersectVisitor.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\osgUtil\SceneView.cpp +SOURCE=..\..\src\osgUtil\NvTriStripObjects.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\osgUtil\Version.cpp +SOURCE=..\..\src\osgUtil\RenderBin.cpp # End Source File # Begin Source File -SOURCE=..\..\Src\osgUtil\TrackballManipulator.cpp +SOURCE=..\..\src\osgUtil\RenderLeaf.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\src\osgUtil\RenderGraph.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\src\osgUtil\RenderStage.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\src\osgUtil\RenderStageLighting.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\src\osgUtil\RenderToTextureStage.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\src\osgUtil\SceneView.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\src\osgUtil\SceneViewManipulator.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\src\osgUtil\SmoothingVisitor.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\src\osgUtil\TrackballManipulator.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\src\osgUtil\TriStripVisitor.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\src\osgUtil\Tesselator.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\src\osgUtil\Version.cpp # End Source File # End Group # Begin Group "Header Files" @@ -134,14 +198,34 @@ SOURCE=..\..\Src\osgUtil\TrackballManipulator.cpp # PROP Default_Filter ";h;hpp;hxx;hm;inl" # Begin Source File +SOURCE=..\..\Include\osgUtil\VisualsRequirementsVisitor +# End Source File +# Begin Source File + SOURCE=..\..\Include\osgUtil\CameraManipulator # End Source File # Begin Source File +SOURCE=..\..\Include\osgUtil\CullVisitor +# End Source File +# Begin Source File + +SOURCE=..\..\Include\osgUtil\CullViewState +# End Source File +# Begin Source File + SOURCE=..\..\Include\osgUtil\DisplayListVisitor # End Source File # Begin Source File +SOURCE=..\..\Include\osgUtil\DepthSortedBin +# End Source File +# Begin Source File + +SOURCE=..\..\Include\osgUtil\StateSetManipulator +# End Source File +# Begin Source File + SOURCE=..\..\include\osgUtil\DriveManipulator # End Source File # Begin Source File @@ -162,11 +246,43 @@ SOURCE=..\..\include\osgUtil\GUIEventAdapter # End Source File # Begin Source File +SOURCE=..\..\include\osgUtil\GUIEventHandler +# End Source File +# Begin Source File + SOURCE=..\..\Include\osgUtil\IntersectVisitor # End Source File # Begin Source File -SOURCE=..\..\Include\osgUtil\RenderVisitor +SOURCE=..\..\Include\osgUtil\InsertImpostorsVisitor +# End Source File +# Begin Source File + +SOURCE=..\..\src\osgUtil\NvTriStripObjects.h +# End Source File +# Begin Source File + +SOURCE=..\..\include\osgUtil\RenderBin +# End Source File +# Begin Source File + +SOURCE=..\..\include\osgUtil\RenderLeaf +# End Source File +# Begin Source File + +SOURCE=..\..\include\osgUtil\RenderGraph +# End Source File +# Begin Source File + +SOURCE=..\..\include\osgUtil\RenderStage +# End Source File +# Begin Source File + +SOURCE=..\..\include\osgUtil\RenderStageLighting +# End Source File +# Begin Source File + +SOURCE=..\..\include\osgUtil\RenderToTextureStage # End Source File # Begin Source File @@ -174,12 +290,32 @@ SOURCE=..\..\Include\osgUtil\SceneView # End Source File # Begin Source File -SOURCE=..\..\Include\osgUtil\Version +SOURCE=..\..\Include\osgUtil\SceneViewManipulator +# End Source File +# Begin Source File + +SOURCE=..\..\include\osgUtil\SmoothingVisitor +# End Source File +# Begin Source File + +SOURCE=..\..\include\osgUtil\Statistics +# End Source File +# Begin Source File + +SOURCE=..\..\include\osgUtil\Tesselator # End Source File # Begin Source File SOURCE=..\..\include\osgUtil\TrackballManipulator # End Source File +# Begin Source File + +SOURCE=..\..\include\osgUtil\TriStripVisitor +# End Source File +# Begin Source File + +SOURCE=..\..\Include\osgUtil\Version +# End Source File # End Group # Begin Group "Resource Files" diff --git a/VisualStudio/osgWX/osgWX.dsp b/VisualStudio/osgWX/osgWX.dsp new file mode 100644 index 000000000..e8904242b --- /dev/null +++ b/VisualStudio/osgWX/osgWX.dsp @@ -0,0 +1,125 @@ +# Microsoft Developer Studio Project File - Name="osgWX" - Package Owner=<4> +# Microsoft Developer Studio Generated Build File, Format Version 6.00 +# ** DO NOT EDIT ** + +# TARGTYPE "Win32 (x86) Dynamic-Link Library" 0x0102 + +CFG=osgWX - Win32 Debug +!MESSAGE This is not a valid makefile. To build this project using NMAKE, +!MESSAGE use the Export Makefile command and run +!MESSAGE +!MESSAGE NMAKE /f "osgWX.mak". +!MESSAGE +!MESSAGE You can specify a configuration when running NMAKE +!MESSAGE by defining the macro CFG on the command line. For example: +!MESSAGE +!MESSAGE NMAKE /f "osgWX.mak" CFG="osgWX - Win32 Debug" +!MESSAGE +!MESSAGE Possible choices for configuration are: +!MESSAGE +!MESSAGE "osgWX - Win32 Release" (based on "Win32 (x86) Dynamic-Link Library") +!MESSAGE "osgWX - Win32 Debug" (based on "Win32 (x86) Dynamic-Link Library") +!MESSAGE + +# Begin Project +# PROP AllowPerConfigDependencies 0 +# PROP Scc_ProjName "" +# PROP Scc_LocalPath "" +CPP=cl.exe +MTL=midl.exe +RSC=rc.exe + +!IF "$(CFG)" == "osgWX - Win32 Release" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 0 +# PROP BASE Output_Dir "../../lib" +# PROP BASE Intermediate_Dir "Release" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 0 +# PROP Output_Dir "../../lib" +# PROP Intermediate_Dir "Release" +# PROP Ignore_Export_Lib 0 +# PROP Target_Dir "" +# ADD BASE CPP /nologo /MT /W3 /GX /O2 /D "WIN32" /D "NDEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "LIBOSGWX_EXPORTS" /YX /FD /c +# ADD CPP /nologo /MD /W3 /GR /GX /O2 /I "../../include" /D "NDEBUG" /D "_MBCS" /D "_USRDLL" /D "LIBOSGWX_EXPORTS" /D "OSGWX_LIBRARY" /D "WIN32" /D "_WINDOWS" /D "__WXMSW__" /YX"wx/wxprec.h" /FD /c +# ADD BASE MTL /nologo /D "NDEBUG" /mktyplib203 /win32 +# ADD MTL /nologo /D "NDEBUG" /mktyplib203 /win32 +# ADD BASE RSC /l 0x809 /d "NDEBUG" +# ADD RSC /l 0x809 /d "NDEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LINK32=link.exe +# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /machine:I386 +# ADD LINK32 wx22_7.lib osgUtil.lib osgDB.lib osg.lib opengl32.lib glu32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /pdb:"../../bin/osgWX.pdb" /machine:I386 /out:"../../bin/osgWX.dll" /libpath:"../../lib" +# SUBTRACT LINK32 /pdb:none + +!ELSEIF "$(CFG)" == "osgWX - Win32 Debug" + +# PROP BASE Use_MFC 0 +# PROP BASE Use_Debug_Libraries 1 +# PROP BASE Output_Dir "Debug" +# PROP BASE Intermediate_Dir "Debug" +# PROP BASE Target_Dir "" +# PROP Use_MFC 0 +# PROP Use_Debug_Libraries 1 +# PROP Output_Dir "../../lib" +# PROP Intermediate_Dir "Debug" +# PROP Ignore_Export_Lib 0 +# PROP Target_Dir "" +# ADD BASE CPP /nologo /MTd /W3 /Gm /GX /ZI /Od /D "WIN32" /D "_DEBUG" /D "_WINDOWS" /D "_MBCS" /D "_USRDLL" /D "LIBOSGWX_EXPORTS" /YX /FD /GZ /c +# ADD CPP /nologo /MDd /W3 /Gm /vmg /vd0 /GR /GX /ZI /Od /I "../../include" /D "_DEBUG" /D "OSGWX_LIBRARY" /D "WIN32" /D "_WINDOWS" /D "__WXMSW__" /FR /YX"wx/wxprec.h" /FD /GZ /c +# ADD BASE MTL /nologo /D "_DEBUG" /mktyplib203 /win32 +# ADD MTL /nologo /D "_DEBUG" /mktyplib203 /win32 +# ADD BASE RSC /l 0x809 /d "_DEBUG" +# ADD RSC /l 0x809 /d "_DEBUG" +BSC32=bscmake.exe +# ADD BASE BSC32 /nologo +# ADD BSC32 /nologo +LINK32=link.exe +# ADD BASE LINK32 kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /debug /machine:I386 /pdbtype:sept +# ADD LINK32 wx22_7d.lib osgUtild.lib osgDBd.lib osgd.lib opengl32.lib glu32.lib kernel32.lib user32.lib gdi32.lib winspool.lib comdlg32.lib advapi32.lib shell32.lib ole32.lib oleaut32.lib uuid.lib odbc32.lib odbccp32.lib /nologo /dll /pdb:"../../bin/osgWXd.pdb" /debug /machine:I386 /out:"../../bin/osgWXd.dll" /pdbtype:sept /libpath:"../../lib" +# SUBTRACT LINK32 /pdb:none + +!ENDIF + +# Begin Target + +# Name "osgWX - Win32 Release" +# Name "osgWX - Win32 Debug" +# Begin Group "Source Files" + +# PROP Default_Filter "cpp;c;cxx;rc;def;r;odl;idl;hpj;bat" +# Begin Source File + +SOURCE=..\..\Src\osgWX\Version.cpp +# End Source File +# Begin Source File + +SOURCE=..\..\src\osgWX\WXEventAdapter.cpp +# End Source File +# End Group +# Begin Group "Header Files" + +# PROP Default_Filter ";h;hpp;hxx;hm;inl" +# Begin Source File + +SOURCE=..\..\Include\osgWX\Export +# End Source File +# Begin Source File + +SOURCE=..\..\Include\osgWX\Version +# End Source File +# Begin Source File + +SOURCE=..\..\Include\osgWX\wxEventAdapter +# End Source File +# End Group +# Begin Group "Resource Files" + +# PROP Default_Filter "ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe" +# End Group +# End Target +# End Project diff --git a/dist/RedHatRPM/osg.spec b/dist/RedHatRPM/osg.spec index 79b8d2bee..c12790b05 100644 --- a/dist/RedHatRPM/osg.spec +++ b/dist/RedHatRPM/osg.spec @@ -1,11 +1,11 @@ Summary: Open Scene Graph Name: OpenSceneGraph -Version: 0.8 -Release: 2 -Copyright: GLPL +Version: 0.8.39 +Release: 1 +Copyright: LGPL Group: Graphics -Source: osg-0.8-2.tar.gz +Source: osg-0.8.39.tar.gz URL: http://www.openscenegraph.org Packager: Robert Osfield diff --git a/doc/Doxyfiles/all_Doxyfile b/doc/Doxyfiles/all_Doxyfile new file mode 100644 index 000000000..4b539d953 --- /dev/null +++ b/doc/Doxyfiles/all_Doxyfile @@ -0,0 +1,717 @@ +# Doxyfile 1.2.2 + +# ========================================================================== +# all_Doxyfile will generate doxygen HTML (only) documenation for all +# software in the distribution, including plug-ins. Assumptions: +# +# You have the 'dot' tool and it's on your path +# OSGHOME points to the root of your OSG tree on your filesystem +# +# ========================================================================== + +# This file describes the settings to be used by doxygen for a project +# +# All text after a hash (#) is considered a comment and will be ignored +# The format is: +# TAG = value [value, ...] +# For lists items can also be appended using: +# TAG += value [value, ...] +# Values that contain spaces should be placed between quotes (" ") + +#--------------------------------------------------------------------------- +# General configuration options +#--------------------------------------------------------------------------- + +# The PROJECT_NAME tag is a single word (or a sequence of words surrounded +# by quotes) that should identify the project. + +PROJECT_NAME = "Open Scene Graph, Utility Toolkit, and bundled Plug-ins" + +# The PROJECT_NUMBER tag can be used to enter a project or revision number. +# This could be handy for archiving the generated documentation or +# if some version control system is used. + +PROJECT_NUMBER = + +# The OUTPUT_DIRECTORY tag is used to specify the (relative or absolute) +# base path where the generated documentation will be put. +# If a relative path is entered, it will be relative to the location +# where doxygen was started. If left blank the current directory will be used. + +OUTPUT_DIRECTORY = $(OSGHOME)/doc/doxygen + +# The OUTPUT_LANGUAGE tag is used to specify the language in which all +# documentation generated by doxygen is written. Doxygen will use this +# information to generate all constant output in the proper language. +# The default language is English, other supported languages are: +# Dutch, French, Italian, Czech, Swedish, German, Finnish, Japanese, +# Korean, Hungarian, Spanish, Romanian, Russian, Croatian, Polish, and +# Portuguese. + +OUTPUT_LANGUAGE = English + +# If the EXTRACT_ALL tag is set to YES doxygen will assume all entities in +# documentation are documented, even if no documentation was available. +# Private class members and static file members will be hidden unless +# the EXTRACT_PRIVATE and EXTRACT_STATIC tags are set to YES + +EXTRACT_ALL = YES + +# If the EXTRACT_PRIVATE tag is set to YES all private members of a class +# will be included in the documentation. + +EXTRACT_PRIVATE = NO + +# If the EXTRACT_STATIC tag is set to YES all static members of a file +# will be included in the documentation. + +EXTRACT_STATIC = NO + +# If the HIDE_UNDOC_MEMBERS tag is set to YES, Doxygen will hide all +# undocumented members of documented classes, files or namespaces. +# If set to NO (the default) these members will be included in the +# various overviews, but no documentation section is generated. +# This option has no effect if EXTRACT_ALL is enabled. + +HIDE_UNDOC_MEMBERS = NO + +# If the HIDE_UNDOC_CLASSES tag is set to YES, Doxygen will hide all +# undocumented classes that are normally visible in the class hierarchy. +# If set to NO (the default) these class will be included in the various +# overviews. This option has no effect if EXTRACT_ALL is enabled. + +HIDE_UNDOC_CLASSES = NO + +# If the BRIEF_MEMBER_DESC tag is set to YES (the default) Doxygen will +# include brief member descriptions after the members that are listed in +# the file and class documentation (similar to JavaDoc). +# Set to NO to disable this. + +BRIEF_MEMBER_DESC = YES + +# If the REPEAT_BRIEF tag is set to YES (the default) Doxygen will prepend +# the brief description of a member or function before the detailed description. +# Note: if both HIDE_UNDOC_MEMBERS and BRIEF_MEMBER_DESC are set to NO, the +# brief descriptions will be completely suppressed. + +REPEAT_BRIEF = YES + +# If the ALWAYS_DETAILED_SEC and REPEAT_BRIEF tags are both set to YES then +# Doxygen will generate a detailed section even if there is only a brief +# description. + +ALWAYS_DETAILED_SEC = NO + +# If the FULL_PATH_NAMES tag is set to YES then Doxygen will prepend the full +# path before files name in the file list and in the header files. If set +# to NO the shortest path that makes the file name unique will be used. + +FULL_PATH_NAMES = NO + +# If the FULL_PATH_NAMES tag is set to YES then the STRIP_FROM_PATH tag +# can be used to strip a user defined part of the path. Stripping is +# only done if one of the specified strings matches the left-hand part of +# the path. It is allowed to use relative paths in the argument list. + +STRIP_FROM_PATH = + +# The INTERNAL_DOCS tag determines if documentation +# that is typed after a \internal command is included. If the tag is set +# to NO (the default) then the documentation will be excluded. +# Set it to YES to include the internal documentation. + +INTERNAL_DOCS = NO + +# If the CLASS_DIAGRAMS tag is set to YES (the default) Doxygen will +# generate a class diagram (in Html and LaTeX) for classes with base or +# super classes. Setting the tag to NO turns the diagrams off. + +CLASS_DIAGRAMS = YES + +# If the SOURCE_BROWSER tag is set to YES then a list of source files will +# be generated. Documented entities will be cross-referenced with these sources. + +SOURCE_BROWSER = NO + +# Setting the INLINE_SOURCES tag to YES will include the body +# of functions and classes directly in the documentation. + +INLINE_SOURCES = NO + +# Setting the STRIP_CODE_COMMENTS tag to YES (the default) will instruct +# doxygen to hide any special comment blocks from generated source code +# fragments. Normal C and C++ comments will always remain visible. + +STRIP_CODE_COMMENTS = YES + +# If the CASE_SENSE_NAMES tag is set to NO then Doxygen will only generate +# file names in lower case letters. If set to YES upper case letters are also +# allowed. This is useful if you have classes or files whose names only differ +# in case and if your file system supports case sensitive file names. Windows +# users are adviced to set this option to NO. + +CASE_SENSE_NAMES = YES + +# If the HIDE_SCOPE_NAMES tag is set to NO (the default) then Doxygen +# will show members with their full class and namespace scopes in the +# documentation. If set to YES the scope will be hidden. + +HIDE_SCOPE_NAMES = NO + +# If the VERBATIM_HEADERS tag is set to YES (the default) then Doxygen +# will generate a verbatim copy of the header file for each class for +# which an include is specified. Set to NO to disable this. + +VERBATIM_HEADERS = YES + +# If the SHOW_INCLUDE_FILES tag is set to YES (the default) then Doxygen +# will put list of the files that are included by a file in the documentation +# of that file. + +SHOW_INCLUDE_FILES = YES + +# If the JAVADOC_AUTOBRIEF tag is set to YES (the default) then Doxygen +# will interpret the first line (until the first dot) of a JavaDoc-style +# comment as the brief description. If set to NO, the Javadoc-style will +# behave just like the Qt-style comments. + +JAVADOC_AUTOBRIEF = YES + +# If the INHERIT_DOCS tag is set to YES (the default) then an undocumented +# member inherits the documentation from any documented member that it +# reimplements. + +INHERIT_DOCS = YES + +# If the INLINE_INFO tag is set to YES (the default) then a tag [inline] +# is inserted in the documentation for inline members. + +INLINE_INFO = YES + +# If the SORT_MEMBER_DOCS tag is set to YES (the default) then doxygen +# will sort the (detailed) documentation of file and class members +# alphabetically by member name. If set to NO the members will appear in +# declaration order. + +SORT_MEMBER_DOCS = YES + +# If member grouping is used in the documentation and the DISTRIBUTE_GROUP_DOC +# tag is set to YES, then doxygen will reuse the documentation of the first +# member in the group (if any) for the other members of the group. By default +# all members of a group must be documented explicitly. + +DISTRIBUTE_GROUP_DOC = NO + +# The TAB_SIZE tag can be used to set the number of spaces in a tab. +# Doxygen uses this value to replace tabs by spaces in code fragments. + +TAB_SIZE = 8 + +# The ENABLE_SECTIONS tag can be used to enable conditional +# documentation sections, marked by \if sectionname ... \endif. + +ENABLED_SECTIONS = + +# The GENERATE_TODOLIST tag can be used to enable (YES) or +# disable (NO) the todo list. This list is created by putting \todo +# commands in the documentation. + +GENERATE_TODOLIST = YES + +# The GENERATE_TESTLIST tag can be used to enable (YES) or +# disable (NO) the test list. This list is created by putting \test +# commands in the documentation. + +GENERATE_TESTLIST = YES + +# This tag can be used to specify a number of aliases that acts +# as commands in the documentation. An alias has the form "name=value". +# For example adding "sideeffect=\par Side Effects:\n" will allow you to +# put the command \sideeffect (or @sideeffect) in the documentation, which +# will result in a user defined paragraph with heading "Side Effects:". +# You can put \n's in the value part of an alias to insert newlines. + +ALIASES = + +#--------------------------------------------------------------------------- +# configuration options related to warning and progress messages +#--------------------------------------------------------------------------- + +# The QUIET tag can be used to turn on/off the messages that are generated +# by doxygen. Possible values are YES and NO. If left blank NO is used. + +QUIET = NO + +# The WARNINGS tag can be used to turn on/off the warning messages that are +# generated by doxygen. Possible values are YES and NO. If left blank +# NO is used. + +WARNINGS = YES + +# If WARN_IF_UNDOCUMENTED is set to YES, then doxygen will generate warnings +# for undocumented members. If EXTRACT_ALL is set to YES then this flag will +# automatically be disabled. + +WARN_IF_UNDOCUMENTED = YES + +# The WARN_FORMAT tag determines the format of the warning messages that +# doxygen can produce. The string should contain the $file, $line, and $text +# tags, which will be replaced by the file and line number from which the +# warning originated and the warning text. + +WARN_FORMAT = "$file:$line: $text" + +#--------------------------------------------------------------------------- +# configuration options related to the input files +#--------------------------------------------------------------------------- + +# The INPUT tag can be used to specify the files and/or directories that contain +# documented source files. You may enter file names like "myfile.cpp" or +# directories like "/usr/src/myproject". Separate the files or directories +# with spaces. + +INPUT = $(OSGHOME) + +# If the value of the INPUT tag contains directories, you can use the +# FILE_PATTERNS tag to specify one or more wildcard pattern (like *.cpp +# and *.h) to filter out the source-files in the directories. If left +# blank all files are included. + +FILE_PATTERNS = */include/* *.h */src/*/*.cpp + +# The RECURSIVE tag can be used to turn specify whether or not subdirectories +# should be searched for input files as well. Possible values are YES and NO. +# If left blank NO is used. + +RECURSIVE = YES + +# The EXCLUDE tag can be used to specify files and/or directories that should +# excluded from the INPUT source files. This way you can easily exclude a +# subdirectory from a directory tree whose root is specified with the INPUT tag. + +EXCLUDE = + +# If the value of the INPUT tag contains directories, you can use the +# EXCLUDE_PATTERNS tag to specify one or more wildcard patterns to exclude +# certain files from those directories. + +EXCLUDE_PATTERNS = + +# The EXAMPLE_PATH tag can be used to specify one or more files or +# directories that contain example code fragments that are included (see +# the \include command). + +EXAMPLE_PATH = + +# If the value of the EXAMPLE_PATH tag contains directories, you can use the +# EXAMPLE_PATTERNS tag to specify one or more wildcard pattern (like *.cpp +# and *.h) to filter out the source-files in the directories. If left +# blank all files are included. + +EXAMPLE_PATTERNS = + +# The IMAGE_PATH tag can be used to specify one or more files or +# directories that contain image that are included in the documentation (see +# the \image command). + +IMAGE_PATH = + +# The INPUT_FILTER tag can be used to specify a program that doxygen should +# invoke to filter for each input file. Doxygen will invoke the filter program +# by executing (via popen()) the command , where +# is the value of the INPUT_FILTER tag, and is the name of an +# input file. Doxygen will then use the output that the filter program writes +# to standard output. + +INPUT_FILTER = + +#--------------------------------------------------------------------------- +# configuration options related to the alphabetical class index +#--------------------------------------------------------------------------- + +# If the ALPHABETICAL_INDEX tag is set to YES, an alphabetical index +# of all compounds will be generated. Enable this if the project +# contains a lot of classes, structs, unions or interfaces. + +ALPHABETICAL_INDEX = YES + +# If the alphabetical index is enabled (see ALPHABETICAL_INDEX) then +# the COLS_IN_ALPHA_INDEX tag can be used to specify the number of columns +# in which this list will be split (can be a number in the range [1..20]) + +COLS_IN_ALPHA_INDEX = 5 + +# In case all classes in a project start with a common prefix, all +# classes will be put under the same header in the alphabetical index. +# The IGNORE_PREFIX tag can be used to specify one or more prefixes that +# should be ignored while generating the index headers. + +IGNORE_PREFIX = + +#--------------------------------------------------------------------------- +# configuration options related to the HTML output +#--------------------------------------------------------------------------- + +# If the GENERATE_HTML tag is set to YES (the default) Doxygen will +# generate HTML output. + +GENERATE_HTML = YES + +# The HTML_OUTPUT tag is used to specify where the HTML docs will be put. +# If a relative path is entered the value of OUTPUT_DIRECTORY will be +# put in front of it. If left blank `html' will be used as the default path. + +HTML_OUTPUT = html + +# The HTML_HEADER tag can be used to specify a personal HTML header for +# each generated HTML page. If it is left blank doxygen will generate a +# standard header. + +HTML_HEADER = + +# The HTML_FOOTER tag can be used to specify a personal HTML footer for +# each generated HTML page. If it is left blank doxygen will generate a +# standard footer. + +HTML_FOOTER = $(OSGHOME)/doc/Doxyfiles/custom_Footer.html + +# The HTML_STYLESHEET tag can be used to specify a user defined cascading +# style sheet that is used by each HTML page. It can be used to +# fine-tune the look of the HTML output. If the tag is left blank doxygen +# will generate a default style sheet + +HTML_STYLESHEET = + +# If the HTML_ALIGN_MEMBERS tag is set to YES, the members of classes, +# files or namespaces will be aligned in HTML using tables. If set to +# NO a bullet list will be used. + +HTML_ALIGN_MEMBERS = YES + +# If the GENERATE_HTMLHELP tag is set to YES, additional index files +# will be generated that can be used as input for tools like the +# Microsoft HTML help workshop to generate a compressed HTML help file (.chm) +# of the generated HTML documentation. + +GENERATE_HTMLHELP = NO + +# The DISABLE_INDEX tag can be used to turn on/off the condensed index at +# top of each HTML page. The value NO (the default) enables the index and +# the value YES disables it. + +DISABLE_INDEX = NO + +#--------------------------------------------------------------------------- +# configuration options related to the LaTeX output +#--------------------------------------------------------------------------- + +# If the GENERATE_LATEX tag is set to YES (the default) Doxygen will +# generate Latex output. + +GENERATE_LATEX = NO + +# The LATEX_OUTPUT tag is used to specify where the LaTeX docs will be put. +# If a relative path is entered the value of OUTPUT_DIRECTORY will be +# put in front of it. If left blank `latex' will be used as the default path. + +LATEX_OUTPUT = latex + +# If the COMPACT_LATEX tag is set to YES Doxygen generates more compact +# LaTeX documents. This may be useful for small projects and may help to +# save some trees in general. + +COMPACT_LATEX = NO + +# The PAPER_TYPE tag can be used to set the paper type that is used +# by the printer. Possible values are: a4, a4wide, letter, legal and +# executive. If left blank a4wide will be used. + +PAPER_TYPE = a4wide + +# The EXTRA_PACKAGES tag can be to specify one or more names of LaTeX +# packages that should be included in the LaTeX output. + +EXTRA_PACKAGES = + +# The LATEX_HEADER tag can be used to specify a personal LaTeX header for +# the generated latex document. The header should contain everything until +# the first chapter. If it is left blank doxygen will generate a +# standard header. Notice: only use this tag if you know what you are doing! + +LATEX_HEADER = + +# If the PDF_HYPERLINKS tag is set to YES, the LaTeX that is generated +# is prepared for conversion to pdf (using ps2pdf). The pdf file will +# contain links (just like the HTML output) instead of page references +# This makes the output suitable for online browsing using a pdf viewer. + +PDF_HYPERLINKS = NO + +# If the USE_PDFLATEX tag is set to YES, pdflatex will be used instead of +# plain latex in the generated Makefile. Set this option to YES to get a +# higher quality PDF documentation. + +USE_PDFLATEX = NO + +# If the LATEX_BATCHMODE tag is set to YES, doxygen will add the \\batchmode. +# command to the generated LaTeX files. This will instruct LaTeX to keep +# running if errors occur, instead of asking the user for help. +# This option is also used when generating formulas in HTML. + +LATEX_BATCHMODE = NO + +#--------------------------------------------------------------------------- +# configuration options related to the RTF output +#--------------------------------------------------------------------------- + +# If the GENERATE_RTF tag is set to YES Doxygen will generate RTF output +# The RTF output is optimised for Word 97 and may not look very pretty with +# other RTF readers or editors. + +GENERATE_RTF = NO + +# The RTF_OUTPUT tag is used to specify where the RTF docs will be put. +# If a relative path is entered the value of OUTPUT_DIRECTORY will be +# put in front of it. If left blank `rtf' will be used as the default path. + +RTF_OUTPUT = rtf + +# If the COMPACT_RTF tag is set to YES Doxygen generates more compact +# RTF documents. This may be useful for small projects and may help to +# save some trees in general. + +COMPACT_RTF = NO + +# If the RTF_HYPERLINKS tag is set to YES, the RTF that is generated +# will contain hyperlink fields. The RTF file will +# contain links (just like the HTML output) instead of page references. +# This makes the output suitable for online browsing using a WORD or other. +# programs which support those fields. +# Note: wordpad (write) and others do not support links. + +RTF_HYPERLINKS = NO + +# Load stylesheet definitions from file. Syntax is similar to doxygen's +# config file, i.e. a series of assigments. You only have to provide +# replacements, missing definitions are set to their default value. + +RTF_STYLESHEET_FILE = + +#--------------------------------------------------------------------------- +# configuration options related to the man page output +#--------------------------------------------------------------------------- + +# If the GENERATE_MAN tag is set to YES (the default) Doxygen will +# generate man pages + +GENERATE_MAN = NO + +# The MAN_OUTPUT tag is used to specify where the man pages will be put. +# If a relative path is entered the value of OUTPUT_DIRECTORY will be +# put in front of it. If left blank `man' will be used as the default path. + +MAN_OUTPUT = man + +# The MAN_EXTENSION tag determines the extension that is added to +# the generated man pages (default is the subroutine's section .3) + +MAN_EXTENSION = .3 + +#--------------------------------------------------------------------------- +# configuration options related to the XML output +#--------------------------------------------------------------------------- + +# If the GENERATE_XML tag is set to YES Doxygen will +# generate an XML file that captures the structure of +# the code including all documentation. Warning: This feature +# is still experimental and very incomplete. + +GENERATE_XML = NO + +#--------------------------------------------------------------------------- +# Configuration options related to the preprocessor +#--------------------------------------------------------------------------- + +# If the ENABLE_PREPROCESSING tag is set to YES (the default) Doxygen will +# evaluate all C-preprocessor directives found in the sources and include +# files. + +ENABLE_PREPROCESSING = YES + +# If the MACRO_EXPANSION tag is set to YES Doxygen will expand all macro +# names in the source code. If set to NO (the default) only conditional +# compilation will be performed. Macro expansion can be done in a controlled +# way by setting EXPAND_ONLY_PREDEF to YES. + +MACRO_EXPANSION = NO + +# If the EXPAND_ONLY_PREDEF and MACRO_EXPANSION tags are both set to YES +# then the macro expansion is limited to the macros specified with the +# PREDEFINED and EXPAND_AS_PREDEFINED tags. + +EXPAND_ONLY_PREDEF = NO + +# If the SEARCH_INCLUDES tag is set to YES (the default) the includes files +# in the INCLUDE_PATH (see below) will be search if a #include is found. + +SEARCH_INCLUDES = YES + +# The INCLUDE_PATH tag can be used to specify one or more directories that +# contain include files that are not input files but should be processed by +# the preprocessor. + +INCLUDE_PATH = + +# You can use the INCLUDE_FILE_PATTERNS tag to specify one or more wildcard +# patterns (like *.h and *.hpp) to filter out the header-files in the +# directories. If left blank, the patterns specified with FILE_PATTERNS will +# be used. + +INCLUDE_FILE_PATTERNS = + +# The PREDEFINED tag can be used to specify one or more macro names that +# are defined before the preprocessor is started (similar to the -D option of +# gcc). The argument of the tag is a list of macros of the form: name +# or name=definition (no spaces). If the definition and the = are +# omitted =1 is assumed. + +PREDEFINED = + +# If the MACRO_EXPANSION and EXPAND_PREDEF_ONLY tags are set to YES then +# this tag can be used to specify a list of macro names that should be expanded. +# The macro definition that is found in the sources will be used. +# Use the PREDEFINED tag if you want to use a different macro definition. + +EXPAND_AS_DEFINED = + +#--------------------------------------------------------------------------- +# Configuration::addtions related to external references +#--------------------------------------------------------------------------- + +# The TAGFILES tag can be used to specify one or more tagfiles. + +TAGFILES = + +# When a file name is specified after GENERATE_TAGFILE, doxygen will create +# a tag file that is based on the input files it reads. + +GENERATE_TAGFILE = + +# If the ALLEXTERNALS tag is set to YES all external classes will be listed +# in the class index. If set to NO only the inherited external classes +# will be listed. + +ALLEXTERNALS = NO + +# The PERL_PATH should be the absolute path and name of the perl script +# interpreter (i.e. the result of `which perl'). + +PERL_PATH = /usr/bin/perl + +#--------------------------------------------------------------------------- +# Configuration options related to the dot tool +#--------------------------------------------------------------------------- + +# If you set the HAVE_DOT tag to YES then doxygen will assume the dot tool is +# available from the path. This tool is part of Graphviz, a graph visualization +# toolkit from AT&T and Lucent Bell Labs. The other options in this section +# have no effect if this option is set to NO (the default) + +HAVE_DOT = YES + +# If the CLASS_GRAPH and HAVE_DOT tags are set to YES then doxygen +# will generate a graph for each documented class showing the direct and +# indirect inheritance relations. Setting this tag to YES will force the +# the CLASS_DIAGRAMS tag to NO. + +CLASS_GRAPH = YES + +# If the COLLABORATION_GRAPH and HAVE_DOT tags are set to YES then doxygen +# will generate a graph for each documented class showing the direct and +# indirect implementation dependencies (inheritance, containment, and +# class references variables) of the class with other documented classes. + +COLLABORATION_GRAPH = YES + +# If the ENABLE_PREPROCESSING, INCLUDE_GRAPH, and HAVE_DOT tags are set to +# YES then doxygen will generate a graph for each documented file showing +# the direct and indirect include dependencies of the file with other +# documented files. + +INCLUDE_GRAPH = YES + +# If the ENABLE_PREPROCESSING, INCLUDED_BY_GRAPH, and HAVE_DOT tags are set to +# YES then doxygen will generate a graph for each documented header file showing +# the documented files that directly or indirectly include this file + +INCLUDED_BY_GRAPH = YES + +# If the GRAPHICAL_HIERARCHY and HAVE_DOT tags are set to YES then doxygen +# will graphical hierarchy of all classes instead of a textual one. + +GRAPHICAL_HIERARCHY = YES + +# The tag DOT_PATH can be used to specify the path where the dot tool can be +# found. If left blank, it is assumed the dot tool can be found on the path. + +DOT_PATH = + +# The MAX_DOT_GRAPH_WIDTH tag can be used to set the maximum allowed width +# (in pixels) of the graphs generated by dot. If a graph becomes larger than +# this value, doxygen will try to truncate the graph, so that it fits within +# the specified constraint. Beware that most browsers cannot cope with very +# large images. + +MAX_DOT_GRAPH_WIDTH = 1024 + +# The MAX_DOT_GRAPH_HEIGHT tag can be used to set the maximum allows height +# (in pixels) of the graphs generated by dot. If a graph becomes larger than +# this value, doxygen will try to truncate the graph, so that it fits within +# the specified constraint. Beware that most browsers cannot cope with very +# large images. + +MAX_DOT_GRAPH_HEIGHT = 1024 + +#--------------------------------------------------------------------------- +# Configuration::addtions related to the search engine +#--------------------------------------------------------------------------- + +# The SEARCHENGINE tag specifies whether or not a search engine should be +# used. If set to NO the values of all tags below this one will be ignored. + +SEARCHENGINE = NO + +# The CGI_NAME tag should be the name of the CGI script that +# starts the search engine (doxysearch) with the correct parameters. +# A script with this name will be generated by doxygen. + +CGI_NAME = search.cgi + +# The CGI_URL tag should be the absolute URL to the directory where the +# cgi binaries are located. See the documentation of your http daemon for +# details. + +CGI_URL = + +# The DOC_URL tag should be the absolute URL to the directory where the +# documentation is located. If left blank the absolute path to the +# documentation, with file:// prepended to it, will be used. + +DOC_URL = + +# The DOC_ABSPATH tag should be the absolute path to the directory where the +# documentation is located. If left blank the directory on the local machine +# will be used. + +DOC_ABSPATH = + +# The BIN_ABSPATH tag must point to the directory where the doxysearch binary +# is installed. + +BIN_ABSPATH = /usr/local/bin/ + +# The EXT_DOC_PATHS tag can be used to specify one or more paths to +# documentation generated for other projects. This allows doxysearch to search +# the documentation for these projects as well. + +EXT_DOC_PATHS = diff --git a/doc/Doxyfiles/auto_Doxyfile b/doc/Doxyfiles/auto_Doxyfile new file mode 100644 index 000000000..31a007d14 --- /dev/null +++ b/doc/Doxyfiles/auto_Doxyfile @@ -0,0 +1,775 @@ +# Doxyfile 1.2.5 + +# ========================================================================== +# auto_Doxyfile has been written for use by a script that will, upon +# release of a new OSG snapshot, automatically generate doxygen tarballs +# and update the online documentation on the web. It relies on various +# non-(OSG)standard environment variables being set, and is not really +# designed for normal shell-based usage. Assumptions: +# +# OSGHOME points to the root of the OSG tree on your filesystem +# OSGVERSION is set to the OSG's version number +# 'dot' is installed +# +# ========================================================================== + +# This file describes the settings to be used by doxygen for a project +# +# All text after a hash (#) is considered a comment and will be ignored +# The format is: +# TAG = value [value, ...] +# For lists items can also be appended using: +# TAG += value [value, ...] +# Values that contain spaces should be placed between quotes (" ") + +#--------------------------------------------------------------------------- +# General configuration options +#--------------------------------------------------------------------------- + +# The PROJECT_NAME tag is a single word (or a sequence of words surrounded +# by quotes) that should identify the project. + +PROJECT_NAME = "Open Scene Graph & Utility Toolkit" + +# The PROJECT_NUMBER tag can be used to enter a project or revision number. +# This could be handy for archiving the generated documentation or +# if some version control system is used. + +PROJECT_NUMBER = $(OSGVERSION) + +# The OUTPUT_DIRECTORY tag is used to specify the (relative or absolute) +# base path where the generated documentation will be put. +# If a relative path is entered, it will be relative to the location +# where doxygen was started. If left blank the current directory will be used. + +OUTPUT_DIRECTORY = $(OSGHOME)/doc/osg-doxygen-$(OSGVERSION) + +# The OUTPUT_LANGUAGE tag is used to specify the language in which all +# documentation generated by doxygen is written. Doxygen will use this +# information to generate all constant output in the proper language. +# The default language is English, other supported languages are: +# Dutch, French, Italian, Czech, Swedish, German, Finnish, Japanese, +# Korean, Hungarian, Norwegian, Spanish, Romanian, Russian, Croatian, +# Polish, Portuguese and Slovene. + +OUTPUT_LANGUAGE = English + +# If the EXTRACT_ALL tag is set to YES doxygen will assume all entities in +# documentation are documented, even if no documentation was available. +# Private class members and static file members will be hidden unless +# the EXTRACT_PRIVATE and EXTRACT_STATIC tags are set to YES + +EXTRACT_ALL = YES + +# If the EXTRACT_PRIVATE tag is set to YES all private members of a class +# will be included in the documentation. + +EXTRACT_PRIVATE = NO + +# If the EXTRACT_STATIC tag is set to YES all static members of a file +# will be included in the documentation. + +EXTRACT_STATIC = NO + +# If the HIDE_UNDOC_MEMBERS tag is set to YES, Doxygen will hide all +# undocumented members of documented classes, files or namespaces. +# If set to NO (the default) these members will be included in the +# various overviews, but no documentation section is generated. +# This option has no effect if EXTRACT_ALL is enabled. + +HIDE_UNDOC_MEMBERS = NO + +# If the HIDE_UNDOC_CLASSES tag is set to YES, Doxygen will hide all +# undocumented classes that are normally visible in the class hierarchy. +# If set to NO (the default) these class will be included in the various +# overviews. This option has no effect if EXTRACT_ALL is enabled. + +HIDE_UNDOC_CLASSES = NO + +# If the BRIEF_MEMBER_DESC tag is set to YES (the default) Doxygen will +# include brief member descriptions after the members that are listed in +# the file and class documentation (similar to JavaDoc). +# Set to NO to disable this. + +BRIEF_MEMBER_DESC = YES + +# If the REPEAT_BRIEF tag is set to YES (the default) Doxygen will prepend +# the brief description of a member or function before the detailed description. +# Note: if both HIDE_UNDOC_MEMBERS and BRIEF_MEMBER_DESC are set to NO, the +# brief descriptions will be completely suppressed. + +REPEAT_BRIEF = YES + +# If the ALWAYS_DETAILED_SEC and REPEAT_BRIEF tags are both set to YES then +# Doxygen will generate a detailed section even if there is only a brief +# description. + +ALWAYS_DETAILED_SEC = NO + +# If the FULL_PATH_NAMES tag is set to YES then Doxygen will prepend the full +# path before files name in the file list and in the header files. If set +# to NO the shortest path that makes the file name unique will be used. + +FULL_PATH_NAMES = NO + +# If the FULL_PATH_NAMES tag is set to YES then the STRIP_FROM_PATH tag +# can be used to strip a user defined part of the path. Stripping is +# only done if one of the specified strings matches the left-hand part of +# the path. It is allowed to use relative paths in the argument list. + +STRIP_FROM_PATH = + +# The INTERNAL_DOCS tag determines if documentation +# that is typed after a \internal command is included. If the tag is set +# to NO (the default) then the documentation will be excluded. +# Set it to YES to include the internal documentation. + +INTERNAL_DOCS = NO + +# If the CLASS_DIAGRAMS tag is set to YES (the default) Doxygen will +# generate a class diagram (in Html and LaTeX) for classes with base or +# super classes. Setting the tag to NO turns the diagrams off. + +CLASS_DIAGRAMS = YES + +# If the SOURCE_BROWSER tag is set to YES then a list of source files will +# be generated. Documented entities will be cross-referenced with these sources. + +SOURCE_BROWSER = NO + +# Setting the INLINE_SOURCES tag to YES will include the body +# of functions and classes directly in the documentation. + +INLINE_SOURCES = NO + +# Setting the STRIP_CODE_COMMENTS tag to YES (the default) will instruct +# doxygen to hide any special comment blocks from generated source code +# fragments. Normal C and C++ comments will always remain visible. + +STRIP_CODE_COMMENTS = YES + +# If the CASE_SENSE_NAMES tag is set to NO then Doxygen will only generate +# file names in lower case letters. If set to YES upper case letters are also +# allowed. This is useful if you have classes or files whose names only differ +# in case and if your file system supports case sensitive file names. Windows +# users are adviced to set this option to NO. + +CASE_SENSE_NAMES = YES + +# If the HIDE_SCOPE_NAMES tag is set to NO (the default) then Doxygen +# will show members with their full class and namespace scopes in the +# documentation. If set to YES the scope will be hidden. + +HIDE_SCOPE_NAMES = NO + +# If the VERBATIM_HEADERS tag is set to YES (the default) then Doxygen +# will generate a verbatim copy of the header file for each class for +# which an include is specified. Set to NO to disable this. + +VERBATIM_HEADERS = YES + +# If the SHOW_INCLUDE_FILES tag is set to YES (the default) then Doxygen +# will put list of the files that are included by a file in the documentation +# of that file. + +SHOW_INCLUDE_FILES = YES + +# If the JAVADOC_AUTOBRIEF tag is set to YES then Doxygen +# will interpret the first line (until the first dot) of a JavaDoc-style +# comment as the brief description. If set to NO, the JavaDoc +# comments will behave just like the Qt-style comments (thus requiring an +# explict @brief command for a brief description. + +JAVADOC_AUTOBRIEF = YES + +# If the INHERIT_DOCS tag is set to YES (the default) then an undocumented +# member inherits the documentation from any documented member that it +# reimplements. + +INHERIT_DOCS = YES + +# If the INLINE_INFO tag is set to YES (the default) then a tag [inline] +# is inserted in the documentation for inline members. + +INLINE_INFO = YES + +# If the SORT_MEMBER_DOCS tag is set to YES (the default) then doxygen +# will sort the (detailed) documentation of file and class members +# alphabetically by member name. If set to NO the members will appear in +# declaration order. + +SORT_MEMBER_DOCS = YES + +# If member grouping is used in the documentation and the DISTRIBUTE_GROUP_DOC +# tag is set to YES, then doxygen will reuse the documentation of the first +# member in the group (if any) for the other members of the group. By default +# all members of a group must be documented explicitly. + +DISTRIBUTE_GROUP_DOC = NO + +# The TAB_SIZE tag can be used to set the number of spaces in a tab. +# Doxygen uses this value to replace tabs by spaces in code fragments. + +TAB_SIZE = 8 + +# The ENABLE_SECTIONS tag can be used to enable conditional +# documentation sections, marked by \if sectionname ... \endif. + +ENABLED_SECTIONS = + +# The GENERATE_TODOLIST tag can be used to enable (YES) or +# disable (NO) the todo list. This list is created by putting \todo +# commands in the documentation. + +GENERATE_TODOLIST = YES + +# The GENERATE_TESTLIST tag can be used to enable (YES) or +# disable (NO) the test list. This list is created by putting \test +# commands in the documentation. + +GENERATE_TESTLIST = YES + +# This tag can be used to specify a number of aliases that acts +# as commands in the documentation. An alias has the form "name=value". +# For example adding "sideeffect=\par Side Effects:\n" will allow you to +# put the command \sideeffect (or @sideeffect) in the documentation, which +# will result in a user defined paragraph with heading "Side Effects:". +# You can put \n's in the value part of an alias to insert newlines. + +ALIASES = + +# The MAX_INITIALIZER_LINES tag determines the maximum number of lines +# the initial value of a variable or define consist of for it to appear in +# the documentation. If the initializer consists of more lines than specified +# here it will be hidden. Use a value of 0 to hide initializers completely. +# The appearance of the initializer of individual variables and defines in the +# documentation can be controlled using \showinitializer or \hideinitializer +# command in the documentation regardless of this setting. + +MAX_INITIALIZER_LINES = 30 + +# Set the OPTIMIZE_OUTPUT_FOR_C tag to YES if your project consists of C sources +# only. Doxygen will then generate output that is more tailored for C. +# For instance some of the names that are used will be different. The list +# of all members will be omitted, etc. + +OPTIMIZE_OUTPUT_FOR_C = NO + +#--------------------------------------------------------------------------- +# configuration options related to warning and progress messages +#--------------------------------------------------------------------------- + +# The QUIET tag can be used to turn on/off the messages that are generated +# by doxygen. Possible values are YES and NO. If left blank NO is used. + +# This doesn't work: +#QUIET = $(OSGAUTODOXYGENQUIET) +QUIET = YES + +# The WARNINGS tag can be used to turn on/off the warning messages that are +# generated by doxygen. Possible values are YES and NO. If left blank +# NO is used. + +WARNINGS = $(OSGAUTODOXYGENWARNINGS) + +# If WARN_IF_UNDOCUMENTED is set to YES, then doxygen will generate warnings +# for undocumented members. If EXTRACT_ALL is set to YES then this flag will +# automatically be disabled. + +WARN_IF_UNDOCUMENTED = $(OSGAUTODOXYGENWARNIFUNDOCUMENTED) + +# The WARN_FORMAT tag determines the format of the warning messages that +# doxygen can produce. The string should contain the $file, $line, and $text +# tags, which will be replaced by the file and line number from which the +# warning originated and the warning text. + +WARN_FORMAT = "$file:$line: $text" + +# The WARN_LOGFILE tag can be used to specify a file to which warning +# and error messages should be written. If left blank the output is written +# to stderr. + +WARN_LOGFILE = + +#--------------------------------------------------------------------------- +# configuration options related to the input files +#--------------------------------------------------------------------------- + +# The INPUT tag can be used to specify the files and/or directories that contain +# documented source files. You may enter file names like "myfile.cpp" or +# directories like "/usr/src/myproject". Separate the files or directories +# with spaces. + +INPUT = $(OSGHOME)/include/osg \ + $(OSGHOME)/include/osgUtil \ + $(OSGHOME)/include/osgDB \ + $(OSGHOME)/include/osgGLUT \ + $(OSGHOME)/src/osg \ + $(OSGHOME)/src/osgUtil \ + $(OSGHOME)/src/osgDB \ + $(OSGHOME)/src/osgGLUT \ + $(OSGHOME)/doc/Doxyfiles/auto_Mainpage + +# If the value of the INPUT tag contains directories, you can use the +# FILE_PATTERNS tag to specify one or more wildcard pattern (like *.cpp +# and *.h) to filter out the source-files in the directories. If left +# blank all files are included. + +FILE_PATTERNS = + +# The RECURSIVE tag can be used to turn specify whether or not subdirectories +# should be searched for input files as well. Possible values are YES and NO. +# If left blank NO is used. + +RECURSIVE = YES + +# The EXCLUDE tag can be used to specify files and/or directories that should +# excluded from the INPUT source files. This way you can easily exclude a +# subdirectory from a directory tree whose root is specified with the INPUT tag. + +EXCLUDE = + +# If the value of the INPUT tag contains directories, you can use the +# EXCLUDE_PATTERNS tag to specify one or more wildcard patterns to exclude +# certain files from those directories. + +EXCLUDE_PATTERNS = + +# The EXAMPLE_PATH tag can be used to specify one or more files or +# directories that contain example code fragments that are included (see +# the \include command). + +EXAMPLE_PATH = + +# If the value of the EXAMPLE_PATH tag contains directories, you can use the +# EXAMPLE_PATTERNS tag to specify one or more wildcard pattern (like *.cpp +# and *.h) to filter out the source-files in the directories. If left +# blank all files are included. + +EXAMPLE_PATTERNS = + +# The IMAGE_PATH tag can be used to specify one or more files or +# directories that contain image that are included in the documentation (see +# the \image command). + +IMAGE_PATH = + +# The INPUT_FILTER tag can be used to specify a program that doxygen should +# invoke to filter for each input file. Doxygen will invoke the filter program +# by executing (via popen()) the command , where +# is the value of the INPUT_FILTER tag, and is the name of an +# input file. Doxygen will then use the output that the filter program writes +# to standard output. + +INPUT_FILTER = + +# If the FILTER_SOURCE_FILES tag is set to YES, the input filter (if set using +# INPUT_FILTER) will be used to filter the input files when producing source +# files to browse. + +FILTER_SOURCE_FILES = NO + +#--------------------------------------------------------------------------- +# configuration options related to the alphabetical class index +#--------------------------------------------------------------------------- + +# If the ALPHABETICAL_INDEX tag is set to YES, an alphabetical index +# of all compounds will be generated. Enable this if the project +# contains a lot of classes, structs, unions or interfaces. + +ALPHABETICAL_INDEX = YES + +# If the alphabetical index is enabled (see ALPHABETICAL_INDEX) then +# the COLS_IN_ALPHA_INDEX tag can be used to specify the number of columns +# in which this list will be split (can be a number in the range [1..20]) + +COLS_IN_ALPHA_INDEX = 5 + +# In case all classes in a project start with a common prefix, all +# classes will be put under the same header in the alphabetical index. +# The IGNORE_PREFIX tag can be used to specify one or more prefixes that +# should be ignored while generating the index headers. + +IGNORE_PREFIX = + +#--------------------------------------------------------------------------- +# configuration options related to the HTML output +#--------------------------------------------------------------------------- + +# If the GENERATE_HTML tag is set to YES (the default) Doxygen will +# generate HTML output. + +GENERATE_HTML = YES + +# The HTML_OUTPUT tag is used to specify where the HTML docs will be put. +# If a relative path is entered the value of OUTPUT_DIRECTORY will be +# put in front of it. If left blank `html' will be used as the default path. + +HTML_OUTPUT = html + +# The HTML_HEADER tag can be used to specify a personal HTML header for +# each generated HTML page. If it is left blank doxygen will generate a +# standard header. + +HTML_HEADER = + +# The HTML_FOOTER tag can be used to specify a personal HTML footer for +# each generated HTML page. If it is left blank doxygen will generate a +# standard footer. + +HTML_FOOTER = $(OSGHOME)/doc/Doxyfiles/custom_Footer.html + +# The HTML_STYLESHEET tag can be used to specify a user defined cascading +# style sheet that is used by each HTML page. It can be used to +# fine-tune the look of the HTML output. If the tag is left blank doxygen +# will generate a default style sheet + +HTML_STYLESHEET = + +# If the HTML_ALIGN_MEMBERS tag is set to YES, the members of classes, +# files or namespaces will be aligned in HTML using tables. If set to +# NO a bullet list will be used. + +HTML_ALIGN_MEMBERS = YES + +# If the GENERATE_HTMLHELP tag is set to YES, additional index files +# will be generated that can be used as input for tools like the +# Microsoft HTML help workshop to generate a compressed HTML help file (.chm) +# of the generated HTML documentation. + +GENERATE_HTMLHELP = NO + +# The DISABLE_INDEX tag can be used to turn on/off the condensed index at +# top of each HTML page. The value NO (the default) enables the index and +# the value YES disables it. + +DISABLE_INDEX = NO + +# This tag can be used to set the number of enum values (range [1..20]) +# that doxygen will group on one line in the generated HTML documentation. + +ENUM_VALUES_PER_LINE = 4 + +# If the GENERATE_TREEVIEW tag is set to YES, a side panel will be +# generated containing a tree-like index structure (just like the one that +# is generated for HTML Help). For this to work a browser that supports +# JavaScript and frames is required (for instance Netscape 4.0+ +# or Internet explorer 4.0+). + +GENERATE_TREEVIEW = NO + +# If the treeview is enabled (see GENERATE_TREEVIEW) then this tag can be +# used to set the initial width (in pixels) of the frame in which the tree +# is shown. + +TREEVIEW_WIDTH = 250 + +#--------------------------------------------------------------------------- +# configuration options related to the LaTeX output +#--------------------------------------------------------------------------- + +# If the GENERATE_LATEX tag is set to YES (the default) Doxygen will +# generate Latex output. + +GENERATE_LATEX = NO + +# The LATEX_OUTPUT tag is used to specify where the LaTeX docs will be put. +# If a relative path is entered the value of OUTPUT_DIRECTORY will be +# put in front of it. If left blank `latex' will be used as the default path. + +LATEX_OUTPUT = latex + +# If the COMPACT_LATEX tag is set to YES Doxygen generates more compact +# LaTeX documents. This may be useful for small projects and may help to +# save some trees in general. + +COMPACT_LATEX = NO + +# The PAPER_TYPE tag can be used to set the paper type that is used +# by the printer. Possible values are: a4, a4wide, letter, legal and +# executive. If left blank a4wide will be used. + +PAPER_TYPE = a4wide + +# The EXTRA_PACKAGES tag can be to specify one or more names of LaTeX +# packages that should be included in the LaTeX output. + +EXTRA_PACKAGES = + +# The LATEX_HEADER tag can be used to specify a personal LaTeX header for +# the generated latex document. The header should contain everything until +# the first chapter. If it is left blank doxygen will generate a +# standard header. Notice: only use this tag if you know what you are doing! + +LATEX_HEADER = + +# If the PDF_HYPERLINKS tag is set to YES, the LaTeX that is generated +# is prepared for conversion to pdf (using ps2pdf). The pdf file will +# contain links (just like the HTML output) instead of page references +# This makes the output suitable for online browsing using a pdf viewer. + +PDF_HYPERLINKS = NO + +# If the USE_PDFLATEX tag is set to YES, pdflatex will be used instead of +# plain latex in the generated Makefile. Set this option to YES to get a +# higher quality PDF documentation. + +USE_PDFLATEX = NO + +# If the LATEX_BATCHMODE tag is set to YES, doxygen will add the \\batchmode. +# command to the generated LaTeX files. This will instruct LaTeX to keep +# running if errors occur, instead of asking the user for help. +# This option is also used when generating formulas in HTML. + +LATEX_BATCHMODE = NO + +#--------------------------------------------------------------------------- +# configuration options related to the RTF output +#--------------------------------------------------------------------------- + +# If the GENERATE_RTF tag is set to YES Doxygen will generate RTF output +# The RTF output is optimised for Word 97 and may not look very pretty with +# other RTF readers or editors. + +GENERATE_RTF = NO + +# The RTF_OUTPUT tag is used to specify where the RTF docs will be put. +# If a relative path is entered the value of OUTPUT_DIRECTORY will be +# put in front of it. If left blank `rtf' will be used as the default path. + +RTF_OUTPUT = rtf + +# If the COMPACT_RTF tag is set to YES Doxygen generates more compact +# RTF documents. This may be useful for small projects and may help to +# save some trees in general. + +COMPACT_RTF = NO + +# If the RTF_HYPERLINKS tag is set to YES, the RTF that is generated +# will contain hyperlink fields. The RTF file will +# contain links (just like the HTML output) instead of page references. +# This makes the output suitable for online browsing using a WORD or other. +# programs which support those fields. +# Note: wordpad (write) and others do not support links. + +RTF_HYPERLINKS = NO + +# Load stylesheet definitions from file. Syntax is similar to doxygen's +# config file, i.e. a series of assigments. You only have to provide +# replacements, missing definitions are set to their default value. + +RTF_STYLESHEET_FILE = + +#--------------------------------------------------------------------------- +# configuration options related to the man page output +#--------------------------------------------------------------------------- + +# If the GENERATE_MAN tag is set to YES (the default) Doxygen will +# generate man pages + +GENERATE_MAN = NO + +# The MAN_OUTPUT tag is used to specify where the man pages will be put. +# If a relative path is entered the value of OUTPUT_DIRECTORY will be +# put in front of it. If left blank `man' will be used as the default path. + +MAN_OUTPUT = man + +# The MAN_EXTENSION tag determines the extension that is added to +# the generated man pages (default is the subroutine's section .3) + +MAN_EXTENSION = .3 + +#--------------------------------------------------------------------------- +# Configuration options related to the preprocessor +#--------------------------------------------------------------------------- + +# If the ENABLE_PREPROCESSING tag is set to YES (the default) Doxygen will +# evaluate all C-preprocessor directives found in the sources and include +# files. + +ENABLE_PREPROCESSING = YES + +# If the MACRO_EXPANSION tag is set to YES Doxygen will expand all macro +# names in the source code. If set to NO (the default) only conditional +# compilation will be performed. Macro expansion can be done in a controlled +# way by setting EXPAND_ONLY_PREDEF to YES. + +MACRO_EXPANSION = NO + +# If the EXPAND_ONLY_PREDEF and MACRO_EXPANSION tags are both set to YES +# then the macro expansion is limited to the macros specified with the +# PREDEFINED and EXPAND_AS_PREDEFINED tags. + +EXPAND_ONLY_PREDEF = NO + +# If the SEARCH_INCLUDES tag is set to YES (the default) the includes files +# in the INCLUDE_PATH (see below) will be search if a #include is found. + +SEARCH_INCLUDES = YES + +# The INCLUDE_PATH tag can be used to specify one or more directories that +# contain include files that are not input files but should be processed by +# the preprocessor. + +INCLUDE_PATH = + +# You can use the INCLUDE_FILE_PATTERNS tag to specify one or more wildcard +# patterns (like *.h and *.hpp) to filter out the header-files in the +# directories. If left blank, the patterns specified with FILE_PATTERNS will +# be used. + +INCLUDE_FILE_PATTERNS = + +# The PREDEFINED tag can be used to specify one or more macro names that +# are defined before the preprocessor is started (similar to the -D option of +# gcc). The argument of the tag is a list of macros of the form: name +# or name=definition (no spaces). If the definition and the = are +# omitted =1 is assumed. + +PREDEFINED = + +# If the MACRO_EXPANSION and EXPAND_PREDEF_ONLY tags are set to YES then +# this tag can be used to specify a list of macro names that should be expanded. +# The macro definition that is found in the sources will be used. +# Use the PREDEFINED tag if you want to use a different macro definition. + +EXPAND_AS_DEFINED = + +#--------------------------------------------------------------------------- +# Configuration::addtions related to external references +#--------------------------------------------------------------------------- + +# The TAGFILES tag can be used to specify one or more tagfiles. + +TAGFILES = + +# When a file name is specified after GENERATE_TAGFILE, doxygen will create +# a tag file that is based on the input files it reads. + +GENERATE_TAGFILE = + +# If the ALLEXTERNALS tag is set to YES all external classes will be listed +# in the class index. If set to NO only the inherited external classes +# will be listed. + +ALLEXTERNALS = NO + +# The PERL_PATH should be the absolute path and name of the perl script +# interpreter (i.e. the result of `which perl'). + +PERL_PATH = /usr/bin/perl + +#--------------------------------------------------------------------------- +# Configuration options related to the dot tool +#--------------------------------------------------------------------------- + +# If you set the HAVE_DOT tag to YES then doxygen will assume the dot tool is +# available from the path. This tool is part of Graphviz, a graph visualization +# toolkit from AT&T and Lucent Bell Labs. The other options in this section +# have no effect if this option is set to NO (the default) + +HAVE_DOT = YES + +# If the CLASS_GRAPH and HAVE_DOT tags are set to YES then doxygen +# will generate a graph for each documented class showing the direct and +# indirect inheritance relations. Setting this tag to YES will force the +# the CLASS_DIAGRAMS tag to NO. + +CLASS_GRAPH = YES + +# If the COLLABORATION_GRAPH and HAVE_DOT tags are set to YES then doxygen +# will generate a graph for each documented class showing the direct and +# indirect implementation dependencies (inheritance, containment, and +# class references variables) of the class with other documented classes. + +COLLABORATION_GRAPH = YES + +# If the ENABLE_PREPROCESSING, INCLUDE_GRAPH, and HAVE_DOT tags are set to +# YES then doxygen will generate a graph for each documented file showing +# the direct and indirect include dependencies of the file with other +# documented files. + +INCLUDE_GRAPH = YES + +# If the ENABLE_PREPROCESSING, INCLUDED_BY_GRAPH, and HAVE_DOT tags are set to +# YES then doxygen will generate a graph for each documented header file showing +# the documented files that directly or indirectly include this file + +INCLUDED_BY_GRAPH = YES + +# If the GRAPHICAL_HIERARCHY and HAVE_DOT tags are set to YES then doxygen +# will graphical hierarchy of all classes instead of a textual one. + +GRAPHICAL_HIERARCHY = YES + +# The tag DOT_PATH can be used to specify the path where the dot tool can be +# found. If left blank, it is assumed the dot tool can be found on the path. + +DOT_PATH = + +# The MAX_DOT_GRAPH_WIDTH tag can be used to set the maximum allowed width +# (in pixels) of the graphs generated by dot. If a graph becomes larger than +# this value, doxygen will try to truncate the graph, so that it fits within +# the specified constraint. Beware that most browsers cannot cope with very +# large images. + +MAX_DOT_GRAPH_WIDTH = 1024 + +# The MAX_DOT_GRAPH_HEIGHT tag can be used to set the maximum allows height +# (in pixels) of the graphs generated by dot. If a graph becomes larger than +# this value, doxygen will try to truncate the graph, so that it fits within +# the specified constraint. Beware that most browsers cannot cope with very +# large images. + +MAX_DOT_GRAPH_HEIGHT = 1024 + +# If the GENERATE_LEGEND tag is set to YES (the default) Doxygen will +# generate a legend page explaining the meaning of the various boxes and +# arrows in the dot generated graphs. + +GENERATE_LEGEND = YES + +#--------------------------------------------------------------------------- +# Configuration::addtions related to the search engine +#--------------------------------------------------------------------------- + +# The SEARCHENGINE tag specifies whether or not a search engine should be +# used. If set to NO the values of all tags below this one will be ignored. + +SEARCHENGINE = NO + +# The CGI_NAME tag should be the name of the CGI script that +# starts the search engine (doxysearch) with the correct parameters. +# A script with this name will be generated by doxygen. + +CGI_NAME = search.cgi + +# The CGI_URL tag should be the absolute URL to the directory where the +# cgi binaries are located. See the documentation of your http daemon for +# details. + +CGI_URL = + +# The DOC_URL tag should be the absolute URL to the directory where the +# documentation is located. If left blank the absolute path to the +# documentation, with file:// prepended to it, will be used. + +DOC_URL = + +# The DOC_ABSPATH tag should be the absolute path to the directory where the +# documentation is located. If left blank the directory on the local machine +# will be used. + +DOC_ABSPATH = + +# The BIN_ABSPATH tag must point to the directory where the doxysearch binary +# is installed. + +BIN_ABSPATH = /usr/local/bin/ + +# The EXT_DOC_PATHS tag can be used to specify one or more paths to +# documentation generated for other projects. This allows doxysearch to search +# the documentation for these projects as well. + +EXT_DOC_PATHS = diff --git a/doc/Doxyfiles/auto_Mainpage b/doc/Doxyfiles/auto_Mainpage new file mode 100644 index 000000000..64097980e --- /dev/null +++ b/doc/Doxyfiles/auto_Mainpage @@ -0,0 +1,13 @@ +/** + * \mainpage + * These pages document the API for the standard Open Scene Graph + * distribution. This includes the core scene graph (osg), the accompanying + * utility toolkit (osgUtil), and the rudimentary GLUT work (osgGLUT). + * In the interests of clarity, the plug-ins which may also be found in + * the distribution have not been documented here. + * + * Tarballs of this documentation may be downloaded from + * here. + * + * Enjoy! +*/ diff --git a/doc/Doxyfiles/core_Doxyfile b/doc/Doxyfiles/core_Doxyfile new file mode 100644 index 000000000..2c8a2abbd --- /dev/null +++ b/doc/Doxyfiles/core_Doxyfile @@ -0,0 +1,726 @@ +# Doxyfile 1.2.2 + +# ========================================================================== +# core_Doxyfile documents only the central core componenets of the OSG, +# ignoring plugins. Assumptions: +# +# OSGHOME points to the root of the OSG tree on your filesystem +# 'dot' is installed +# +# ========================================================================== + +# This file describes the settings to be used by doxygen for a project +# +# All text after a hash (#) is considered a comment and will be ignored +# The format is: +# TAG = value [value, ...] +# For lists items can also be appended using: +# TAG += value [value, ...] +# Values that contain spaces should be placed between quotes (" ") + +#--------------------------------------------------------------------------- +# General configuration options +#--------------------------------------------------------------------------- + +# The PROJECT_NAME tag is a single word (or a sequence of words surrounded +# by quotes) that should identify the project. + +PROJECT_NAME = "Open Scene Graph & Utility Toolkit" + +# The PROJECT_NUMBER tag can be used to enter a project or revision number. +# This could be handy for archiving the generated documentation or +# if some version control system is used. + +PROJECT_NUMBER = + +# The OUTPUT_DIRECTORY tag is used to specify the (relative or absolute) +# base path where the generated documentation will be put. +# If a relative path is entered, it will be relative to the location +# where doxygen was started. If left blank the current directory will be used. + +OUTPUT_DIRECTORY = $(OSGHOME)/doc/doxygen + +# The OUTPUT_LANGUAGE tag is used to specify the language in which all +# documentation generated by doxygen is written. Doxygen will use this +# information to generate all constant output in the proper language. +# The default language is English, other supported languages are: +# Dutch, French, Italian, Czech, Swedish, German, Finnish, Japanese, +# Korean, Hungarian, Spanish, Romanian, Russian, Croatian, Polish, and +# Portuguese. + +OUTPUT_LANGUAGE = English + +# If the EXTRACT_ALL tag is set to YES doxygen will assume all entities in +# documentation are documented, even if no documentation was available. +# Private class members and static file members will be hidden unless +# the EXTRACT_PRIVATE and EXTRACT_STATIC tags are set to YES + +EXTRACT_ALL = YES + +# If the EXTRACT_PRIVATE tag is set to YES all private members of a class +# will be included in the documentation. + +EXTRACT_PRIVATE = NO + +# If the EXTRACT_STATIC tag is set to YES all static members of a file +# will be included in the documentation. + +EXTRACT_STATIC = NO + +# If the HIDE_UNDOC_MEMBERS tag is set to YES, Doxygen will hide all +# undocumented members of documented classes, files or namespaces. +# If set to NO (the default) these members will be included in the +# various overviews, but no documentation section is generated. +# This option has no effect if EXTRACT_ALL is enabled. + +HIDE_UNDOC_MEMBERS = NO + +# If the HIDE_UNDOC_CLASSES tag is set to YES, Doxygen will hide all +# undocumented classes that are normally visible in the class hierarchy. +# If set to NO (the default) these class will be included in the various +# overviews. This option has no effect if EXTRACT_ALL is enabled. + +HIDE_UNDOC_CLASSES = NO + +# If the BRIEF_MEMBER_DESC tag is set to YES (the default) Doxygen will +# include brief member descriptions after the members that are listed in +# the file and class documentation (similar to JavaDoc). +# Set to NO to disable this. + +BRIEF_MEMBER_DESC = YES + +# If the REPEAT_BRIEF tag is set to YES (the default) Doxygen will prepend +# the brief description of a member or function before the detailed description. +# Note: if both HIDE_UNDOC_MEMBERS and BRIEF_MEMBER_DESC are set to NO, the +# brief descriptions will be completely suppressed. + +REPEAT_BRIEF = YES + +# If the ALWAYS_DETAILED_SEC and REPEAT_BRIEF tags are both set to YES then +# Doxygen will generate a detailed section even if there is only a brief +# description. + +ALWAYS_DETAILED_SEC = NO + +# If the FULL_PATH_NAMES tag is set to YES then Doxygen will prepend the full +# path before files name in the file list and in the header files. If set +# to NO the shortest path that makes the file name unique will be used. + +FULL_PATH_NAMES = NO + +# If the FULL_PATH_NAMES tag is set to YES then the STRIP_FROM_PATH tag +# can be used to strip a user defined part of the path. Stripping is +# only done if one of the specified strings matches the left-hand part of +# the path. It is allowed to use relative paths in the argument list. + +STRIP_FROM_PATH = + +# The INTERNAL_DOCS tag determines if documentation +# that is typed after a \internal command is included. If the tag is set +# to NO (the default) then the documentation will be excluded. +# Set it to YES to include the internal documentation. + +INTERNAL_DOCS = NO + +# If the CLASS_DIAGRAMS tag is set to YES (the default) Doxygen will +# generate a class diagram (in Html and LaTeX) for classes with base or +# super classes. Setting the tag to NO turns the diagrams off. + +CLASS_DIAGRAMS = YES + +# If the SOURCE_BROWSER tag is set to YES then a list of source files will +# be generated. Documented entities will be cross-referenced with these sources. + +SOURCE_BROWSER = NO + +# Setting the INLINE_SOURCES tag to YES will include the body +# of functions and classes directly in the documentation. + +INLINE_SOURCES = NO + +# Setting the STRIP_CODE_COMMENTS tag to YES (the default) will instruct +# doxygen to hide any special comment blocks from generated source code +# fragments. Normal C and C++ comments will always remain visible. + +STRIP_CODE_COMMENTS = YES + +# If the CASE_SENSE_NAMES tag is set to NO then Doxygen will only generate +# file names in lower case letters. If set to YES upper case letters are also +# allowed. This is useful if you have classes or files whose names only differ +# in case and if your file system supports case sensitive file names. Windows +# users are adviced to set this option to NO. + +CASE_SENSE_NAMES = YES + +# If the HIDE_SCOPE_NAMES tag is set to NO (the default) then Doxygen +# will show members with their full class and namespace scopes in the +# documentation. If set to YES the scope will be hidden. + +HIDE_SCOPE_NAMES = NO + +# If the VERBATIM_HEADERS tag is set to YES (the default) then Doxygen +# will generate a verbatim copy of the header file for each class for +# which an include is specified. Set to NO to disable this. + +VERBATIM_HEADERS = YES + +# If the SHOW_INCLUDE_FILES tag is set to YES (the default) then Doxygen +# will put list of the files that are included by a file in the documentation +# of that file. + +SHOW_INCLUDE_FILES = YES + +# If the JAVADOC_AUTOBRIEF tag is set to YES (the default) then Doxygen +# will interpret the first line (until the first dot) of a JavaDoc-style +# comment as the brief description. If set to NO, the Javadoc-style will +# behave just like the Qt-style comments. + +JAVADOC_AUTOBRIEF = YES + +# If the INHERIT_DOCS tag is set to YES (the default) then an undocumented +# member inherits the documentation from any documented member that it +# reimplements. + +INHERIT_DOCS = YES + +# If the INLINE_INFO tag is set to YES (the default) then a tag [inline] +# is inserted in the documentation for inline members. + +INLINE_INFO = YES + +# If the SORT_MEMBER_DOCS tag is set to YES (the default) then doxygen +# will sort the (detailed) documentation of file and class members +# alphabetically by member name. If set to NO the members will appear in +# declaration order. + +SORT_MEMBER_DOCS = YES + +# If member grouping is used in the documentation and the DISTRIBUTE_GROUP_DOC +# tag is set to YES, then doxygen will reuse the documentation of the first +# member in the group (if any) for the other members of the group. By default +# all members of a group must be documented explicitly. + +DISTRIBUTE_GROUP_DOC = NO + +# The TAB_SIZE tag can be used to set the number of spaces in a tab. +# Doxygen uses this value to replace tabs by spaces in code fragments. + +TAB_SIZE = 8 + +# The ENABLE_SECTIONS tag can be used to enable conditional +# documentation sections, marked by \if sectionname ... \endif. + +ENABLED_SECTIONS = + +# The GENERATE_TODOLIST tag can be used to enable (YES) or +# disable (NO) the todo list. This list is created by putting \todo +# commands in the documentation. + +GENERATE_TODOLIST = YES + +# The GENERATE_TESTLIST tag can be used to enable (YES) or +# disable (NO) the test list. This list is created by putting \test +# commands in the documentation. + +GENERATE_TESTLIST = YES + +# This tag can be used to specify a number of aliases that acts +# as commands in the documentation. An alias has the form "name=value". +# For example adding "sideeffect=\par Side Effects:\n" will allow you to +# put the command \sideeffect (or @sideeffect) in the documentation, which +# will result in a user defined paragraph with heading "Side Effects:". +# You can put \n's in the value part of an alias to insert newlines. + +ALIASES = + +#--------------------------------------------------------------------------- +# configuration options related to warning and progress messages +#--------------------------------------------------------------------------- + +# The QUIET tag can be used to turn on/off the messages that are generated +# by doxygen. Possible values are YES and NO. If left blank NO is used. + +QUIET = NO + +# The WARNINGS tag can be used to turn on/off the warning messages that are +# generated by doxygen. Possible values are YES and NO. If left blank +# NO is used. + +WARNINGS = YES + +# If WARN_IF_UNDOCUMENTED is set to YES, then doxygen will generate warnings +# for undocumented members. If EXTRACT_ALL is set to YES then this flag will +# automatically be disabled. + +WARN_IF_UNDOCUMENTED = YES + +# The WARN_FORMAT tag determines the format of the warning messages that +# doxygen can produce. The string should contain the $file, $line, and $text +# tags, which will be replaced by the file and line number from which the +# warning originated and the warning text. + +WARN_FORMAT = "$file:$line: $text" + +#--------------------------------------------------------------------------- +# configuration options related to the input files +#--------------------------------------------------------------------------- + +# The INPUT tag can be used to specify the files and/or directories that contain +# documented source files. You may enter file names like "myfile.cpp" or +# directories like "/usr/src/myproject". Separate the files or directories +# with spaces. + +INPUT = $(OSGHOME)/include/osg \ + $(OSGHOME)/include/osgUtil \ + $(OSGHOME)/include/osgDB \ + $(OSGHOME)/include/osgGLUT \ + $(OSGHOME)/src/osg \ + $(OSGHOME)/src/osgUtil \ + $(OSGHOME)/src/osgDB \ + $(OSGHOME)/src/osgGLUT \ + $(OSGHOME)/doc/Doxyfiles/auto_Mainpage + + +# If the value of the INPUT tag contains directories, you can use the +# FILE_PATTERNS tag to specify one or more wildcard pattern (like *.cpp +# and *.h) to filter out the source-files in the directories. If left +# blank all files are included. + +FILE_PATTERNS = + +# The RECURSIVE tag can be used to turn specify whether or not subdirectories +# should be searched for input files as well. Possible values are YES and NO. +# If left blank NO is used. + +RECURSIVE = YES + +# The EXCLUDE tag can be used to specify files and/or directories that should +# excluded from the INPUT source files. This way you can easily exclude a +# subdirectory from a directory tree whose root is specified with the INPUT tag. + +EXCLUDE = + +# If the value of the INPUT tag contains directories, you can use the +# EXCLUDE_PATTERNS tag to specify one or more wildcard patterns to exclude +# certain files from those directories. + +EXCLUDE_PATTERNS = + +# The EXAMPLE_PATH tag can be used to specify one or more files or +# directories that contain example code fragments that are included (see +# the \include command). + +EXAMPLE_PATH = + +# If the value of the EXAMPLE_PATH tag contains directories, you can use the +# EXAMPLE_PATTERNS tag to specify one or more wildcard pattern (like *.cpp +# and *.h) to filter out the source-files in the directories. If left +# blank all files are included. + +EXAMPLE_PATTERNS = + +# The IMAGE_PATH tag can be used to specify one or more files or +# directories that contain image that are included in the documentation (see +# the \image command). + +IMAGE_PATH = + +# The INPUT_FILTER tag can be used to specify a program that doxygen should +# invoke to filter for each input file. Doxygen will invoke the filter program +# by executing (via popen()) the command , where +# is the value of the INPUT_FILTER tag, and is the name of an +# input file. Doxygen will then use the output that the filter program writes +# to standard output. + +INPUT_FILTER = + +#--------------------------------------------------------------------------- +# configuration options related to the alphabetical class index +#--------------------------------------------------------------------------- + +# If the ALPHABETICAL_INDEX tag is set to YES, an alphabetical index +# of all compounds will be generated. Enable this if the project +# contains a lot of classes, structs, unions or interfaces. + +ALPHABETICAL_INDEX = YES + +# If the alphabetical index is enabled (see ALPHABETICAL_INDEX) then +# the COLS_IN_ALPHA_INDEX tag can be used to specify the number of columns +# in which this list will be split (can be a number in the range [1..20]) + +COLS_IN_ALPHA_INDEX = 5 + +# In case all classes in a project start with a common prefix, all +# classes will be put under the same header in the alphabetical index. +# The IGNORE_PREFIX tag can be used to specify one or more prefixes that +# should be ignored while generating the index headers. + +IGNORE_PREFIX = + +#--------------------------------------------------------------------------- +# configuration options related to the HTML output +#--------------------------------------------------------------------------- + +# If the GENERATE_HTML tag is set to YES (the default) Doxygen will +# generate HTML output. + +GENERATE_HTML = YES + +# The HTML_OUTPUT tag is used to specify where the HTML docs will be put. +# If a relative path is entered the value of OUTPUT_DIRECTORY will be +# put in front of it. If left blank `html' will be used as the default path. + +HTML_OUTPUT = html + +# The HTML_HEADER tag can be used to specify a personal HTML header for +# each generated HTML page. If it is left blank doxygen will generate a +# standard header. + +HTML_HEADER = + +# The HTML_FOOTER tag can be used to specify a personal HTML footer for +# each generated HTML page. If it is left blank doxygen will generate a +# standard footer. + +HTML_FOOTER = $(OSGHOME)/doc/Doxyfiles/custom_Footer.html + +# The HTML_STYLESHEET tag can be used to specify a user defined cascading +# style sheet that is used by each HTML page. It can be used to +# fine-tune the look of the HTML output. If the tag is left blank doxygen +# will generate a default style sheet + +HTML_STYLESHEET = + +# If the HTML_ALIGN_MEMBERS tag is set to YES, the members of classes, +# files or namespaces will be aligned in HTML using tables. If set to +# NO a bullet list will be used. + +HTML_ALIGN_MEMBERS = YES + +# If the GENERATE_HTMLHELP tag is set to YES, additional index files +# will be generated that can be used as input for tools like the +# Microsoft HTML help workshop to generate a compressed HTML help file (.chm) +# of the generated HTML documentation. + +GENERATE_HTMLHELP = NO + +# The DISABLE_INDEX tag can be used to turn on/off the condensed index at +# top of each HTML page. The value NO (the default) enables the index and +# the value YES disables it. + +DISABLE_INDEX = NO + +#--------------------------------------------------------------------------- +# configuration options related to the LaTeX output +#--------------------------------------------------------------------------- + +# If the GENERATE_LATEX tag is set to YES (the default) Doxygen will +# generate Latex output. + +GENERATE_LATEX = NO + +# The LATEX_OUTPUT tag is used to specify where the LaTeX docs will be put. +# If a relative path is entered the value of OUTPUT_DIRECTORY will be +# put in front of it. If left blank `latex' will be used as the default path. + +LATEX_OUTPUT = latex + +# If the COMPACT_LATEX tag is set to YES Doxygen generates more compact +# LaTeX documents. This may be useful for small projects and may help to +# save some trees in general. + +COMPACT_LATEX = NO + +# The PAPER_TYPE tag can be used to set the paper type that is used +# by the printer. Possible values are: a4, a4wide, letter, legal and +# executive. If left blank a4wide will be used. + +PAPER_TYPE = a4wide + +# The EXTRA_PACKAGES tag can be to specify one or more names of LaTeX +# packages that should be included in the LaTeX output. + +EXTRA_PACKAGES = + +# The LATEX_HEADER tag can be used to specify a personal LaTeX header for +# the generated latex document. The header should contain everything until +# the first chapter. If it is left blank doxygen will generate a +# standard header. Notice: only use this tag if you know what you are doing! + +LATEX_HEADER = + +# If the PDF_HYPERLINKS tag is set to YES, the LaTeX that is generated +# is prepared for conversion to pdf (using ps2pdf). The pdf file will +# contain links (just like the HTML output) instead of page references +# This makes the output suitable for online browsing using a pdf viewer. + +PDF_HYPERLINKS = NO + +# If the USE_PDFLATEX tag is set to YES, pdflatex will be used instead of +# plain latex in the generated Makefile. Set this option to YES to get a +# higher quality PDF documentation. + +USE_PDFLATEX = NO + +# If the LATEX_BATCHMODE tag is set to YES, doxygen will add the \\batchmode. +# command to the generated LaTeX files. This will instruct LaTeX to keep +# running if errors occur, instead of asking the user for help. +# This option is also used when generating formulas in HTML. + +LATEX_BATCHMODE = NO + +#--------------------------------------------------------------------------- +# configuration options related to the RTF output +#--------------------------------------------------------------------------- + +# If the GENERATE_RTF tag is set to YES Doxygen will generate RTF output +# The RTF output is optimised for Word 97 and may not look very pretty with +# other RTF readers or editors. + +GENERATE_RTF = NO + +# The RTF_OUTPUT tag is used to specify where the RTF docs will be put. +# If a relative path is entered the value of OUTPUT_DIRECTORY will be +# put in front of it. If left blank `rtf' will be used as the default path. + +RTF_OUTPUT = rtf + +# If the COMPACT_RTF tag is set to YES Doxygen generates more compact +# RTF documents. This may be useful for small projects and may help to +# save some trees in general. + +COMPACT_RTF = NO + +# If the RTF_HYPERLINKS tag is set to YES, the RTF that is generated +# will contain hyperlink fields. The RTF file will +# contain links (just like the HTML output) instead of page references. +# This makes the output suitable for online browsing using a WORD or other. +# programs which support those fields. +# Note: wordpad (write) and others do not support links. + +RTF_HYPERLINKS = NO + +# Load stylesheet definitions from file. Syntax is similar to doxygen's +# config file, i.e. a series of assigments. You only have to provide +# replacements, missing definitions are set to their default value. + +RTF_STYLESHEET_FILE = + +#--------------------------------------------------------------------------- +# configuration options related to the man page output +#--------------------------------------------------------------------------- + +# If the GENERATE_MAN tag is set to YES (the default) Doxygen will +# generate man pages + +GENERATE_MAN = NO + +# The MAN_OUTPUT tag is used to specify where the man pages will be put. +# If a relative path is entered the value of OUTPUT_DIRECTORY will be +# put in front of it. If left blank `man' will be used as the default path. + +MAN_OUTPUT = man + +# The MAN_EXTENSION tag determines the extension that is added to +# the generated man pages (default is the subroutine's section .3) + +MAN_EXTENSION = .3 + +#--------------------------------------------------------------------------- +# configuration options related to the XML output +#--------------------------------------------------------------------------- + +# If the GENERATE_XML tag is set to YES Doxygen will +# generate an XML file that captures the structure of +# the code including all documentation. Warning: This feature +# is still experimental and very incomplete. + +GENERATE_XML = NO + +#--------------------------------------------------------------------------- +# Configuration options related to the preprocessor +#--------------------------------------------------------------------------- + +# If the ENABLE_PREPROCESSING tag is set to YES (the default) Doxygen will +# evaluate all C-preprocessor directives found in the sources and include +# files. + +ENABLE_PREPROCESSING = YES + +# If the MACRO_EXPANSION tag is set to YES Doxygen will expand all macro +# names in the source code. If set to NO (the default) only conditional +# compilation will be performed. Macro expansion can be done in a controlled +# way by setting EXPAND_ONLY_PREDEF to YES. + +MACRO_EXPANSION = NO + +# If the EXPAND_ONLY_PREDEF and MACRO_EXPANSION tags are both set to YES +# then the macro expansion is limited to the macros specified with the +# PREDEFINED and EXPAND_AS_PREDEFINED tags. + +EXPAND_ONLY_PREDEF = NO + +# If the SEARCH_INCLUDES tag is set to YES (the default) the includes files +# in the INCLUDE_PATH (see below) will be search if a #include is found. + +SEARCH_INCLUDES = YES + +# The INCLUDE_PATH tag can be used to specify one or more directories that +# contain include files that are not input files but should be processed by +# the preprocessor. + +INCLUDE_PATH = + +# You can use the INCLUDE_FILE_PATTERNS tag to specify one or more wildcard +# patterns (like *.h and *.hpp) to filter out the header-files in the +# directories. If left blank, the patterns specified with FILE_PATTERNS will +# be used. + +INCLUDE_FILE_PATTERNS = + +# The PREDEFINED tag can be used to specify one or more macro names that +# are defined before the preprocessor is started (similar to the -D option of +# gcc). The argument of the tag is a list of macros of the form: name +# or name=definition (no spaces). If the definition and the = are +# omitted =1 is assumed. + +PREDEFINED = + +# If the MACRO_EXPANSION and EXPAND_PREDEF_ONLY tags are set to YES then +# this tag can be used to specify a list of macro names that should be expanded. +# The macro definition that is found in the sources will be used. +# Use the PREDEFINED tag if you want to use a different macro definition. + +EXPAND_AS_DEFINED = + +#--------------------------------------------------------------------------- +# Configuration::addtions related to external references +#--------------------------------------------------------------------------- + +# The TAGFILES tag can be used to specify one or more tagfiles. + +TAGFILES = + +# When a file name is specified after GENERATE_TAGFILE, doxygen will create +# a tag file that is based on the input files it reads. + +GENERATE_TAGFILE = + +# If the ALLEXTERNALS tag is set to YES all external classes will be listed +# in the class index. If set to NO only the inherited external classes +# will be listed. + +ALLEXTERNALS = NO + +# The PERL_PATH should be the absolute path and name of the perl script +# interpreter (i.e. the result of `which perl'). + +PERL_PATH = /usr/bin/perl + +#--------------------------------------------------------------------------- +# Configuration options related to the dot tool +#--------------------------------------------------------------------------- + +# If you set the HAVE_DOT tag to YES then doxygen will assume the dot tool is +# available from the path. This tool is part of Graphviz, a graph visualization +# toolkit from AT&T and Lucent Bell Labs. The other options in this section +# have no effect if this option is set to NO (the default) + +HAVE_DOT = YES + +# If the CLASS_GRAPH and HAVE_DOT tags are set to YES then doxygen +# will generate a graph for each documented class showing the direct and +# indirect inheritance relations. Setting this tag to YES will force the +# the CLASS_DIAGRAMS tag to NO. + +CLASS_GRAPH = YES + +# If the COLLABORATION_GRAPH and HAVE_DOT tags are set to YES then doxygen +# will generate a graph for each documented class showing the direct and +# indirect implementation dependencies (inheritance, containment, and +# class references variables) of the class with other documented classes. + +COLLABORATION_GRAPH = YES + +# If the ENABLE_PREPROCESSING, INCLUDE_GRAPH, and HAVE_DOT tags are set to +# YES then doxygen will generate a graph for each documented file showing +# the direct and indirect include dependencies of the file with other +# documented files. + +INCLUDE_GRAPH = YES + +# If the ENABLE_PREPROCESSING, INCLUDED_BY_GRAPH, and HAVE_DOT tags are set to +# YES then doxygen will generate a graph for each documented header file showing +# the documented files that directly or indirectly include this file + +INCLUDED_BY_GRAPH = YES + +# If the GRAPHICAL_HIERARCHY and HAVE_DOT tags are set to YES then doxygen +# will graphical hierarchy of all classes instead of a textual one. + +GRAPHICAL_HIERARCHY = YES + +# The tag DOT_PATH can be used to specify the path where the dot tool can be +# found. If left blank, it is assumed the dot tool can be found on the path. + +DOT_PATH = + +# The MAX_DOT_GRAPH_WIDTH tag can be used to set the maximum allowed width +# (in pixels) of the graphs generated by dot. If a graph becomes larger than +# this value, doxygen will try to truncate the graph, so that it fits within +# the specified constraint. Beware that most browsers cannot cope with very +# large images. + +MAX_DOT_GRAPH_WIDTH = 1024 + +# The MAX_DOT_GRAPH_HEIGHT tag can be used to set the maximum allows height +# (in pixels) of the graphs generated by dot. If a graph becomes larger than +# this value, doxygen will try to truncate the graph, so that it fits within +# the specified constraint. Beware that most browsers cannot cope with very +# large images. + +MAX_DOT_GRAPH_HEIGHT = 1024 + +#--------------------------------------------------------------------------- +# Configuration::addtions related to the search engine +#--------------------------------------------------------------------------- + +# The SEARCHENGINE tag specifies whether or not a search engine should be +# used. If set to NO the values of all tags below this one will be ignored. + +SEARCHENGINE = NO + +# The CGI_NAME tag should be the name of the CGI script that +# starts the search engine (doxysearch) with the correct parameters. +# A script with this name will be generated by doxygen. + +CGI_NAME = search.cgi + +# The CGI_URL tag should be the absolute URL to the directory where the +# cgi binaries are located. See the documentation of your http daemon for +# details. + +CGI_URL = + +# The DOC_URL tag should be the absolute URL to the directory where the +# documentation is located. If left blank the absolute path to the +# documentation, with file:// prepended to it, will be used. + +DOC_URL = + +# The DOC_ABSPATH tag should be the absolute path to the directory where the +# documentation is located. If left blank the directory on the local machine +# will be used. + +DOC_ABSPATH = + +# The BIN_ABSPATH tag must point to the directory where the doxysearch binary +# is installed. + +BIN_ABSPATH = /usr/local/bin/ + +# The EXT_DOC_PATHS tag can be used to specify one or more paths to +# documentation generated for other projects. This allows doxysearch to search +# the documentation for these projects as well. + +EXT_DOC_PATHS = diff --git a/doc/Doxyfiles/custom_Footer.html b/doc/Doxyfiles/custom_Footer.html new file mode 100644 index 000000000..06a91476d --- /dev/null +++ b/doc/Doxyfiles/custom_Footer.html @@ -0,0 +1,6 @@ +
+
Generated at $datetime for the Open Scene Graph +by doxygen $doxygenversion.
+ + + diff --git a/doc/index.html b/doc/index.html index e0cea4404..ca5a53abe 100644 --- a/doc/index.html +++ b/doc/index.html @@ -2,34 +2,43 @@ - + OSG Documentation - + + + -

-Open Scene Graph Documentation

+Documentation The documentation on the OSG is still in its early stages, and far from complete. If you can't find your answers in what documentation there currently -is, please feel free to post the question on the OSG mailing list. -

Introduction, distribution contents and contacts +is, please feel free to post the question on the OSG mailing list. +

Introduction, distribution contents and contacts +

User documention +

sgv                +Documentation on key binding in sgv (Scene Graph Viewer.)

Reference guides (automatically generated using doc++) -

osg/               +
osg/              core scene graph reference guide. -
osgUtil/          +
osgUtil/          scene graph utilities reference guide. -
osgGLUT/     simple -GLUT based viewer base classes reference guide.
-UML Diagrams +
osgDB/          +scene graph database utilities reference guide. +
osgGLUT/      +simple GLUT based viewer base classes reference guide. +
osgWX/         +WXEvenetAdapter for integrating wxWindows with osgUtil manipulators.
+

Doxygen-generated tarballs are available for download from the website

+

UML Diagrams

osg                UML diagram of the osg core library
osgUtil           -UML diagram of the osg utilities library
-Mind Maps +UML diagram of the osg utilities library

+

Mind Maps

Design Pattern used in the OSG. -
Mission Statement for OSG.
+
Mission Statement for OSG.

diff --git a/include/osg/AlphaFunc b/include/osg/AlphaFunc index 40ec57b4d..4b5a89982 100644 --- a/include/osg/AlphaFunc +++ b/include/osg/AlphaFunc @@ -1,18 +1,30 @@ #ifndef OSG_ALPHAFUNC #define OSG_ALPHAFUNC 1 -#include -#include -#include +#include +#include namespace osg { /** Encapsulte OpenGL glAlphaFunc. */ -class SG_EXPORT AlphaFunc : public Object +class SG_EXPORT AlphaFunc : public StateAttribute { public : + + AlphaFunc(); + virtual bool isSameKindAs(const Object* obj) const { return dynamic_cast(obj)!=0L; } + virtual Object* clone() const { return new AlphaFunc(); } + virtual const char* className() const { return "AlphaFunc"; } + + virtual const Type getType() const { return ALPHAFUNC; } + + virtual void setStateSetModes(StateSet& ds,const GLModeValue value) const + { + ds.setMode(GL_ALPHA_TEST,value); + } + enum ComparisonFunction { NEVER = GL_NEVER, LESS = GL_LESS, @@ -23,38 +35,23 @@ class SG_EXPORT AlphaFunc : public Object GEQUAL = GL_GEQUAL, ALWAYS = GL_ALWAYS }; - - AlphaFunc(); - static AlphaFunc* instance(); - virtual bool isSameKindAs(Object* obj) { return dynamic_cast(obj)!=NULL; } - virtual Object* clone() const { return new AlphaFunc(); } - virtual const char* className() const { return "AlphaFunc"; } - - void setFunction(ComparisonFunction func,float ref) + + inline void setFunction(const ComparisonFunction func,const float ref) { _comparisonFunc = func; _referenceValue = ref; } - ComparisonFunction getFunction() const { return _comparisonFunc; } + inline const ComparisonFunction getFunction() const { return _comparisonFunc; } - float getRefrenceValue() const { return _referenceValue; } - - static void enable(); - static void disable(); - - void apply(); + inline const float getReferenceValue() const { return _referenceValue; } + virtual void apply(State& state) const; + protected: virtual ~AlphaFunc(); - virtual bool readLocalData(Input& fr); - virtual bool writeLocalData(Output& fw); - - bool matchFuncStr(const char* str,ComparisonFunction& func); - const char* getFuncStr(ComparisonFunction func); - ComparisonFunction _comparisonFunc; float _referenceValue; diff --git a/include/osg/Billboard b/include/osg/Billboard index 64bc3009e..a94728462 100644 --- a/include/osg/Billboard +++ b/include/osg/Billboard @@ -1,11 +1,12 @@ #ifndef OSG_BILLBOARD #define OSG_BILLBOARD 1 +#include #include namespace osg { -/** Billboard - a Geode which orientates its child osg::GeoSet's to face +/** Billboard - a Geode which orientates its child osg::Drawable's to face the eye point. Typical uses are for trees, or particle explosions. */ @@ -22,56 +23,66 @@ class SG_EXPORT Billboard : public Geode Billboard(); virtual Object* clone() const { return new Billboard(); } - virtual bool isSameKindAs(Object* obj) { return dynamic_cast(obj)!=NULL; } + virtual bool isSameKindAs(const Object* obj) const { return dynamic_cast(obj)!=NULL; } virtual const char* className() const { return "Billboard"; } virtual void accept(NodeVisitor& nv) { nv.apply(*this); } - void setAxis(const Vec3& axis) { _axis = axis; } - void getAxis(Vec3& axis) const { axis = _axis; } + /** Set the axis about which all the billboard's drawable rotate. */ + inline void setAxis(const Vec3& axis) { _axis = axis; } + /** Get the axis about which all the billboard's drawable rotate. */ + inline const Vec3& getAxis() const { return _axis; } - void setMode(Mode mode) { _mode = mode; } - int getMode() const { return _mode; } + /** Set the billboard rotation mode. */ + inline void setMode(const Mode mode) { _mode = mode; } + /** Get the billboard rotation mode. */ + inline const Mode getMode() const { return _mode; } - void setPos(int i,const Vec3& pos) { _positionList[i] = pos; } - void getPos(int i,Vec3& pos) const { pos = _positionList[i]; } + /** Set the position of specified drawable. */ + inline void setPos(int i,const Vec3& pos) { _positionList[i] = pos; } + /** Get the position of specified drawable. */ + inline const Vec3& getPos(int i) const { return _positionList[i]; } - /** Add GeoSet to Billboard with default position(0,0,0); + /** PositionList represents a list of pivot points for each drawable.*/ + typedef std::vector PositionList; + + /** Get the PostionList from the billboard.*/ + inline PositionList& getPositionList() { return _positionList; } + /** Get a const PostionList from the billboard.*/ + inline const PositionList& getPositionList() const { return _positionList; } + + /** Add Drawable to Billboard with default position(0,0,0); * If gset not NULL and is not contained in Billboard then increment its * reference count, and dirty the bounding box to cause it to recompute on * next getBound() and return true for success. Otherwise return false. */ - virtual bool addGeoSet( GeoSet *gset ); + virtual const bool addDrawable( Drawable *gset ); - /** Add GeoSet to Geode at position pos. + /** Add Drawable to Geode at position pos. * If gset not NULL and is not contained in Billboard then increment its * reference count, and dirty the bounding box to cause it to recompute on * next getBound() and return true for success. Otherwise return false. */ - virtual bool addGeoSet(GeoSet *gset,const Vec3& pos); + virtual const bool addDrawable(Drawable *gset,const Vec3& pos); - /** Remove GeoSet and associated position from Billboard. + /** Remove Drawable and associated position from Billboard. * If gset is contained in Billboard then remove it from the geoset * list and decrement its reference count, and dirty the * bounding box to cause it to recompute on next getBound() and * return true for success. If gset is not found then return false * and do not the reference count of gset is left unchanged. */ - virtual bool removeGeoSet( GeoSet *gset ); + virtual const bool removeDrawable( Drawable *gset ); - void calcRotation(const Vec3& eye_local, const Vec3& pos_local,Matrix& mat); - void calcTransform(const Vec3& eye_local, const Vec3& pos_local,Matrix& mat); + void calcRotation(const Vec3& eye_local, const Vec3& pos_local,Matrix& mat) const; + void calcTransform(const Vec3& eye_local, const Vec3& pos_local,Matrix& mat) const; protected: virtual ~Billboard(); - virtual bool readLocalData(Input& fr); - virtual bool writeLocalData(Output& fw); - - virtual bool computeBound( void ); + virtual const bool computeBound() const; - typedef std::vector PositionList; Mode _mode; Vec3 _axis; diff --git a/include/osg/BoundingBox b/include/osg/BoundingBox index 12b24953b..6cb55ec01 100644 --- a/include/osg/BoundingBox +++ b/include/osg/BoundingBox @@ -29,7 +29,7 @@ class SG_EXPORT BoundingBox _max(-FLT_MAX,-FLT_MAX,-FLT_MAX) {} /** initialize to invalid values to represent an unset bounding box.*/ - void init() + inline void init() { _min.set(FLT_MAX,FLT_MAX,FLT_MAX); _max.set(-FLT_MAX,-FLT_MAX,-FLT_MAX); @@ -37,44 +37,44 @@ class SG_EXPORT BoundingBox /** return true if the bounding box contains valid values, false if the bounding box is effectively unset/empty.*/ - bool isValid() const + inline const bool isValid() const { return _max.x()>=_min.x(); } - float& xMin() { return _min.x(); } - float xMin() const { return _min.x(); } + inline float& xMin() { return _min.x(); } + inline const float xMin() const { return _min.x(); } - float& yMin() { return _min.y(); } - float yMin() const { return _min.y(); } + inline float& yMin() { return _min.y(); } + inline const float yMin() const { return _min.y(); } - float& zMin() { return _min.z(); } - float zMin() const { return _min.z(); } + inline float& zMin() { return _min.z(); } + inline const float zMin() const { return _min.z(); } - float& xMax() { return _max.x(); } - float xMax() const { return _max.x(); } + inline float& xMax() { return _max.x(); } + inline const float xMax() const { return _max.x(); } - float& yMax() { return _max.y(); } - float yMax() const { return _max.y(); } + inline float& yMax() { return _max.y(); } + inline const float yMax() const { return _max.y(); } - float& zMax() { return _max.z(); } - float zMax() const { return _max.z(); } + inline float& zMax() { return _max.z(); } + inline const float zMax() const { return _max.z(); } /** Calculate and return the center of the bounding box.*/ - Vec3 center() const + inline const Vec3 center() const { return (_min+_max)*0.5f; } /** Calculate and return the radius of the bounding box.*/ - float radius() const + inline const float radius() const { return sqrtf(radius2()); } /** Calculate and return the radius squared of the bounding box. Note, radius2() is faster to calculate than radius().*/ - float radius2() const + inline const float radius2() const { return 0.25f*((_max-_min).length2()); } @@ -84,7 +84,7 @@ class SG_EXPORT BoundingBox the first bit toggles between x min and x max, second bit toggles between y min and y max, third bit toggles between z min and z max.*/ - Vec3 corner(unsigned int pos) const + inline const Vec3 corner(unsigned int pos) const { return Vec3(pos&1?_max.x():_min.x(),pos&2?_max.y():_min.y(),pos&4?_max.z():_min.z()); } @@ -102,7 +102,7 @@ class SG_EXPORT BoundingBox void expandBy(const BoundingSphere& sh); /** return true is vertex v is within the box.*/ - bool contains(const Vec3& v) + inline const bool contains(const Vec3& v) const { return isValid() && (v.x()>=_min.x() && v.x()<=_max.x()) && diff --git a/include/osg/BoundingSphere b/include/osg/BoundingSphere index a144b7ae7..3bba443cb 100644 --- a/include/osg/BoundingSphere +++ b/include/osg/BoundingSphere @@ -23,7 +23,7 @@ class SG_EXPORT BoundingSphere BoundingSphere() : _center(0.0f,0.0f,0.0f),_radius(-1.0f) {} /** initialize to invalid values to represent an unset bounding sphere.*/ - void init() + inline void init() { _center.set(0.0f,0.0f,0.0f); _radius = -1.0f; @@ -31,24 +31,25 @@ class SG_EXPORT BoundingSphere /** return true if the bounding sphere contains valid values, false if the bounding sphere is effectively unset.*/ - bool isValid() const { return _radius>=0.0f; } + inline const bool isValid() const { return _radius>=0.0f; } - /** return the const center of the bounding sphere.*/ - const Vec3& center() const { return _center; } /** return the center of the bounding sphere.*/ - Vec3& center() { return _center; } + inline Vec3& center() { return _center; } + /** return the const center of the bounding sphere.*/ + inline const Vec3& center() const { return _center; } + + /** return the radius of the bounding sphere.*/ + inline float& radius() { return _radius; } /** return the const radius of the bounding sphere.*/ - float radius() const { return _radius; } - /** return the radius of the bounding sphere.*/ - float& radius() { return _radius; } + inline const float radius() const { return _radius; } /** return the radius squared. Note, for performance reasons, assumes the calling method has ensured that the sphere is valid before calling radius2(), i.e. has _radius>=0.0, as it does not check th validity of sphere and will eroneously return a positive value.*/ - float radius2() const { return _radius*_radius; } + inline const float radius2() const { return _radius*_radius; } /** If the vertex is outwith the sphere expand to ecompass vertex. Calculates the combination of movement of center and radius which @@ -73,11 +74,18 @@ class SG_EXPORT BoundingSphere void expandRadiusBy(const BoundingSphere& sh); /** return true is vertex v is within the sphere.*/ - bool contains(const Vec3& v) + inline const bool contains(const Vec3& v) const { return isValid() && ((v-_center).length2()<=radius2()); } + /** return true if bounding sphere's intersect each other.*/ + inline const bool intersects( const BoundingSphere& bs ) const + { + return isValid() && bs.isValid() && + ((_center - bs._center).length2() <= (_radius + bs._radius)*(_radius + bs._radius)); + } + }; }; diff --git a/include/osg/Camera b/include/osg/Camera index a6836af55..6320df06c 100644 --- a/include/osg/Camera +++ b/include/osg/Camera @@ -1,17 +1,19 @@ #ifndef OSG_CAMERA #define OSG_CAMERA 1 -#include -#include +#include +#include +#include +#include +#include namespace osg { -/** Camera class for encapsulating the view position and orientation. - * This is the first implementation of osg::Camera class and - * currently is a perspective camera, but in future will be - * a base class from which PerpsectivCamera,FrustumCamera and OrthoCamera - * will be derived. - */ +/** Camera class for encapsulating the view position and orientation and + * projection (lens) used. Creates a projection and modelview matrices + * which can be used to set OpenGL's PROJECTION and MODELVIEW matrices + * represectively. + */ class SG_EXPORT Camera: public osg::Referenced { @@ -20,19 +22,91 @@ class SG_EXPORT Camera: public osg::Referenced Camera(); virtual ~Camera(); + /** Range of projection types. + * OTHO2D is a special case of OTHO where the near and far planes + * are equal to -1 and 1 respectively. + * PRESPECTIVE is a special case of FRUSTUM where the left & right + * and bottom and top and symetrical.*/ + enum ProjectionType + { + ORTHO, + ORTHO2D, + FRUSTUM, + PERSPECTIVE + }; + + /** Get the projection type set by setOtho,setOtho2D,setFrustum, + * and set perspective methods.*/ + const ProjectionType getProjectionType() const { return _projectionType; } + + /** Set a orthographics projection. See glOrtho for further details.*/ + void setOrtho(const double left, const double right, + const double bottom, const double top, + const double zNear, const double zFar); + + /** Set a 2D orthographics projection. See gluOrtho2D for further details.*/ + void setOrtho2D(const double left, const double right, + const double bottom, const double top); + + /** Set a perspective projection. See glFrustum for further details.*/ + void setFrustum(const double left, const double right, + const double bottom, const double top, + const double zNear, const double zFar); + + /** Set a sysmetical perspective projection, See gluPerspective for further details. + * Aspect ratio is defined as width/height.*/ + void setPerspective(const double fovy,const double aspectRatio, + const double zNear, const double zFar); - /** - * Set field of view and window aspect ratio. - * The parameters have the same meaning as their counterparts - * in gluPerspective(fovy,aspectRatio - */ - void setFieldOfView(double fovy,double aspectRatio); - void setFieldOfViewY(double fovy) { _fovy = fovy; } - double getFieldOfViewY() const { return _fovy; } + /** Set the near and far clipping planes.*/ + void setNearFar(const double zNear, const double zFar); - void setAspectRatio(double aspectRatio) { _aspectRatio = aspectRatio; } - double getAspectRatio() const { return _aspectRatio; } + /** Use in combination with adjustAspectRatio, to control + * the change in frustum clipping planes to account for + * changes in windows aspect ratio,*/ + enum AdjustAxis + { + ADJUST_VERTICAL, + ADJUST_HORIZONTAL + }; + + /** Adjust the clipping planes to account for a new window aspcect ratio. + * Typicall used after resizeing a window. Aspect ratio is defined as + * width/height.*/ + void adjustAspectRatio(const double newAspectRatio, const AdjustAxis aa = ADJUST_HORIZONTAL); + + const double left() const; + const double right() const; + const double top() const; + const double bottom() const; + const double zNear() const; + const double zFar() const; + + /** Calculate and return the equivilant fovx for the current project setting. + * This value is only valid for when a symetric persepctive projection exists. + * i.e. getProjectionType()==PERSPECTIVE.*/ + const double calc_fovy() const; + + /** Calculate and return the equivilant fovy for the current project setting. + * This value is only valid for when a symetric persepctive projection exists. + * i.e. getProjectionType()==PERSPECTIVE.*/ + const double calc_fovx() const; + + /** Calculate and return the projection aspect ratio. + * Aspect ratio is defined as width/height.*/ + const double calc_aspectRatio() const; + + const Matrix& getProjectionMatrix() const; + + enum LookAtType + { + USE_HOME_POSITON, + USE_EYE_AND_QUATERNION, + USE_EYE_CENTER_AND_UP + }; + + const LookAtType getLookAtType() const { return _lookAtType; } /** * hardwired home view for now, looking straight down the @@ -41,96 +115,171 @@ class SG_EXPORT Camera: public osg::Referenced void home(); /** - * Set the View, the up vector should be orthogonal to the - * look vector. - */ - void setView(Vec3 eyePoint, - Vec3 lookPoint, - Vec3 upVector); + * Set the View, the up vector should be orthogonal to the look vector. + * setView is now mapped to setLookAt(eye,center,up), and is only + * kept for backwards compatibility. + */ + void setView(const Vec3& eyePoint, + const Vec3& lookPoint, + const Vec3& upVector); + + /** set the position and orientaion of the camera, using the same convention as + * gluLookAt. + */ + void setLookAt(const Vec3& eye, + const Vec3& center, + const Vec3& up); + + /** set the position and orientaion of the camera, using the same convention as + * gluLookAt. + */ + void setLookAt(const double eyeX, const double eyeY, const double eyeZ, + const double centerX, const double centerY, const double centerZ, + const double upX, const double upY, const double upZ); + + /** post multiple the existing eye point and orientation by matrix. + * note, does not affect any ModelTransforms that are applied.*/ + void transformLookAt(const Matrix& matrix); + + void ensureOrthogonalUpVector(); - /** get the eyepoint. */ - const Vec3& getEyePoint() const {return _eyePoint;} + /** get the eye point. */ + inline const Vec3& getEyePoint() const { return _eye; } - /** get the lookpoint. */ - const Vec3& getLookPoint() const {return _lookPoint;} + /** get the center point. */ + inline const Vec3& getCenterPoint() const { return _center; } - /** which way is up? */ - const Vec3& getUpVector() const {return _upVector;} - - /** calculate side vector.*/ - Vec3 getSideVector() const - { - Vec3 sv = (_lookPoint-_eyePoint)^_upVector; - sv.normalize(); - return sv; - } + /** get the up vector */ + inline const Vec3& getUpVector() const { return _up; } /** calculate look vector.*/ - Vec3 getLookVector() const + const Vec3 getLookVector() const; + + /** calculate side vector.*/ + const Vec3 getSideVector() const; + + /** get focal distance.*/ + inline const float getFocalLength() const { return _focalLength; } + + + enum TransformMode { - Vec3 lv = (_lookPoint-_eyePoint); - lv.normalize(); - return lv; - } + EYE_TO_MODEL, + MODEL_TO_EYE, + NO_ATTACHED_TRANSFORM + }; + - /** calculate focal distance.*/ - float getFocalDistance() const - { - return (_lookPoint-_eyePoint).length(); - } + /** Attach a transform matrix which is applied after the camera look at. + * The attached matrix can work in two ways, either as transform of the eye + * into the model coordinates - EYE_TO_MODEL, or as a transform of the + * model to the eye - MODEL_TO_EYE. The former is equivilant to attaching + * a camera internal to the scene graph. The later is equivilant to adding + * a osg::Transform at root of the scene to move the scene to the eye point. + * Typical used in conjunction with the LookAt position set to home, + * in which case it is simply treated as a model view matrix. + * If the same behaviour as IRIS Performer's setViewMat is desired + * then set the LookAt to be (0,0,0),(0,1,0),(0,0,1) since Performer's + * default direction is along the y axis, unlike OpenGL and the default OSG. + * If modelTransfor is NULL then do not use any model transform - just use the + * basic LookAt values. + * note: Camera internals maintains the both EYE_TO_MODEL and MODEL_TO_EYE + * internally and ensures that they are the inverse of one another. However, + * if you modify the attached transform then you must call dirtyTransform, to + * allow the OSG to update matrices accordingly.*/ + void attachTransform(const TransformMode mode, Matrix* modelTransform=0); - /** set the near plane. */ - void setNearPlane(double nearPlane) {_nearPlane=nearPlane;} - - /**get the near plane. */ - double getNearPlane() const {return _nearPlane;} - - /** set the far plane. */ - void setFarPlane(double farPlane) {_farPlane=farPlane;} - - /** get the far plane. */ - double getFarPlane() const {return _farPlane;} + /** must be called after you modify an attachedTransform. */ + void dirtyTransform(); + + Matrix* getTransform(const TransformMode mode); + + const Matrix* getTransform(const TransformMode mode) const; - - /** Set up the OpenGL GL_PROJECTION matrix. - Enters the GL_PROJECTION mode, sets up matrix, then - resets model GL_MODELVIEW, which is by OpenGL convention the default.*/ - void draw_PROJECTION() const; - - /** Set up the OpenGL GL_MODELVIEW matrix. - * Enters the GL_MODELVIEW mode, sets matrix to identity - * and then sets matrix up according to camera, eye point, center - * point and upvector. - */ - void draw_MODELVIEW() const; + const Vec3 getEyePoint_Model() const; + const Vec3 getCenterPoint_Model() const; + const Vec3 getLookVector_Model() const; + const Vec3 getUpVector_Model() const; + const Vec3 getSideVector_Model() const; + + /** Get the ModelView matrix. + * If a ModelTransform is supplied then the ModelView matrix is + * created by multipling the current LookAt by ModelTransform. + * Otherwise it is simply created by using the current LookAt, + * equivialent to using gluLookAt.*/ + const Matrix& getModelViewMatrix() const; + + + void setUseNearClippingPlane(const bool use); + const bool getUseNearClippingPlane() const { return _useNearClippingPlane; } + + void setUseFarClippingPlane(const bool use); + const bool getUseFarClippingPlane() const { return _useFarClippingPlane; } + + /** get the view frustum clipping in model coordinates */ + const ClippingVolume& getClippingVolume() const; - - /** post multiply a camera by matrix.*/ - void mult(const Camera& camera,const Matrix& m); - - /** pre multiply a camera by matrix.*/ - void mult(const Matrix& m,const Camera& camera); - - void ensureOrthogonalUpVector(); + /** Map object coordinates into windows coordinates. + * Equivilant to gluProject(...). */ + const bool project(const Vec3& obj,const int* viewport,Vec3& win) const; + + /** Map window coordinates into object coordinates. + * Equivilant to gluUnProject(...). */ + const bool unproject(const Vec3& win,const int* viewport,Vec3& obj) const; - private: - + protected: + // Disallow copy construction & assignment (for now) Camera(const Camera&); Camera& operator=(const Camera&); - Vec3 _eyePoint; - Vec3 _lookPoint; - Vec3 _upVector; + // projection details. + ProjectionType _projectionType; - double _fovy; - double _aspectRatio; + // note, in Frustum/Perspective mode these values are scaled + // by the zNear from when they were initialised to ensure that + // subsequent changes in zNear do not affect them. + double _left; + double _right; + double _bottom; + double _top; + + double _zNear; + double _zFar; + + + // look at details. + LookAtType _lookAtType; + + Vec3 _eye; + Vec3 _center; + Vec3 _up; + + double _focalLength; + + TransformMode _attachedTransformMode; + ref_ptr _eyeToModelTransform; + ref_ptr _modelToEyeTransform; + + // flags to determin if near and far clipping planes are required. + bool _useNearClippingPlane; + bool _useFarClippingPlane; + + // cached matrix and clipping volume derived from above settings. + mutable bool _dirty; + mutable ref_ptr _projectionMatrix; + mutable ref_ptr _modelViewMatrix; + mutable ClippingVolume _clippingVolume; + + mutable ref_ptr _MP; + mutable ref_ptr _inverseMP; + + void calculateMatricesAndClippingVolume() const; + - double _nearPlane; // No Dougal, these are small... but those... - double _farPlane; // are far away }; diff --git a/include/osg/CullFace b/include/osg/CullFace index 391a07b92..a08fa6b47 100644 --- a/include/osg/CullFace +++ b/include/osg/CullFace @@ -1,46 +1,45 @@ #ifndef OSG_CULLFACE #define OSG_CULLFACE 1 -#include -#include #include +#include +#include namespace osg { -/** Class to globally enable/disable OpenGL's polygon culling mode - (GL_CULL_FACE). +/** Class to globally enable/disable OpenGL's polygon culling mode=. */ -class SG_EXPORT CullFace : public Object +class SG_EXPORT CullFace : public StateAttribute { public : + CullFace(); + virtual bool isSameKindAs(const Object* obj) const { return dynamic_cast(obj)!=0L; } + virtual Object* clone() const { return new CullFace(); } + virtual const char* className() const { return "CullFace"; } + + virtual const Type getType() const { return CULLFACE; } + + virtual void setStateSetModes(StateSet& ds,const GLModeValue value) const + { + ds.setMode(GL_CULL_FACE,value); + } + enum Mode { FRONT = GL_FRONT, BACK = GL_BACK, FRONT_AND_BACK = GL_FRONT_AND_BACK }; - CullFace(); - static CullFace* instance(); - virtual bool isSameKindAs(Object* obj) { return dynamic_cast(obj)!=NULL; } - virtual Object* clone() const { return new CullFace(); } - virtual const char* className() const { return "CullFace"; } - - void setMode(Mode mode) { _mode = mode; } - - /** Enable the polygon culling mode.*/ - static void enable(); - /** Disable the polygon culling mode.*/ - static void disable(); + inline void setMode(const Mode mode) { _mode = mode; } - void apply(); + inline const Mode getMode() const { return _mode; } + + virtual void apply(State& state) const; protected: virtual ~CullFace(); - - virtual bool readLocalData(Input& fr); - virtual bool writeLocalData(Output& fw); Mode _mode; diff --git a/include/osg/Export b/include/osg/Export index 44f9b0ee7..7fa697dee 100644 --- a/include/osg/Export +++ b/include/osg/Export @@ -5,18 +5,6 @@ #pragma warning( disable : 4251 ) #pragma warning( disable : 4275 ) #pragma warning( disable : 4786 ) - -/* Define NULL pointer value */ - -#ifndef NULL -#ifdef __cplusplus -#define NULL 0 -#else -#define NULL ((void *)0) -#endif -#endif - - #endif #if defined(_MSC_VER) @@ -29,4 +17,14 @@ # define SG_EXPORT #endif +/* Define NULL pointer value */ + +#ifndef NULL +#ifdef __cplusplus +#define NULL 0 +#else +#define NULL ((void *)0) +#endif +#endif + #endif diff --git a/include/osg/Fog b/include/osg/Fog index 2f96a2ad6..ac9c34d80 100644 --- a/include/osg/Fog +++ b/include/osg/Fog @@ -1,60 +1,59 @@ #ifndef OSG_FOG #define OSG_FOG 1 -#include -#include #include -#include +#include +#include +#include namespace osg { /** Fog - encapsulates OpenGL fog state. */ -class SG_EXPORT Fog : public Object +class SG_EXPORT Fog : public StateAttribute { public : - enum FogMode { + Fog(); + virtual Object* clone() const { return new Fog(); } + virtual bool isSameKindAs(const Object* obj) const { return dynamic_cast(obj)!=NULL; } + virtual const char* className() const { return "Fog"; } + + virtual const Type getType() const { return FOG; } + + virtual void setStateSetModes(StateSet& ds,const GLModeValue value) const + { + ds.setMode(GL_FOG,value); + } + + enum Mode { LINEAR = GL_LINEAR, EXP = GL_EXP, EXP2 = GL_EXP2 }; - Fog( void ); - static Fog* instance(); - virtual Object* clone() const { return new Fog(); } - virtual bool isSameKindAs(Object* obj) { return dynamic_cast(obj)!=NULL; } - virtual const char* className() const { return "Fog"; } + inline void setMode( const Mode mode ) { _mode = mode; } + inline Mode getMode() const { return _mode; } - static void enable( void ); - static void disable( void ); - void apply( void ); + inline void setDensity( const float density ) { _density = density; } + inline const float getDensity() const { return _density; } - void setMode( uint mode ) { _mode = mode; } - uint getMode( void ) { return _mode; } + inline void setStart( const float start ) { _start = start; } + inline const float getStart() const { return _start; } - void setDensity( float density ) { _density = density; } - float getDensity( void ) { return _density; } + inline void setEnd( const float end ) { _end = end; } + inline const float getEnd() const { return _end; } - void setStart( float start ) { _start = start; } - float getStart( void ) { return _start; } + inline void setColor( const Vec4 &color ) { _color = color; } + inline const Vec4& getColor() const { return _color; } - void setEnd( float end ) { _end = end; } - float getEnd( void ) { return _end; } - - void setColor( Vec4 &color ) - { - _color[0] = color[0]; - _color[1] = color[1]; - _color[2] = color[2]; - _color[3] = color[3]; - } + virtual void apply(State& state) const; protected : - virtual ~Fog( void ); + virtual ~Fog(); - uint _mode; + Mode _mode; float _density; float _start; float _end; diff --git a/include/osg/GL b/include/osg/GL index e2f6c71a3..098bb6d81 100644 --- a/include/osg/GL +++ b/include/osg/GL @@ -1,71 +1,62 @@ #ifndef OSG_GL #define OSG_GL 1 -#ifdef WIN32 +#ifndef WIN32 - // this works with no problems -// #ifndef _WINDOWS_ -// #define WIN32_LEAN_AND_MEAN -// #include -// #endif + // non windows, doesn't require nonesense as seen below :-) + #ifndef __gl_h_ + #include + #endif -// follows lifted from glut.h, to avoid including - -//#if defined(_WIN32) - -// GLUT 3.7 now tries to avoid including -// to avoid name space pollution, but Win32's -// needs APIENTRY and WINGDIAPI defined properly. -# if 0 -# define WIN32_LEAN_AND_MEAN -# include -# else - // XXX This is from Win32's -# ifndef APIENTRY -# define GLUT_APIENTRY_DEFINED -# if (_MSC_VER >= 800) || defined(_STDCALL_SUPPORTED) -# define APIENTRY __stdcall -# else -# define APIENTRY -# endif -# endif - // XXX This is from Win32's -# ifndef CALLBACK -# if (defined(_M_MRX000) || defined(_M_IX86) || defined(_M_ALPHA) || defined(_M_PPC)) && !defined(MIDL_PASS) -# define CALLBACK __stdcall -# else -# define CALLBACK -# endif -# endif - // XXX This is from Win32's and -# ifndef WINGDIAPI -# define GLUT_WINGDIAPI_DEFINED -# define WINGDIAPI __declspec(dllimport) -# endif - // XXX This is from Win32's -# ifndef _WCHAR_T_DEFINED -typedef unsigned short wchar_t; -# define _WCHAR_T_DEFINED -# endif -# endif + // required for compatibility with glext.h sytle function definitions of + // OpenGL extensions, such as in src/osg/Point.cpp. + #ifndef APIENTRY + #define APIENTRY + #endif +#else + // Under windows avoid including + // to avoid name space pollution, but Win32's + // needs APIENTRY and WINGDIAPI defined properly. + // F + # if 0 + # define WIN32_LEAN_AND_MEAN + # include + # else + // XXX This is from Win32's + # ifndef APIENTRY + # define GLUT_APIENTRY_DEFINED + # if (_MSC_VER >= 800) || defined(_STDCALL_SUPPORTED) + # define APIENTRY __stdcall + # else + # define APIENTRY + # endif + # endif + // XXX This is from Win32's + # ifndef CALLBACK + # if (defined(_M_MRX000) || defined(_M_IX86) || defined(_M_ALPHA) || defined(_M_PPC)) && !defined(MIDL_PASS) + # define CALLBACK __stdcall + # else + # define CALLBACK + # endif + # endif + // XXX This is from Win32's and + # ifndef WINGDIAPI + # define GLUT_WINGDIAPI_DEFINED + # define WINGDIAPI __declspec(dllimport) + # endif + // XXX This is from Win32's + # ifndef _WCHAR_T_DEFINED + typedef unsigned short wchar_t; + # define _WCHAR_T_DEFINED + # endif + # endif #ifndef __gl_h_ #include #endif - #ifndef __glu_h__ - #include - #endif - -#else - // GL_GLEXT_LEGACY required by some Linux OpenGL implementations - // to allow compilation of glPointParameterfEXT. - #define GL_GLEXT_LEGACY 1 - #include - #include - #include #endif #endif // __osgGL_h diff --git a/include/osg/GeoSet b/include/osg/GeoSet index ac040a004..434a65110 100644 --- a/include/osg/GeoSet +++ b/include/osg/GeoSet @@ -1,26 +1,21 @@ #ifndef OSG_GEOSET #define OSG_GEOSET 1 -#include #include -#include -#include -#include +#include +#include +#include namespace osg { - -class Input; -class Output; - /** Encapsulates OpenGL drawing primitives, geometry and optional binding of normal, color and texture coordinates. Used for representing the visible objects in the scene. State attributes - for a GeoSet are maintained in GeoState which the GeoSet maintains - a referenced counted pointer to. Both GeoSet's and GeoState's can + for a GeoSet are maintained in StateSet which the GeoSet maintains + a referenced counted pointer to. Both GeoSet's and StateSet's can be shared for optimal memory usage and graphics performance. */ -class SG_EXPORT GeoSet : public Object +class SG_EXPORT GeoSet : public Drawable { public: @@ -67,201 +62,275 @@ class SG_EXPORT GeoSet : public Object IA_T4F_C4F_N3F_V4F }; + + struct IndexPointer + { + + uint _size; + bool _is_ushort; + union + { + ushort* _ushort; + uint* _uint; + } _ptr; + + IndexPointer() { _size=0;_is_ushort=true;_ptr._ushort = (ushort*)0; } + + inline const bool operator == (const IndexPointer& ip) const + { + return _size == ip._size && + _is_ushort == ip._is_ushort && + _ptr._ushort == ip._ptr._ushort; + } + + inline const bool valid() const + { + return _ptr._ushort != (ushort*)0; + } + + inline const bool null() const + { + return _ptr._ushort == (ushort*)0; + } + + inline void setToNull() + { + _size = 0; + _is_ushort = true; + _ptr._ushort = (ushort*)0; + } + + inline void set(uint size,ushort* data) + { + _size = size; + _is_ushort = true; + _ptr._ushort = data; + } + + + void set(const uint size,uint* data) + { + _size = size; + _is_ushort = false; + _ptr._uint = data; + } + + inline const uint maxIndex() const + { + uint max = 0; + if (_is_ushort) + { + for(uint ai = 0; ai < _size; ai++ ) + if( _ptr._ushort[ai] > max ) max = _ptr._ushort[ai]; + } + else + { + for(uint ai = 0; ai < _size; ai++ ) + if( _ptr._uint[ai] > max ) max = _ptr._uint[ai]; + } + return max; + } + + inline const uint operator [] (const uint pos) const + { + if (_is_ushort) return _ptr._ushort[pos]; + else return _ptr._uint[pos]; + } + + }; + GeoSet(); - static GeoSet* instance(); virtual Object* clone() const { return new GeoSet(); } - virtual bool isSameKindAs(Object* obj) { return dynamic_cast(obj)!=NULL; } - virtual const char* className() const { return "Geoset"; } + virtual bool isSameKindAs(const Object* obj) const { return dynamic_cast(obj)!=NULL; } + virtual const char* className() const { return "GeoSet"; } // data access methods. - void setNumPrims( int n ) { _numprims = n; } - int getNumPrims( void ) { return _numprims; } + inline void setNumPrims( const int n ) { _numprims = n; } + inline const int getNumPrims() const { return _numprims; } - void setPrimType( PrimitiveType type ); - PrimitiveType getPrimType( void ) { return _primtype; } + void setPrimType( const PrimitiveType type ); + inline const PrimitiveType getPrimType() const { return _primtype; } - void setPrimLengths( int *lens ) { _primLengths = lens; } - int *getPrimLengths( void ) { return _primLengths; } + inline void setPrimLengths( int *lens ) { _primLengths = lens; } + inline int *getPrimLengths() { return _primLengths; } + inline const int *getPrimLengths() const { return _primLengths; } void computeNumVerts(); /** get the number of coords required by the defined primitives. */ - int getNumCoords() { return _numcoords; } + inline const int getNumCoords() const { return _numcoords; } /** get a pointer to Vec3 coord array. */ - Vec3* getCoords() { return _coords; } + inline Vec3* getCoords() { return _coords; } + /** get a const pointer to Vec3 coord array. */ + inline const Vec3* getCoords() const { return _coords; } /** get the number of indices required by the defined primitives. */ - int getNumIndices() { return _numindices; } + inline const int getNumCoordIndices() const { return _cindex._size; } /** get the coord index array. */ - ushort* getCIndex() { return _cindex; } + inline IndexPointer& getCoordIndices() { return _cindex; } + /** get the const coord index array. */ + inline const IndexPointer& getCoordIndices() const { return _cindex; } /** set the coords (i.e the geometry) of the geoset.*/ void setCoords( Vec3 *cp ); - /** set the coords (i.e the geometry) and indices of the geoset.*/ + /** set the coords (i.e the geometry) and ushort indices of the geoset. + To reduce memory footprint and bandwidth for small datasets it is + recommended the ushort undices are used instead of unit indices.*/ void setCoords( Vec3 *cp, ushort *ci ); + /** set the coords (i.e the geometry) and uint indices of the geoset. + Unless your data set exceeds 65536 indices prefer ushort indices + over uint indices, only use this unit indices version if neccessary.*/ + void setCoords( Vec3 *cp, uint *ci ); + /** set the coords (i.e the geometry) and indices of the geoset.*/ + void setCoords( Vec3 *cp, IndexPointer& ip ); /** get the number of normals required by the defined primitives and normals binding.*/ - int getNumNormals() { return _numnormals; } + inline const int getNumNormals() const { return _numnormals; } /** get a pointer to Vec3 normal array. */ - Vec3* getNormals() { return _normals; } + inline Vec3* getNormals() { return _normals; } + /** get a const pointer to Vec3 normal array. */ + inline const Vec3* getNormals() const { return _normals; } /** get the number of normal indices required by the defined primitives and normals binding.*/ - int getNumNIndices() { return _numnindices; } + inline int getNumNormalIndices() const { return _nindex._size; } /** get the normal index array. */ - ushort* getNIndex() { return _nindex; } + inline IndexPointer& getNormalIndices() { return _nindex; } + /** get the const normal index array. */ + inline const IndexPointer& getNormalIndices() const { return _nindex; } /** set the normals of the geoset.*/ void setNormals( Vec3 *np ); /** set the normals and normal indices of the geoset.*/ void setNormals( Vec3 *np, ushort *ni ); + /** set the normals and normal indices of the geoset.*/ + void setNormals( Vec3 *np, uint *ni ); + /** set the normals and normal indices of the geoset.*/ + void setNormals( Vec3 *np, IndexPointer& ip ); /** set the normals binding to the vertices/primitives/overall.*/ - void setNormalBinding( BindingType binding ); - BindingType getNormalBinding() { return _normal_binding; } + void setNormalBinding( const BindingType binding ); + inline const BindingType getNormalBinding() const { return _normal_binding; } /** get the number of colors required by the defined primitives and color binding.*/ - int getNumColors() { return _numcolors; } + inline const int getNumColors() const { return _numcolors; } /** get a pointer to Vec4 color array. */ - Vec4* getColors() { return _colors; } + inline Vec4* getColors() { return _colors; } + /** get a pointer to Vec4 color array. */ + inline const Vec4* getColors() const { return _colors; } /** get the number of colors indices required by the defined primitives and color binding.*/ - int getNumCIndices() { return _numcindices; } + inline int getNumColorIndices() const { return _colindex._size; } /** get the color index array. */ - ushort* getColIndex() { return _colindex; } + inline IndexPointer& getColorIndices() { return _colindex; } + /** get the const color index array. */ + inline const IndexPointer& getColorIndices() const { return _colindex; } /** set the colors of the geoset.*/ - void setColors( Vec4 *lp ); + void setColors( Vec4 *cp ); /** set the colors and color indices of the geoset.*/ - void setColors( Vec4 *lp, ushort *li ); + void setColors( Vec4 *cp, ushort *li ); + /** set the colors and color indices of the geoset.*/ + void setColors( Vec4 *cp, uint *li ); + /** set the colors and color indices of the geoset.*/ + void setColors( Vec4 *cp, IndexPointer& ip ); /** set the color binding to the vertices/primitives/overall.*/ void setColorBinding( BindingType binding ); - BindingType getColorBinding() { return _color_binding; } + inline BindingType getColorBinding() const { return _color_binding; } /** get the number of texture coords required by the defined primitives and textures binding.*/ - int getNumTCoords() { return _numtcoords; } + inline const int getNumTextureCoords() const { return _numtcoords; } /** get a pointer to Vec4 color array. */ - Vec2* getTCoords() { return _tcoords; } + inline Vec2* getTextureCoords() { return _tcoords; } + /** get a pointer to Vec4 color array. */ + inline const Vec2* getTextureCoords() const { return _tcoords; } /** get the number of texture coord indices required by the defined primitives and texture binding.*/ - int getNumTIndices() { return _numtindices; } + inline const int getNumTextureIndices() const { return _tindex._size; } /** get the texture index array. */ - ushort* getTIndex() { return _tindex; } + inline IndexPointer& getTextureIndices() { return _tindex; } + /** get the texture index array. */ + inline const IndexPointer& getTextureIndices() const { return _tindex; } /** set the texture coords of the geoset.*/ void setTextureCoords( Vec2 *tc ); /** set the texture coords and texture coord indices of the geoset.*/ void setTextureCoords( Vec2 *tc, ushort *ti ); + /** set the texture coords and texture coord indices of the geoset.*/ + void setTextureCoords( Vec2 *tc, uint *ti ); + /** set the texture coords and texture indices of the geoset.*/ + void setTextureCoords( Vec2 *tc, IndexPointer& ip ); /** set the texture coord binding to the vertices/primitives/overall.*/ - void setTextureBinding( BindingType binding ); - BindingType getTextureBinding() { return _texture_binding; } - - void setInterleavedArray( InterleaveArrayType format, float *ia ); - void setInterleavedArray( InterleaveArrayType format, float *ia, ushort *iai ); - - void setGeoState(GeoState *state) { _state = state; } - GeoState* getGeoState() const { return _state.get();} - - - /** When set to true, force the draw method to use OpenGL Display List for rendering. - If false rendering directly. If the display list has not been already - compile the next call to draw will automatically create the display list.*/ - void setUseDisplayList(bool flag); - - /** Return whether OpenGL display lists are being used for rendering.*/ - bool getUseDisplayList() { return _useDisplayList; } - - /** Force a recompile on next draw() of any OpenGL display list associated with this geoset.*/ - void dirtyDisplayList(); - - /** get bounding box of geoset. - * Note, now made virtual to make it possible to implement user-drawn - * objects albiet so what crudely, to be improved later. - */ - virtual const BoundingBox& getBound() ; - - /** draw geoset. - * If the geoset has _useDisplayList set to true then use an OpenGL display - * list, automatically compiling one if required. - * Otherwise call drawImmediateMode(). - * Note, draw method should not be overiden in subclasses as it - * manages the optional display list. - */ - void draw( void ); + void setTextureBinding( const BindingType binding ); + inline const BindingType getTextureBinding() const { return _texture_binding; } + /** get the number of texture coords required by the defined primitives and textures binding.*/ + inline const int getNumInterleavedCoords() const { return _numcoords; } + /** get a pointer to interleaved float array. */ + inline void* getInterleavedArray() { return _iarray; } + /** get a const pointer to interleaved float array. */ + inline const void* getInterleavedArray() const { return _iarray; } + /** get the number of texture coord indices required by the defined primitives and texture binding.*/ + inline const int getNumIterleavedIndices() const { return _iaindex._size; } + /** get the texture index array. */ + inline IndexPointer& getInterleavedIndices() { return _iaindex; } + /** get the interleaved index array. */ + inline const IndexPointer& getInterleavedIndices() const { return _iaindex; } + /** get the interleaved array storage format. */ + inline const InterleaveArrayType getInterleavedFromat() const { return _iaformat; } + + /** set the interleaved arrays of the geoset.*/ + void setInterleavedArray( const InterleaveArrayType format, float *ia ); + void setInterleavedArray( const InterleaveArrayType format, float *ia, ushort *iai ); + void setInterleavedArray( const InterleaveArrayType format, float *ia, uint *iai ); + void setInterleavedArray( const InterleaveArrayType format, float *ia, IndexPointer& iai ); /** draw geoset directly ignoring an OpenGL display list which could be attached. * This is the internal draw method which does the drawing itself, * and is the method to override when deriving from GeoSet for user-drawn objects. */ - virtual void drawImmediateMode(); + virtual void drawImmediateMode(State& state); - /** Immediately compile this geoset into an OpenGL Display List, set _useDisplayList to true.*/ - void compile( void ); - - bool check(); + const bool check() const; protected: - GeoSet(const GeoSet&):Object() {} + GeoSet(const GeoSet&):Drawable() {} GeoSet& operator = (const GeoSet&) { return *this;} virtual ~GeoSet(); - bool matchBindingTypeStr(const char* str,BindingType& mode); - const char* getBindingTypeStr(BindingType mode); - - virtual bool readLocalData(Input& fr); - virtual bool writeLocalData(Output& fw); - - private : - + virtual const bool computeBound() const; + int _numprims; PrimitiveType _primtype; int _needprimlen; unsigned int _oglprimtype; int *_primLengths; - int _numverts; unsigned char _primlength; unsigned char _flat_shaded_skip; - int _numcoords; - int _numindices; - Vec3 *_coords; - ushort *_cindex; + int _numcoords; + Vec3 *_coords; + IndexPointer _cindex; - int _numnormals; - int _numnindices; - Vec3 *_normals; - ushort *_nindex; - BindingType _normal_binding; + BindingType _normal_binding; + int _numnormals; + Vec3 *_normals; + IndexPointer _nindex; - int _numcolors; - int _numcindices; - Vec4 *_colors; - ushort *_colindex; - BindingType _color_binding; + BindingType _color_binding; + int _numcolors; + Vec4 *_colors; + IndexPointer _colindex; - int _numtcoords; - int _numtindices; - Vec2 *_tcoords; - ushort *_tindex; - BindingType _texture_binding; + BindingType _texture_binding; + int _numtcoords; + Vec2 *_tcoords; + IndexPointer _tindex; - void *_iarray; - ushort *_iaindex; + void *_iarray; + IndexPointer _iaindex; InterleaveArrayType _iaformat; unsigned int _ogliaformat; - /** return the bbbbffff composition required for an interleaved array row.*/ - const char* getInterleavedRowComposition(InterleaveArrayType at) const; - /** return the number of bytes required for an interleaved array row.*/ - int getInterleavedRowLength(InterleaveArrayType at) const; int _fast_path; - ref_ptr _state; - - bool _useDisplayList; - uint _globj; - - BoundingBox _bbox; - int _bbox_computed; - - void computeBound( void ); + void set_fast_path( void ); void draw_fast_path( void ); void draw_alternate_path( void ); @@ -279,21 +348,47 @@ void for_each_triangle(GeoSet& gset,T& op) case(GeoSet::TRIANGLE_STRIP): case(GeoSet::FLAT_TRIANGLE_STRIP): { - if (gset.getCIndex()) + if (gset.getCoordIndices().valid()) { - ushort* iptr = gset.getCIndex(); - Vec3* vptr = gset.getCoords(); - const int numPrim = gset.getNumPrims(); - for(int i=0; i0) + ushort* iptr = gset.getCoordIndices()._ptr._ushort; + Vec3* vptr = gset.getCoords(); + const int numPrim = gset.getNumPrims(); + for(int i=0; i0) { - op(start,vptr[*(iptr)],vptr[*(iptr+1)]); + const Vec3& start = vptr[*(iptr)]; + ushort* iend = iptr+primLength; ++iptr; + for(int j = 2; j < primLength; ++j ) + { + op(start,vptr[*(iptr)],vptr[*(iptr+1)]); + ++iptr; + } + iptr=iend; + } + } + } + else + { + uint* iptr = gset.getCoordIndices()._ptr._uint; + Vec3* vptr = gset.getCoords(); + const int numPrim = gset.getNumPrims(); + for(int i=0; i0) + { + const Vec3& start = vptr[*(iptr)]; + uint* iend = iptr+primLength; + ++iptr; + for(int j = 2; j < primLength; ++j ) + { + op(start,vptr[*(iptr)],vptr[*(iptr+1)]); + ++iptr; + } + iptr=iend; } - iptr=iend; } } } diff --git a/include/osg/Geode b/include/osg/Geode index 24e268c65..dcbbbd3e2 100644 --- a/include/osg/Geode +++ b/include/osg/Geode @@ -1,70 +1,69 @@ #ifndef OSG_GEODE #define OSG_GEODE 1 -#include - #include -#include #include - -#include +#include namespace osg { -/** Leaf Node for grouping GeoSets.*/ +/** Leaf Node for grouping Drawables.*/ class SG_EXPORT Geode : public Node { public: - typedef std::vector< ref_ptr > GeoSetList; + typedef std::vector< ref_ptr > DrawableList; Geode(); virtual Object* clone() const { return new Geode(); } - virtual bool isSameKindAs(Object* obj) { return dynamic_cast(obj)!=NULL; } + virtual bool isSameKindAs(const Object* obj) const { return dynamic_cast(obj)!=NULL; } virtual const char* className() const { return "Geode"; } virtual void accept(NodeVisitor& nv) { nv.apply(*this); } - /** Add GeoSet to Geode. + /** Add Drawable to Geode. * If gset is not NULL and is not contained in Geode then increment its - * reference count, add it to the geosets list and dirty the bounding + * reference count, add it to the drawables list and dirty the bounding * sphere to force it to recompute on next getBound() and return true for success. * Otherwise return false. */ - virtual bool addGeoSet( GeoSet *gset ); + virtual const bool addDrawable( Drawable *drawable ); - /** Remove GeoSet from Geode. + /** Remove Drawable from Geode. * If gset is contained in Geode then remove it from the geoset * list and decrement its reference count, and dirty the * bounding sphere to force it to recompute on next getBound() and * return true for success. If gset is not found then return false * and do not change the reference count of gset. */ - virtual bool removeGeoSet( GeoSet *gset ); + virtual const bool removeDrawable( Drawable *drawable ); - /** Replace specified GeoSet with another GeoSet. + /** Replace specified Drawable with another Drawable. * Decrement the reference count origGSet and increments the * reference count of newGset, and dirty the bounding sphere * to force it to recompute on next getBound() and returns true. - * If origGeoSet is not found then return false and do not + * If origDrawable is not found then return false and do not * add newGset. If newGset is NULL then return false and do * not remove origGset. */ - virtual bool replaceGeoSet( GeoSet *origGset, GeoSet *newGset ); + virtual const bool replaceDrawable( Drawable *origDraw, Drawable *newDraw ); /** return the number of geoset's.*/ - int getNumGeosets( void ) const { return _geosets.size(); } + inline const int getNumDrawables() const { return _drawables.size(); } /** return geoset at position i.*/ - GeoSet* getGeoSet( int i ) { return _geosets[i].get(); } + inline Drawable* getDrawable( const int i ) { return _drawables[i].get(); } + + /** return geoset at position i.*/ + inline const Drawable* getDrawable( const int i ) const { return _drawables[i].get(); } /** return true is geoset is contained within Geode.*/ - bool containsGeoSet( GeoSet* gset) + inline const bool containsDrawable(const Drawable* gset) const { - for (GeoSetList::iterator itr=_geosets.begin(); - itr!=_geosets.end(); + for (DrawableList::const_iterator itr=_drawables.begin(); + itr!=_drawables.end(); ++itr) { if (itr->get()==gset) return true; @@ -72,34 +71,46 @@ class SG_EXPORT Geode : public Node return false; } - /** return the iterator postion for specified GeoSet. + /** return the iterator postion for specified Drawable. * return _geoset.end() if gset not is contained in Geode. */ - GeoSetList::iterator findGeoSet( GeoSet* gset) + inline DrawableList::iterator findDrawable(const Drawable* gset) { - for (GeoSetList::iterator itr=_geosets.begin(); - itr!=_geosets.end(); + for (DrawableList::iterator itr=_drawables.begin(); + itr!=_drawables.end(); ++itr) { if (itr->get()==gset) return itr; } - return _geosets.end(); + return _drawables.end(); + } + + /** return the const_iterator postion for specified Drawable. + * return _geoset.end() if gset not is contained in Geode. + */ + inline DrawableList::const_iterator findDrawable(const Drawable* gset) const + { + + for (DrawableList::const_iterator itr=_drawables.begin(); + itr!=_drawables.end(); + ++itr) + { + if (itr->get()==gset) return itr; + } + return _drawables.end(); } /** complile OpenGL Display List for each geoset.*/ - void compileGeoSets( void ); + void compileDrawables(State& state); protected: virtual ~Geode(); - virtual bool readLocalData(Input& fr); - virtual bool writeLocalData(Output& fw); + virtual const bool computeBound() const; - virtual bool computeBound( void ); - - GeoSetList _geosets; + DrawableList _drawables; }; diff --git a/include/osg/Group b/include/osg/Group index 5fa9abf6b..42b8bf65a 100644 --- a/include/osg/Group +++ b/include/osg/Group @@ -4,12 +4,10 @@ #include #include -#include - namespace osg { /** General group node which maintains a list of children. - Children are reference counted to allow children to be shared + Children are reference counted. This allows children to be shared with memory management handled automatically via osg::Referenced. */ class SG_EXPORT Group : public Node @@ -21,7 +19,7 @@ class SG_EXPORT Group : public Node Group(); virtual Object* clone() const { return new Group(); } - virtual bool isSameKindAs(Object* obj) { return dynamic_cast(obj)!=NULL; } + virtual bool isSameKindAs(const Object* obj) const { return dynamic_cast(obj)!=NULL; } virtual const char* className() const { return "Group"; } virtual void accept(NodeVisitor& nv) { nv.apply(*this); } @@ -31,7 +29,7 @@ class SG_EXPORT Group : public Node * If node is not NULL and is not contained in Group then increment its * reference count, add it to the child list and dirty the bounding * sphere to force it to recompute on next getBound() and return true for success. - * Otherwise return false. + * Otherwise return false. Scene nodes can't be added as child nodes. */ virtual bool addChild( Node *child ); @@ -50,21 +48,24 @@ class SG_EXPORT Group : public Node * to force it to recompute on next getBound() and returns true. * If origNode is not found then return false and do not * add newNode. If newNode is NULL then return false and do - * not remove origNode. + * not remove origNode. Also returns false if newChild is a Scene node. */ virtual bool replaceChild( Node *origChild, Node* newChild ); /** return the number of chilren nodes.*/ - int getNumChildren( void ) { return _children.size(); } + inline const int getNumChildren() const { return _children.size(); } /** return child node at position i.*/ - Node *getChild( int i ) { return _children[i].get(); } + inline Node *getChild( const int i ) { return _children[i].get(); } - /** return true is node is contained within Group.*/ - bool containsNode( Node* node ) + /** return child node at position i.*/ + inline const Node *getChild( const int i ) const { return _children[i].get(); } + + /** return true if node is contained within Group.*/ + inline bool containsNode( const Node* node ) const { - for (ChildList::iterator itr=_children.begin(); + for (ChildList::const_iterator itr=_children.begin(); itr!=_children.end(); ++itr) { @@ -73,12 +74,12 @@ class SG_EXPORT Group : public Node return false; } + /** return the iterator postion for specified Node. * return _chilren.end() if node is not contained in Group. */ - ChildList::iterator findNode( Node* node ) + inline ChildList::iterator findNode( const Node* node ) { - for (ChildList::iterator itr=_children.begin(); itr!=_children.end(); ++itr) @@ -88,16 +89,28 @@ class SG_EXPORT Group : public Node return _children.end(); } + /** return the const_iterator postion for specified Node. + * return _chilren.end() if node is not contained in Group. + */ + inline ChildList::const_iterator findNode( const Node* node ) const + { + for (ChildList::const_iterator itr=_children.begin(); + itr!=_children.end(); + ++itr) + { + if (itr->get()==node) return itr; + } + return _children.end(); + } + protected: virtual ~Group(); - virtual bool readLocalData(Input& fr); - virtual bool writeLocalData(Output& fw); + virtual const bool computeBound() const; ChildList _children; - bool computeBound( void ); }; diff --git a/include/osg/Image b/include/osg/Image index e395de8a3..e75aec80f 100644 --- a/include/osg/Image +++ b/include/osg/Image @@ -1,14 +1,14 @@ +// -*-c++-*- + #ifndef OSG_IMAGE #define OSG_IMAGE 1 #include -#include + +#include namespace osg { -class Output; -class Input; - /** Image class for encapsulating the storage texture image data.*/ class SG_EXPORT Image : public Object { @@ -18,50 +18,56 @@ class SG_EXPORT Image : public Object Image(); virtual Object* clone() const { return new Image(); } - virtual bool isSameKindAs(Object* obj) { return dynamic_cast(obj)!=NULL; } + virtual bool isSameKindAs(const Object* obj) const { return dynamic_cast(obj)!=0; } virtual const char* className() const { return "Image"; } - const char* getFileName() { return _fileName; } - void setFileName(const char* fileName); + inline const std::string& getFileName() const { return _fileName; } + void setFileName(const std::string& fileName); /** set the image data and format. - * note, when no packing value is negative (the default is -1) this method assumes + * note, when the packing value is negative (the default is -1) this method assumes * a _packing width of 1 if the width is not a multiple of 4, * otherwise automatically sets to _packing to 4. If a postive * value of packing is supplied than _packing is simply set to that value. */ - void setImage(int s,int t,int r, - int internalFormat, - unsigned int pixelFormat, - unsigned int dataType, + void setImage(const int s,const int t,const int r, + const int internalFormat, + const unsigned int pixelFormat, + const unsigned int dataType, unsigned char *data, - int packing=-1); + const int packing=-1); /** Width of image.*/ - int s() { return _s; } + inline const int s() const { return _s; } /** Height of image.*/ - int t() { return _t; } + inline const int t() const { return _t; } /** Depth of image.*/ - int r() { return _r; } + inline const int r() const { return _r; } - int internalFormat() { return _internalFormat; } - unsigned int pixelFormat() { return _pixelFormat; } - unsigned int dataType() { return _dataType; } - unsigned int packing() { return _packing; } + inline const int internalFormat() const { return _internalFormat; } + inline const unsigned int pixelFormat() const { return _pixelFormat; } + inline const unsigned int dataType() const { return _dataType; } + inline const unsigned int packing() const { return _packing; } /** raw image data.*/ - unsigned char *data() { return _data; } + inline unsigned char *data() { return _data; } + /** raw const image data.*/ + inline const unsigned char *data() const { return _data; } + /** Scale image to specified size. */ - void scaleImage(int s,int t,int r); + void scaleImage(const int s,const int t,const int r); /** Ensure image dimensions are a power of two. * Mip Mapped texture require the image dimensions to be * power of two. */ void ensureDimensionsArePowerOfTwo(); - + + /** Get modified tag value. */ + inline const unsigned int getModifiedTag() const { return _modifiedTag; } + protected : virtual ~Image(); @@ -69,10 +75,7 @@ class SG_EXPORT Image : public Object // Image(const Image&) {} // Image& operator = (const Image& image) {} - virtual bool readLocalData(Input& fr); - virtual bool writeLocalData(Output& fw); - - char* _fileName; + std::string _fileName; int _s, _t, _r; int _internalFormat; unsigned int _pixelFormat; @@ -80,18 +83,21 @@ class SG_EXPORT Image : public Object unsigned int _packing; unsigned char *_data; + unsigned int _modifiedTag; }; class Geode; -/** Convinience function to be used by images loaders to generate a valid geode to return for readNode(). - * Use the images s and t values scale the dimensions of the image. - */ +/** Convenience function to be used by images loaders to generate a valid geode + * to return for readNode(). + * Use the images s and t values scale the dimensions of the image. + */ SG_EXPORT extern Geode* createGeodeForImage(Image* image); -/** Convinience function to be used by images loaders to generate a valid geode to return for readNode(). - * Use the specified s and t values scale the dimensions of the image. - */ -SG_EXPORT extern Geode* createGeodeForImage(Image* image,float s,float t); +/** Convenience function to be used by images loaders to generate a valid geode + * to return for readNode(). + * Use the specified s and t values scale the dimensions of the image. + */ +SG_EXPORT extern Geode* createGeodeForImage(Image* image,const float s,const float t); }; diff --git a/include/osg/LOD b/include/osg/LOD index d6c6fb8e1..7dd1d7014 100644 --- a/include/osg/LOD +++ b/include/osg/LOD @@ -1,9 +1,7 @@ #ifndef OSG_LOD #define OSG_LOD 1 -#include - -#include +#include namespace osg { @@ -20,7 +18,7 @@ class SG_EXPORT LOD : public Group LOD() {} virtual Object* clone() const { return new LOD(); } - virtual bool isSameKindAs(Object* obj) { return dynamic_cast(obj)!=NULL; } + virtual bool isSameKindAs(const Object* obj) const { return dynamic_cast(obj)!=NULL; } virtual const char* className() const { return "LOD"; } virtual void accept(NodeVisitor& nv) { nv.apply(*this); } virtual void traverse(NodeVisitor& nv); @@ -29,31 +27,31 @@ class SG_EXPORT LOD : public Group is a floating point distance specified in world coordinates. Range list automatically expands to accomodate values beyond the current getNumRanges().*/ - void setRange(unsigned int index, float range); - /** pfLOD::getRange returns the range element index.*/ - float getRange(unsigned int index) { return _rangeList[index]; } + void setRange(const unsigned int index, const float range); + + /** returns the range for specified index.*/ + inline const float getRange(const unsigned int index) const { return _rangeList[index]; } + /** returns the number of ranges currently set.*/ - int getNumRanges() { return _rangeList.size(); } + inline const int getNumRanges() const { return _rangeList.size(); } /** Sets the object-space point which defines the center of the osg::LOD. center is affected by any transforms in the hierarchy above the osg::LOD.*/ - void setCenter(const Vec3 ¢er) { _center = center; } + inline void setCenter(const Vec3 ¢er) { _center = center; } + /** return the LOD center point. */ - const Vec3& getCenter() { return _center; } + inline const Vec3& getCenter() const { return _center; } /** return the child to traverse. Selected by the distance between the eye point in local coordinates and the LOD center, mutliplied by the bias.*/ - int evaluate(const Vec3& eye_local,float bias=1.0f); + const int evaluate(const Vec3& eye_local,const float bias=1.0f) const; protected : virtual ~LOD() {} - virtual bool readLocalData(Input& fr); - virtual bool writeLocalData(Output& fw); - typedef std::vector RangeList; RangeList _rangeList; RangeList _rangeList2; diff --git a/include/osg/Light b/include/osg/Light index f8d4c0243..663e2f695 100644 --- a/include/osg/Light +++ b/include/osg/Light @@ -1,113 +1,111 @@ #ifndef OSG_LIGHT #define OSG_LIGHT 1 -#include -#include +#include #include +#include +#include namespace osg { /** Light state class which encapsulates OpenGL glLight() functionality.*/ -class SG_EXPORT Light : public Object +class SG_EXPORT Light : public StateAttribute { public : Light(); - /** return a static instance of an osg::Light, to be used as prototype - for loading lights.*/ - static Light* instance(); - /** return a shallow copy of a node, with Object* return type.*/ virtual Object* clone() const { return new Light(); } - virtual bool isSameKindAs(Object* obj) { return dynamic_cast(obj)!=NULL; } + /** return true if this and obj are of the same kind of object.*/ + virtual bool isSameKindAs(const Object* obj) const { return dynamic_cast(obj)!=NULL; } /** return the name of the node's class type.*/ virtual const char* className() const { return "Light"; } + virtual const Type getType() const { return LIGHTING; } + + virtual void setStateSetModes(StateSet& ds,const GLModeValue value) const + { + ds.setMode((GLMode)(GL_LIGHT0+_lightnum),value); + } /** * Turn the light on. * Calling this method doesn't directly affect OpenGL's lighting mode. */ - void on( void ) { _on = true; } + inline void on() { _on = true; } /** * Turn the light off. * Calling this method doesn't directly affect OpenGL's lighting mode. */ - void off( void ) { _on = false; } - - /** Enable OpenGL's Lighting mode. */ - static void enable( void ); - - /** Disable OpenGL's Lighting mode. */ - static void disable( void ); + inline void off() { _on = false; } /** Apply the light's state to the OpenGL state machine. */ - void apply( void ); + virtual void apply(State& state) const; /** Set the ambient component of the light. */ - void setAmbient( const Vec4& ambient ) { _ambient = ambient; } + inline void setAmbient( const Vec4& ambient ) { _ambient = ambient; } /** Get the ambient component of the light. */ - const Vec4& getAmbient() const { return _ambient; } + inline const Vec4& getAmbient() const { return _ambient; } /** Set the diffuse component of the light. */ - void setDiffuse( const Vec4& diffuse ) { _diffuse = diffuse; } + inline void setDiffuse( const Vec4& diffuse ) { _diffuse = diffuse; } /** Get the diffuse component of the light. */ - const Vec4& getDiffuse() const { return _diffuse; } + inline const Vec4& getDiffuse() const { return _diffuse; } /** Set the specular component of the light. */ - void setSpecular( const Vec4& specular ) { _specular = specular; } + inline void setSpecular( const Vec4& specular ) { _specular = specular; } /** Get the specular component of the light. */ - const Vec4& getSpecular() const { return _specular; } + inline const Vec4& getSpecular() const { return _specular; } /** Set the position of the light. */ - void setPosition( const Vec4& position ) { _position = position; } + inline void setPosition( const Vec4& position ) { _position = position; } /** Get the position of the light. */ - const Vec4& getPosition() const { return _position; } + inline const Vec4& getPosition() const { return _position; } /** Set the direction of the light. */ - void setDirection( const Vec3& direction ) { _direction = direction; } + inline void setDirection( const Vec3& direction ) { _direction = direction; } /** Get the direction of the light. */ - const Vec3& getDirection() const { return _direction; } + inline const Vec3& getDirection() const { return _direction; } /** Set the constant attenuation of the light. */ - void setConstantAttenuation( float constant_attenuation ) { _constant_attenuation = constant_attenuation; } + inline void setConstantAttenuation( const float constant_attenuation ) { _constant_attenuation = constant_attenuation; } /** Get the constant attenuation of the light. */ - float setConstantAttenuation() const { return _constant_attenuation; } + inline const float getConstantAttenuation() const { return _constant_attenuation; } /** Set the linear attenuation of the light. */ - void setLinearAttenuation ( float linear_attenuation ) { _linear_attenuation = linear_attenuation; } + inline void setLinearAttenuation ( const float linear_attenuation ) { _linear_attenuation = linear_attenuation; } /** Get the linear attenuation of the light. */ - float getLinearAttenuation () const { return _linear_attenuation; } + inline const float getLinearAttenuation () const { return _linear_attenuation; } /** Set the quadratic attenuation of the light. */ - void setQuadraticAttenuation ( float quadratic_attenuation ) { _quadratic_attenuation = quadratic_attenuation; } + inline void setQuadraticAttenuation ( const float quadratic_attenuation ) { _quadratic_attenuation = quadratic_attenuation; } /** Get the quadratic attenuation of the light. */ - float getQuadraticAttenuation() const { return _quadratic_attenuation; } + inline const float getQuadraticAttenuation() const { return _quadratic_attenuation; } /** Set the spot exponent of the light. */ - void setSpotExponent( float spot_exponent ) { _spot_exponent = spot_exponent; } + inline void setSpotExponent( const float spot_exponent ) { _spot_exponent = spot_exponent; } /** Get the spot exponent of the light. */ - float getSpotExponent() const { return _spot_exponent; } + inline const float getSpotExponent() const { return _spot_exponent; } /** Set the spot cutoff of the light. */ - void setSpotCutoff( float spot_cutoff ) { _spot_cutoff = spot_cutoff; } + inline void setSpotCutoff( const float spot_cutoff ) { _spot_cutoff = spot_cutoff; } /** Get the spot cutoff of the light. */ - float getSpotCutoff() { return _spot_cutoff; } + inline const float getSpotCutoff() const { return _spot_cutoff; } /** * Capture the lighting settings of the current OpenGL state @@ -117,10 +115,10 @@ class SG_EXPORT Light : public Object protected : - virtual ~Light( void ); + virtual ~Light(); /** Initialize the light's settings with some decent defaults. */ - void init( void ); + void init(); int _lightnum; // OpenGL light number bool _on; // on/off state diff --git a/include/osg/LightSource b/include/osg/LightSource index fa41cd358..da4019e60 100644 --- a/include/osg/LightSource +++ b/include/osg/LightSource @@ -1,7 +1,7 @@ #ifndef OSG_LIGHTSOURCE #define OSG_LIGHTSOURCE 1 -#include +#include #include #include @@ -15,24 +15,24 @@ class SG_EXPORT LightSource : public Node LightSource(); virtual Object* clone() const { return new LightSource(); } - virtual bool isSameKindAs(Object* obj) { return dynamic_cast(obj)!=NULL; } + virtual bool isSameKindAs(const Object* obj) const { return dynamic_cast(obj)!=NULL; } virtual const char* className() const { return "LightSource"; } virtual void accept(NodeVisitor& nv) { nv.apply(*this); } /** Set the attached light.*/ - void setLight(Light* light) { _light = light; } + inline void setLight(Light* light) { _light = light; } /** Get the attached light.*/ - Light* getLight() { return _light.get(); } + inline Light* getLight() { return _light.get(); } + + /** Get the const attached light.*/ + inline const Light* getLight() const { return _light.get(); } protected: virtual ~LightSource(); - virtual bool readLocalData(Input& fr); - virtual bool writeLocalData(Output& fw); - - virtual bool computeBound( void ); + virtual const bool computeBound() const; ref_ptr _light; }; diff --git a/include/osg/Material b/include/osg/Material index a0aec7488..422d5b3f0 100644 --- a/include/osg/Material +++ b/include/osg/Material @@ -1,26 +1,39 @@ #ifndef OSG_MATERIAL #define OSG_MATERIAL 1 -#include -#include #include -#include +#include +#include namespace osg { - - -class Input; -class Output; - -class SG_EXPORT Material : public Object +/** Material - encapsulates OpenGL glMaterial state.*/ +class SG_EXPORT Material : public StateAttribute { public : - enum MaterialFace { - FACE_FRONT = GL_FRONT, - FACE_BACK = GL_BACK, - FACE_FRONT_AND_BACK = GL_FRONT_AND_BACK + + Material(); + virtual Object* clone() const { return new Material(); } + virtual bool isSameKindAs(const Object* obj) const { return dynamic_cast(obj)!=NULL; } + const char* className() const { return "Material"; } + + virtual const Type getType() const { return MATERIAL; } + + virtual void setStateSetModes(StateSet& ds,const GLModeValue value) const + { + // Have to think about the role of _colorMode + // in setting the colormaterial... also need to take the + // color material enable/disable out of the the apply()... + ds.setMode(GL_COLOR_MATERIAL,value); + } + + virtual void apply(State& state) const; + + enum Face { + FRONT = GL_FRONT, + BACK = GL_BACK, + FRONT_AND_BACK = GL_FRONT_AND_BACK }; enum ColorMode { @@ -32,44 +45,51 @@ class SG_EXPORT Material : public Object OFF }; - Material( void ); - static Material* instance(); - virtual Object* clone() const { return new Material(); } - virtual bool isSameKindAs(Object* obj) { return dynamic_cast(obj)!=NULL; } - const char* className() const { return "Material"; } + inline void setColorMode(const ColorMode mode) { _colorMode = mode; } + inline const ColorMode getColorMode() const { return _colorMode; } - void apply( void ); + void setAmbient( const Face face, const Vec4& ambient ); + const Vec4& getAmbient(const Face face) const; + inline const bool getAmbientFrontAndBack() const { return _ambientFrontAndBack; } - void setColorMode(ColorMode mode) { _colorMode = mode; } + void setDiffuse( const Face face, const Vec4& diffuse ); + const Vec4& getDiffuse(const Face face) const; + inline const bool getDiffuseFrontAndBack() const { return _diffuseFrontAndBack; } - void setAmbient( MaterialFace face, const Vec4& ambient ); - const Vec4& getAmbient(MaterialFace face) const; - bool getAmbientFrontAndBack() { return _ambientFrontAndBack; } + /** Set specular value of specified face(s) of the material, + * valid specular[0..3] range is 0.0 to 1.0.*/ + void setSpecular( const Face face, const Vec4& specular ); + /** Get the specular value for specified face.*/ + const Vec4& getSpecular(const Face face) const; + /** Get the whether specular values are equal for front and back faces.*/ + inline const bool getSpecularFrontAndBack() const { return _specularFrontAndBack; } - void setDiffuse( MaterialFace face, const Vec4& diffuse ); - const Vec4& getDiffuse(MaterialFace face) const; - bool getDiffuseFrontAndBack() { return _diffuseFrontAndBack; } + /** Set emmision value of specified face(s) of the material, + * valid emmison[0..3] range is 0.0 to 1.0.*/ + void setEmission( const Face face, const Vec4& emission ); + /** Get the emmsion value for specified face.*/ + const Vec4& getEmission(const Face face) const; + /** Get the whether emmision values are equal for front and back faces.*/ + inline const bool getEmissionFrontAndBack() const { return _emissionFrontAndBack; } - void setSpecular( MaterialFace face, const Vec4& specular ); - const Vec4& getSpecular(MaterialFace face) const; - bool getSpecularFrontAndBack() { return _specularFrontAndBack; } + /** Set shininess of specified face(s) of the material, valid shininess range is 0.0 to 1.0.*/ + void setShininess( const Face face, float shininess ); + /** Get the shininess value for specified face.*/ + const float getShininess(const Face face) const; + /** Get the whether shininess values are equal for front and back faces.*/ + inline const bool getShininessFrontAndBack() const { return _shininessFrontAndBack; } + + /** Set the alpha value of ambient,diffuse,specular and emmission colors, + * of specified face, to 1-transparancy. Valid transparancy range is 0.0 to 1.0.*/ + void setTransparency(const Face face,float trans); - void setEmission( MaterialFace face, const Vec4& emission ); - const Vec4& getEmission(MaterialFace face) const; - bool getEmissionFrontAndBack() { return _emissionFrontAndBack; } - - void setShininess( MaterialFace face, float shininess ); - float getShininess(MaterialFace face) const; - bool getShininessFrontAndBack() { return _shininessFrontAndBack; } + /** Set the alpha value of ambient,diffuse,specular and emmission colors. + * Valid transparancy range is 0.0 to 1.0.*/ + void setAlpha(const Face face,float alpha); protected : - virtual ~Material( void ); - - virtual bool readLocalData(Input& fr); - virtual bool writeLocalData(Output& fw); - - bool matchFaceAndColor(Input& fr,const char* name,MaterialFace& mf,Vec4& color); + virtual ~Material(); ColorMode _colorMode; diff --git a/include/osg/Matrix b/include/osg/Matrix index 5fe633c0d..0455d431d 100644 --- a/include/osg/Matrix +++ b/include/osg/Matrix @@ -2,16 +2,28 @@ #define OSG_MATRIX 1 #include -#include +#include +#include + +#ifdef OSG_USE_IO_DOT_H +#include +#else +#include +using namespace std; +#endif namespace osg { -class Input; -class Output; - /** 4x4 Matrix for storage & manipulation of transformations in scene graph. Provides basic maths operations, IO and via osg::Object reference counting. + You can directly load the matrix with OpenGL's LoadMatrixf() function via + the public member _mat as the matrix is stored in the OpenGL format. + Caution: The disadvantage of this feature is, that the matrix access is + 'transposed' if you compare it with the standard C/C++ 2d-array-access + convention . I.e. _mat[i][j] accesses the ith column of the jth row in the + 4x4 matrix. */ + class SG_EXPORT Matrix : public Object { public: @@ -26,14 +38,19 @@ class SG_EXPORT Matrix : public Object virtual ~Matrix(); - static Matrix* instance(); virtual Object* clone() const { return new Matrix(); } - virtual bool isSameKindAs(Object* obj) { return dynamic_cast(obj)!=NULL; } + virtual bool isSameKindAs(const Object* obj) const { return dynamic_cast(obj)!=NULL; } virtual const char* className() const { return "Matrix"; } void makeIdent(); void set(const float* m); + + void set( float a00, float a01, float a02, float a03, + float a10, float a11, float a12, float a13, + float a20, float a21, float a22, float a23, + float a30, float a31, float a32, float a33); + void copy(const Matrix& matrix); void makeScale(float sx, float sy, float sz); @@ -52,6 +69,13 @@ class SG_EXPORT Matrix : public Object void postTrans( float tx, float ty, float tz ); + /** + * Calc the rotation matrix which aligns vector \a old_vec with + * vector \a new_vec. Both \a old_vec and \a new_vec must have + * length 1.0. + */ + void makeRot( const Vec3& old_vec, const Vec3& new_vec ); + void makeRot( float deg, float x, float y, float z ); void preRot( float deg, float x, float y, float z, const Matrix& m ); void postRot( const Matrix& m, float deg, float x, float y, float z ); @@ -69,8 +93,24 @@ class SG_EXPORT Matrix : public Object Matrix operator * (const Matrix& m) const; + /** apply apply an 3x3 transform of v*M[0..2,0..2] */ + inline static Vec3 transform3x3(const Vec3& v,const Matrix& m); + /** apply apply an 3x3 transform of M[0..2,0..2]*v */ + inline static Vec3 transform3x3(const Matrix& m,const Vec3& v); + + /** post multipy v. ie. (m*v) */ inline Vec3 operator * (const Vec3& v) const; - inline friend Vec3 operator * (const Vec3& v,const Matrix& m); + + /** pre multipy v. ie. (v*m) */ + friend inline Vec3 operator * (const Vec3& v,const Matrix& m); + + /** post multipy v. ie. (m*v) */ + inline Vec4 operator * (const Vec4& v) const; + + /** pre multipy v. ie. (v*m) */ + friend inline Vec4 operator * (const Vec4& v,const Matrix& m); + + friend inline ostream& operator << (ostream& output, const Matrix& matrix); bool invert(const Matrix& m); @@ -78,12 +118,8 @@ class SG_EXPORT Matrix : public Object float _mat[4][4]; protected: - - virtual bool readLocalData(Input& fr); - virtual bool writeLocalData(Output& fw); }; -// post multiple v. ie. (m*v) inline Vec3 Matrix::operator * (const Vec3& v) const { float d = 1.0f/(_mat[3][0]*v.x()+_mat[3][1]*v.y()+_mat[3][2]*v.z()+_mat[3][3]) ; @@ -93,7 +129,6 @@ inline Vec3 Matrix::operator * (const Vec3& v) const } -// pre multiple v. ie. (v*m) inline Vec3 operator * (const Vec3& v,const Matrix& m) { float d = 1.0f/(m._mat[0][3]*v.x()+m._mat[1][3]*v.y()+m._mat[2][3]*v.z()+m._mat[3][3]) ; @@ -102,6 +137,48 @@ inline Vec3 operator * (const Vec3& v,const Matrix& m) (m._mat[0][2]*v.x() + m._mat[1][2]*v.y() + m._mat[2][2]*v.z() + m._mat[3][2])*d); } +inline Vec4 Matrix::operator * (const Vec4& v) const +{ + return Vec4( (_mat[0][0]*v.x() + _mat[0][1]*v.y() + _mat[0][2]*v.z() + _mat[0][3]*v.w()), + (_mat[1][0]*v.x() + _mat[1][1]*v.y() + _mat[1][2]*v.z() + _mat[1][3]*v.w()), + (_mat[2][0]*v.x() + _mat[2][1]*v.y() + _mat[2][2]*v.z() + _mat[2][3]*v.w()), + (_mat[3][0]*v.x() + _mat[3][1]*v.y() + _mat[3][2]*v.z() + _mat[3][3]*v.w())) ; +} + + +inline Vec4 operator * (const Vec4& v,const Matrix& m) +{ + return Vec4( (m._mat[0][0]*v.x() + m._mat[1][0]*v.y() + m._mat[2][0]*v.z() + m._mat[3][0]*v.w()), + (m._mat[0][1]*v.x() + m._mat[1][1]*v.y() + m._mat[2][1]*v.z() + m._mat[3][1]*v.w()), + (m._mat[0][2]*v.x() + m._mat[1][2]*v.y() + m._mat[2][2]*v.z() + m._mat[3][2]*v.w()), + (m._mat[0][3]*v.x() + m._mat[1][3]*v.y() + m._mat[2][3]*v.z() + m._mat[3][3]*v.w())); +} + +inline Vec3 Matrix::transform3x3(const Vec3& v,const Matrix& m) +{ + return Vec3( (m._mat[0][0]*v.x() + m._mat[1][0]*v.y() + m._mat[2][0]*v.z()), + (m._mat[0][1]*v.x() + m._mat[1][1]*v.y() + m._mat[2][1]*v.z()), + (m._mat[0][2]*v.x() + m._mat[1][2]*v.y() + m._mat[2][2]*v.z())); +} + +inline Vec3 Matrix::transform3x3(const Matrix& m,const Vec3& v) +{ + return Vec3( (m._mat[0][0]*v.x() + m._mat[0][1]*v.y() + m._mat[0][2]*v.z()), + (m._mat[1][0]*v.x() + m._mat[1][1]*v.y() + m._mat[1][2]*v.z()), + (m._mat[2][0]*v.x() + m._mat[2][1]*v.y() + m._mat[2][2]*v.z()) ) ; +} + +inline ostream& operator << (ostream& output, const Matrix& matrix) +{ + output << "{"< #include +#include #include +#include +#include #include #include @@ -13,39 +15,6 @@ namespace osg { class NodeVisitor; class Group; -/** Class for adapting the memory management of external data. - * Typically used to specify the memory management of user data - * which can be attached to osg::Node. - */ -class SG_EXPORT MemoryAdapter : public Referenced -{ - public: - MemoryAdapter() {} - - /** Increment the reference count of the userData.*/ - virtual void incrementReference(void* /*userData*/) = 0; - - /** Decrement the reference count of the userData. - Is usually implemented such that if reference count - is decremented to zero the userData should be - deleted. However, this is entirely up to the - discression of the user who is extending this base class.*/ - virtual void decrementReference(void* /*userData*/) = 0; - - /** not current used, but will be used in future.*/ - virtual void* clone(void* /*userData*/) { return 0L; } - - /** not current used, but will be used in future.*/ - virtual bool write(Output& /*fw*/,void* /*userData*/) { return false; } - - /** not current used, but will be used in future.*/ - virtual bool read(Input& /*fr*/,void* /*userData*/) { return false; } - - protected: - - virtual ~MemoryAdapter() {} -}; - /** Base class for all internal nodes in the scene graph. Provides interface for most common node operations (Composite Pattern). */ @@ -60,11 +29,9 @@ class SG_EXPORT Node : public Object /** return a shallow copy of a node, with Object* return type.*/ virtual Object* clone() const { return new Node(); } - /** return a shallow copy of a node, with Node* return type.*/ - Node* cloneNode() const { return (Node*)clone(); } /** return true if this and obj are of the same kind of object.*/ - virtual bool isSameKindAs(Object* obj) { return dynamic_cast(obj)!=NULL; } + virtual bool isSameKindAs(const Object* obj) const { return dynamic_cast(obj)!=NULL; } /** return the name of the node's class type.*/ virtual const char* className() const { return "Node"; } @@ -78,54 +45,66 @@ class SG_EXPORT Node : public Object /** Set the name of node using C++ style string.*/ - void setName( const std::string& name ) { _name = name; } + inline void setName( const std::string& name ) { _name = name; } /** Set the name of node using a C style string.*/ - void setName( const char* name ) { _name = name; } + inline void setName( const char* name ) { _name = name; } /** Get the name of node.*/ - const std::string& getName( void ) { return _name; } + inline const std::string& getName() const { return _name; } /** A vector of osg::Group pointers which is used to store the parent(s) of node.*/ typedef std::vector ParentList; /** Get the parent list of node. */ - const ParentList& getParents() const { return _parents; } + inline const ParentList& getParents() const { return _parents; } + + /** Get the a copy of parent list of node. A copy is returned to + * prevent modifiaction of the parent list.*/ +// inline ParentList getParents() { return _parents; } + + inline Group* getParent(const int i) { return _parents[i]; } /** - * Get a single parent of node. + * Get a single const parent of node. * @param i index of the parent to get. * @return the parent i. */ - Group* getParent(int i) const { return _parents[i]; } + inline const Group* getParent(const int i) const { return _parents[i]; } + /** * Get the number of parents of node. * @return the number of parents of this node. */ - int getNumParents() const { return _parents.size(); } + inline const int getNumParents() const { return _parents.size(); } /** * Set user data. See MemoryAdapter documention for details * of how to specify memory managament of _userData. */ - void setUserData(void* data,MemoryAdapter* ma=0L) + inline void setUserData(void* data,MemoryAdapter* ma=0L) { - if (_userData && _memoryAdapter.valid()) _memoryAdapter->decrementReference(_userData); + if (_userData && _memoryAdapter.valid()) _memoryAdapter->unref_data(_userData); _userData = data; _memoryAdapter = ma; - if (_userData && _memoryAdapter.valid()) _memoryAdapter->incrementReference(_userData); + if (_userData && _memoryAdapter.valid()) _memoryAdapter->ref_data(_userData); } /** Get user data.*/ - void* getUserData() const { return _userData; } + inline void* getUserData() { return _userData; } + /** Get const user data.*/ + inline const void* getUserData() const { return _userData; } + /** Get the memory adapter associated with _userData.*/ - MemoryAdapter* getMemoryAdapter() const { return _memoryAdapter.get(); } + inline MemoryAdapter* getMemoryAdapter() { return _memoryAdapter.get(); } + /** Get the const memory adapter associated with _userData.*/ + inline const MemoryAdapter* getMemoryAdapter() const { return _memoryAdapter.get(); } typedef unsigned int NodeMask; /** Set the node mask. Note, node mask is will be replaced by TraversalMask.*/ - void setNodeMask(NodeMask nm) { _nodeMask = nm; } + inline void setNodeMask(const NodeMask nm) { _nodeMask = nm; } /** Get the node Mask. Note, node mask is will be replaced by TraversalMask.*/ - NodeMask getNodeMask() { return _nodeMask; } + inline const NodeMask getNodeMask() const { return _nodeMask; } @@ -133,21 +112,36 @@ class SG_EXPORT Node : public Object typedef std::vector DescriptionList; /** Get the description list of the const node.*/ - const DescriptionList& getDescriptions() const { return _descriptions; } + inline const DescriptionList& getDescriptions() const { return _descriptions; } /** Get the description list of the const node.*/ - DescriptionList& getDescriptions() { return _descriptions; } + inline DescriptionList& getDescriptions() { return _descriptions; } /** Get a single const description of the const node.*/ - const std::string& getDescription(int i) const { return _descriptions[i]; } + inline const std::string& getDescription(const int i) const { return _descriptions[i]; } /** Get a single description of the node.*/ - std::string& getDescription(int i) { return _descriptions[i]; } + inline std::string& getDescription(const int i) { return _descriptions[i]; } /** Get the number of descriptions of the node.*/ - int getNumDescriptions() const { return _descriptions.size(); } + inline const int getNumDescriptions() const { return _descriptions.size(); } /** Add a description string to the node.*/ void addDescription(const std::string& desc) { _descriptions.push_back(desc); } + + /** set the node's StateSet.*/ + inline void setStateSet(osg::StateSet* dstate) { _dstate = dstate; } + + /** return the node's StateSet.*/ + inline osg::StateSet* getStateSet() { return _dstate.get(); } + + /** return the node's const StateSet.*/ + inline const osg::StateSet* getStateSet() const { return _dstate.get(); } + /** get the bounding sphere of node. Using lazy evaluation computes the bounding sphere if it is 'dirty'.*/ - const BoundingSphere& getBound(); + inline const BoundingSphere& getBound() const + { + if(!_bsphere_computed) computeBound(); + return _bsphere; + } + /** Mark this node's bounding sphere dirty. Forcing it to be computed on the next call to getBound().*/ @@ -165,29 +159,14 @@ class SG_EXPORT Node : public Object = new Node().*/ virtual ~Node(); - /** - * Template Method Pattern : read local data from .osg file. - * Note should be implemented in derived classes, which - * call their parent class's readLocalData. - * @return true if the input iterator has been advanced, otherwise false. - */ - virtual bool readLocalData(Input& fr); - - /** - * Template Method Pattern : read local data from .osg file. - * Note should be implemented in derivied classes, which - * call their parent class's writeLocalData. - * @return true if data has been written out, otherwise false. - */ - virtual bool writeLocalData(Output& fw); /** Compute the bounding sphere around Node's geometry or children. This method is automatically called by getBound() when the bounding sphere has been marked dirty via dirtyBound().*/ - virtual bool computeBound( void ) ; + virtual const bool computeBound() const; - BoundingSphere _bsphere; - bool _bsphere_computed; + mutable BoundingSphere _bsphere; + mutable bool _bsphere_computed; std::string _name; @@ -201,6 +180,8 @@ class SG_EXPORT Node : public Object DescriptionList _descriptions; + ref_ptr _dstate; + }; /** A vector of Nodes pointers which is used to describe the path from a root node to a descendant.*/ diff --git a/include/osg/NodeVisitor b/include/osg/NodeVisitor index 86011f43a..e18261b01 100644 --- a/include/osg/NodeVisitor +++ b/include/osg/NodeVisitor @@ -9,11 +9,11 @@ class Geode; class Billboard; class LightSource; class Group; -class DCS; +class Transform; class LOD; class Sequence; -class Scene; class Switch; +class Impostor; /** Visitor for type safe operations on osg::Node's. Based on GOF's Visitor pattern.*/ @@ -32,21 +32,27 @@ class SG_EXPORT NodeVisitor : public Referenced NodeVisitor(TraversalMode tm=TRAVERSE_NONE); virtual ~NodeVisitor(); + /** Method to call to reset visitor. Useful for your visitor accumulates + state during a traversal, and you plan to resuse the visitor. + To flush that state for the next traversal than call reset() prior + to each traversal.*/ + virtual void reset() {} /** Set the traversal mode for Node::traverse() to use when deciding which children of a node to traverse. If a NodeVisitor has been attached via setTraverseVisitor() and the new mode is not TRAVERSE_VISITOR then the attached visitor is detached. Default mode is TRAVERSE_NONE.*/ - void setTraverseMode(TraversalMode mode); + void setTraversalMode(const TraversalMode mode); /** Get the traversal mode.*/ - TraversalMode getTraverseMode() { return _traverseMode; } - /** Set a visitor to handle traversal. - Overides the traverse mode setting it to TRAVERSE_VISITOR.*/ + inline const TraversalMode getTraversalMode() const { return _traversalMode; } - void setTraverseVisitor(NodeVisitor* nv); - /** Get the traverse visitor, returns NULL if none is attached.*/ - NodeVisitor* getTraverseVisitor() { return _traverseVisitor; } + /** Set a visitor to handle traversal. + Overides the traverse mode setting it to TRAVERSAL_VISITOR.*/ + void setTraversalVisitor(NodeVisitor* nv); + + /** Get the traversal visitor, returns NULL if none is attached.*/ + NodeVisitor* getTraversalVisitor() { return _traversalVisitor.get(); } /** Inline method for passing handling traversal of a nodes. If you intend to use the visitor for actively traversing @@ -54,28 +60,28 @@ class SG_EXPORT NodeVisitor : public Referenced this method unless they handle traversal directly.*/ void traverse(Node& node) { - if (_traverseVisitor) node.accept(*_traverseVisitor); - else if (_traverseMode==TRAVERSE_PARENTS) node.ascend(*this); - else if (_traverseMode!=TRAVERSE_NONE) node.traverse(*this); + if (_traversalVisitor.valid()) node.accept(*_traversalVisitor); + else if (_traversalMode==TRAVERSE_PARENTS) node.ascend(*this); + else if (_traversalMode!=TRAVERSE_NONE) node.traverse(*this); } - virtual void apply(Node& node) { traverse(node);} + virtual void apply(Node& node) { traverse(node);} - virtual void apply(Geode& node) { apply((Node&)node); } - virtual void apply(Billboard& node){ apply((Geode&)node); } + virtual void apply(Geode& node) { apply((Node&)node); } + virtual void apply(Billboard& node) { apply((Geode&)node); } virtual void apply(LightSource& node){ apply((Node&)node); } - virtual void apply(Group& node) { apply((Node&)node); } - virtual void apply(DCS& node) { apply((Group&)node); } - virtual void apply(Switch& node) { apply((Group&)node); } - virtual void apply(Sequence& node) { apply((Group&)node); } - virtual void apply(LOD& node) { apply((Group&)node); } - virtual void apply(Scene& node) { apply((Group&)node); } + virtual void apply(Group& node) { apply((Node&)node); } + virtual void apply(Transform& node) { apply((Group&)node); } + virtual void apply(Switch& node) { apply((Group&)node); } + virtual void apply(Sequence& node) { apply((Group&)node); } + virtual void apply(LOD& node) { apply((Group&)node); } + virtual void apply(Impostor& node) { apply((LOD&)node); } protected: - NodeVisitor* _traverseVisitor; - TraversalMode _traverseMode; + ref_ptr _traversalVisitor; + TraversalMode _traversalMode; }; diff --git a/include/osg/Notify b/include/osg/Notify index 23fbd9b5a..3f8dd142c 100644 --- a/include/osg/Notify +++ b/include/osg/Notify @@ -6,59 +6,84 @@ #ifdef OSG_USE_IO_DOT_H #include #include -//#include #else #include #include -//#include using namespace std; #endif namespace osg { +/** Range of notify levels from DEBUG_FP through to FATAL, ALWAYS + * is reserved for forcing the absorption of all messages. The + * keywords are also used verbatim when specified by the environmental + * variable OSGNOTIFYLEVEL. See documentation on osg::notify() for + * further details. + */ enum NotifySeverity { ALWAYS=0, FATAL=1, WARN=2, NOTICE=3, INFO=4, - DEBUG=5, - FP_DEBUG=6 + DEBUG_INFO=5, + DEBUG_FP=6 }; -extern NotifySeverity g_NotifyLevel; -extern ofstream *g_absorbStreamPtr; +/** global notify level. */ +SG_EXPORT extern NotifySeverity g_NotifyLevel; +/** set the notify level, overriding the default or value set by + * the environmental variable OSGNOTIFYLEVEL. + */ SG_EXPORT extern void setNotifyLevel(NotifySeverity severity); -SG_EXPORT extern int getNotifyLevel(); + +/** get the notify level. */ +SG_EXPORT extern NotifySeverity getNotifyLevel(); + +/** initialize notify level. */ +SG_EXPORT extern bool initNotifyLevel(); + +/** notify messaging function for providing fatal through to verbose + * debugging messages. Level of messages sent to the console can + * be controlled by setting the NotifyLevel either within your + * application or via the an environmental variable. For instance + * setenv OSGNOTIFYLEVEL DEBUG (for tsh), export OSGNOTIFYLEVEL=DEBUG + * (for bourne shell) or set OSGNOTIFYLEVEL=DEBUG (for Windows) all + * set tell the osg to redirect all debugging and more important messages + * to the console (useful for debugging :-) setting ALWAYS will force + * all messages to be absorbed, which might be appropriate for final + * applications. Default NotifyLevel is NOTICE. Check the enum + * NotifySeverity for full range of possibilities. To use the notify + * with your code simply use the notify function as a normal file + * stream (like cout) i.e osg::notify(osg::DEBUG) << "Hello Bugs!"< -#include #include +#include +#include namespace osg { -class Input; -class Output; - -class SG_EXPORT Point : public Object +/** Point - encapsulates the OpenGL point smmothing and size state.*/ +class SG_EXPORT Point : public StateAttribute { public : Point(); - static Point* instance(); virtual Object* clone() const { return new Point(); } - virtual bool isSameKindAs(Object* obj) { return dynamic_cast(obj)!=NULL; } + virtual bool isSameKindAs(const Object* obj) const { return dynamic_cast(obj)!=NULL; } virtual const char* className() const { return "Point"; } - void setSize(float size); - void setFadeThresholdSize(float fadeThresholdSize); + virtual const Type getType() const { return POINT; } + + virtual void setStateSetModes(StateSet& ds,const GLModeValue value) const + { + ds.setMode(GL_POINT_SMOOTH,value); + } + + void setSize(const float size); + inline const float getSize() const { return _size; } + + void setFadeThresholdSize(const float fadeThresholdSize); + inline const float getFadeThresholdSize() const { return _fadeThresholdSize; } + void setDistanceAttenuation(const Vec3& distanceAttenuation); + inline const Vec3& getDistanceAttenuation() const { return _distanceAttenuation; } - static void enableSmooth( void ); - static void disableSmooth( void ); - - void apply( void ); + virtual void apply(State& state) const; static void init_GL_EXT(); @@ -35,9 +41,6 @@ class SG_EXPORT Point : public Object virtual ~Point(); - virtual bool readLocalData(Input& fr); - virtual bool writeLocalData(Output& fw); - float _size; float _fadeThresholdSize; Vec3 _distanceAttenuation; diff --git a/include/osg/PolygonOffset b/include/osg/PolygonOffset index f156fffd5..f77f633cd 100644 --- a/include/osg/PolygonOffset +++ b/include/osg/PolygonOffset @@ -1,39 +1,42 @@ #ifndef OSG_POLYGONOFFSET #define OSG_POLYGONOFFSET 1 -#include -#include -#include +#include +#include namespace osg { -class Input; -class Output; - -class SG_EXPORT PolygonOffset : public Object +/** PolygonOffset - encapsulates the OpenGL glPolygonOffset state.*/ +class SG_EXPORT PolygonOffset : public StateAttribute { public : PolygonOffset(); - static PolygonOffset* instance(); virtual Object* clone() const { return new PolygonOffset(); } - virtual bool isSameKindAs(Object* obj) { return dynamic_cast(obj)!=NULL; } + virtual bool isSameKindAs(const Object* obj) const { return dynamic_cast(obj)!=NULL; } virtual const char* className() const { return "PolygonOffset"; } - void setOffset(float factor,float units); + virtual const Type getType() const { return POLYGONOFFSET; } - static void enable( void ); - static void disable( void ); + virtual void setStateSetModes(StateSet& ds,const GLModeValue value) const + { + ds.setMode(GL_POLYGON_OFFSET_FILL,value); + ds.setMode(GL_POLYGON_OFFSET_LINE,value); + ds.setMode(GL_POLYGON_OFFSET_POINT,value); + } - void apply( void ); + inline void setFactor(const float factor) { _factor = factor; } + inline const float getFactor() const { return _factor; } + + inline void setUnits(const float units) { _units = units; } + inline const float getUnits() const { return _units; } + + virtual void apply(State& state) const; protected : virtual ~PolygonOffset(); - virtual bool readLocalData(Input& fr); - virtual bool writeLocalData(Output& fw); - float _factor; float _units; diff --git a/include/osg/Quat b/include/osg/Quat index aa3190cd9..5ad9f5a15 100644 --- a/include/osg/Quat +++ b/include/osg/Quat @@ -1,11 +1,8 @@ #ifndef OSG_QUAT #define OSG_QUAT 1 -#include -#include - -#include #include +#include #include namespace osg { @@ -28,30 +25,39 @@ class SG_EXPORT Quat ---------------------------------------------------------- */ Vec4 _fv; // a four-vector - /* ---------------------------------- - CONSTRUCTORS - Default constructor - One to accept four floats - One to accept a Vec4 - These are implemented in Quat.cpp - ---------------------------------- */ - Quat( void ); - Quat( float x, float y, float z, float w ); - Quat( const Vec4& vec ); + Quat() {} + Quat( float x, float y, float z, float w ): _fv(x,y,z,w) {} + Quat( const Vec4& v ): _fv(v) {} /* ---------------------------------- Methods to access data members ---------------------------------- */ - inline Vec4 asVec4( void ) const + inline Vec4& asVec4() { return _fv; } - inline Vec3 asVec3( void ) const + inline const Vec4& asVec4() const + { + return _fv; + } + + inline const Vec3 asVec3() const { return Vec3(_fv[0], _fv[1], _fv[2]); } + inline void set(const float x, const float y, const float z, const float w) + { + _fv.set(x,y,z,w); + } + + inline void set(const osg::Vec4& v) + { + _fv = v; + } + + /* ------------------------------------------------------------- BASIC ARITHMETIC METHODS Implemented in terms of Vec4s. Some Vec4 operators, e.g. @@ -60,7 +66,7 @@ class SG_EXPORT Quat Also define methods for conjugate and the multiplicative inverse. ------------------------------------------------------------- */ /// Multiply by scalar - inline Quat operator * (const float& rhs) const + inline const Quat operator * (const float& rhs) const { return Quat(_fv*rhs); } @@ -73,7 +79,7 @@ class SG_EXPORT Quat } /// Binary multiply - inline Quat operator*(const Quat& rhs) const + inline const Quat operator*(const Quat& rhs) const { return Quat( _fv[3]*rhs._fv[0] + _fv[0]*rhs._fv[3] + _fv[1]*rhs._fv[2] - _fv[2]*rhs._fv[1], _fv[3]*rhs._fv[1] - _fv[0]*rhs._fv[2] + _fv[1]*rhs._fv[3] + _fv[2]*rhs._fv[0], @@ -97,7 +103,7 @@ class SG_EXPORT Quat } /// Divide by scalar - inline Quat operator / (const float& rhs) const + inline const Quat operator / (const float& rhs) const { return Quat(_fv/rhs); } @@ -110,7 +116,7 @@ class SG_EXPORT Quat } /// Binary divide - inline Quat operator/(const Quat& denom) const + inline const Quat operator/(const Quat& denom) const { return ( (*this) * denom.inverse() ); } @@ -123,7 +129,7 @@ class SG_EXPORT Quat } /// Binary addition - inline Quat operator + (const Quat& rhs) const + inline const Quat operator + (const Quat& rhs) const { return Quat( _fv + rhs._fv ); } @@ -136,7 +142,7 @@ class SG_EXPORT Quat } /// Binary subtraction - inline Quat operator - (const Quat& rhs) const + inline const Quat operator - (const Quat& rhs) const { return Quat( _fv - rhs._fv ); } @@ -150,31 +156,31 @@ class SG_EXPORT Quat /** Negation operator - returns the negative of the quaternion. Basically just calls operator - () on the Vec4 */ - inline Quat operator - () const + inline const Quat operator - () const { return Quat ( -_fv ); } /// Length of the quaternion = sqrt( vec . vec ) - float length( void ) const + const float length() const { return _fv.length(); } /// Length of the quaternion = vec . vec - float length2( void ) const + const float length2() const { return _fv.length2(); } /// Conjugate - inline Quat conj ( void ) const + inline const Quat conj () const { return Quat( -_fv[0], -_fv[1], -_fv[2], _fv[3] ); } /// Multiplicative inverse method: q^(-1) = q^*/(q.q^*) - inline Quat inverse ( void ) const + inline const Quat inverse () const { return conj() / length2(); } @@ -215,17 +221,18 @@ class SG_EXPORT Quat /** Get the equivalent matrix for this quaternion.*/ void get( osg::Matrix& m ) const; - friend inline ostream& operator << (ostream& output, const Quat& vec) - { - output << vec._fv[0] << " " - << vec._fv[1] << " " - << vec._fv[2] << " " - << vec._fv[3]; - return output; // to enable cascading - } - + friend inline ostream& operator << (ostream& output, const Quat& vec); }; // end of class prototype +inline ostream& operator << (ostream& output, const Quat& vec) +{ + output << vec._fv[0] << " " + << vec._fv[1] << " " + << vec._fv[2] << " " + << vec._fv[3]; + return output; // to enable cascading +} + }; // end of namespace #endif diff --git a/include/osg/Referenced b/include/osg/Referenced index bbd4b3a4e..267affc11 100644 --- a/include/osg/Referenced +++ b/include/osg/Referenced @@ -2,100 +2,35 @@ #define OSG_REFERENCED 1 #include +#include namespace osg { -/** Convience functor for unreferencing objects.*/ -template -struct UnrefOp -{ - void operator () (T* node) { node->unref(); } -}; - -/** Smart pointer for handling referenced counted objects.*/ -template -class ref_ptr -{ - - public: - ref_ptr() :_ptr(0L) {} - ref_ptr(T* t):_ptr(t) { if (_ptr) _ptr->ref(); } - ref_ptr(const ref_ptr& rp):_ptr(rp._ptr) { if (_ptr) _ptr->ref(); } - ~ref_ptr() { if (_ptr) _ptr->unref(); } - - ref_ptr& operator = (const ref_ptr& rp) - { - if (_ptr==rp._ptr) return *this; - if (_ptr) _ptr->unref(); - _ptr = rp._ptr; - if (_ptr) _ptr->ref(); - return *this; - } - - ref_ptr& operator = (T* ptr) - { - if (_ptr==ptr) return *this; - if (_ptr) _ptr->unref(); - _ptr = ptr; - if (_ptr) _ptr->ref(); - return *this; - } - - bool operator == (const ref_ptr& rp) const - { - return (_ptr==rp._ptr); - } - - bool operator == (const T* ptr) const - { - return (_ptr==ptr); - } - - bool operator != (const ref_ptr& rp) const - { - return (_ptr!=rp._ptr); - } - - bool operator != (const T* ptr) const - { - return (_ptr!=ptr); - } - - T& operator*() const { return *_ptr; } - T* operator->() const { return _ptr; } - bool operator!() const { return _ptr==0L; } - bool valid() const { return _ptr!=0L; } - - T* get() const { return _ptr; } - - private: - T* _ptr; -}; - /** Base class from providing referencing counted objects.*/ -class Referenced +class SG_EXPORT Referenced { public: Referenced() { _refCount=0; } - Referenced(Referenced&) { _refCount=0; } + Referenced(const Referenced&) { _refCount=0; } - Referenced& operator = (Referenced&) { return *this; } + inline Referenced& operator = (Referenced&) { return *this; } /** increment the reference count by one, indicating that this object has another pointer which is referencing it.*/ - void ref() { ++_refCount; } + inline void ref() const { ++_refCount; } /** decrement the reference count by one, indicating that a pointer to this object is referencing it. If the refence count goes to zero, it is assumed that this object is nolonger referenced and is automatically deleted.*/ - void unref() { --_refCount; if (_refCount<=0) delete this; } + inline void unref() const { --_refCount; if (_refCount<=0) delete this; } /** return the number pointers currently referencing this object. */ - int referenceCount() { return _refCount; } + inline const int referenceCount() const { return _refCount; } protected: - virtual ~Referenced() {}; - int _refCount; + virtual ~Referenced() {} + mutable int _refCount; + }; }; diff --git a/include/osg/State b/include/osg/State index 55d58b38f..b3b135cb6 100644 --- a/include/osg/State +++ b/include/osg/State @@ -2,19 +2,181 @@ #define OSG_STATE 1 #include +#include +#include + +#include +#include namespace osg { -class SG_EXPORT State +/** macro for use with osg::StateAttrbiute::apply methods for detected and + * reporting OpenGL error messages.*/ +#define OSG_GL_DEBUG(message) \ + if (state.getFineGrainedErrorDetection()) \ + { \ + GLenum errorNo = glGetError(); \ + if (errorNo!=GL_NO_ERROR) \ + { \ + osg::notify(WARN)<<"Warning: detected OpenGL error '"<getType()]); + } + + + /** apply stateset.*/ + void apply(const StateSet* dstate); + + /** apply the state.*/ + void apply(); + + /** mode has been set externally, update state to reflect this setting.*/ + void have_applied(const StateAttribute::GLMode mode,const StateAttribute::GLModeValue value); + + /** attribute has been applied externally, update state to reflect this setting.*/ + void have_applied(const StateAttribute* attribute); + + + /** Set the current OpenGL context uniqueID. + Note, it is the application developers responsiblity to + set up unique ID for each OpenGL context. This value is + then used by osg::StateAttribure's and osg::Drawable's to + help manage OpenGL display list and texture binds appropriate + for each context.*/ + inline void setContextID(unsigned int contextID) { _contextID=contextID; } + + /** Get the current OpenGL context unique ID.*/ + inline const unsigned int getContextID() const { return _contextID; } + + + + /** Set the frame number.*/ + inline void setFrameNumber(unsigned int fn) { _frameNumber = fn; } + + /** Get the frame number.*/ + inline unsigned int getFrameNumber() const { return _frameNumber; } + + /** Increment the frame number. Done once per frame.*/ + inline void incrementFrameNumber() { ++_frameNumber; } + + + /** Set the hint to OpenGL routines to do fine grained OpenGL error checking.*/ + void setFineGrainedErrorDetection(const bool flag) { _fineGrainedErrorDetection = flag; } + + /** Get the hint to OpenGL routines to do fine grained OpenGL error checking.*/ + const bool getFineGrainedErrorDetection() const { return _fineGrainedErrorDetection; } + + private: + + unsigned int _contextID; + unsigned int _frameNumber; + + typedef std::vector ValueVec; + + struct ModeStack + { + ModeStack() + { + changed = false; + last_applied_value = false; + } + + bool changed; + bool last_applied_value; + ValueVec valueVec; + }; + + + typedef std::pair AttributePair; + typedef std::vector AttributeVec; + + struct AttributeStack + { + AttributeStack() + { + changed = false; + last_applied_attribute = 0L; + } + + + bool changed; + const StateAttribute* last_applied_attribute; + AttributeVec attributeVec; + }; + + /** apply an OpenGL mode if required, passing in mode, enable flag and appropriate mode stack */ + inline const bool apply_mode(const StateAttribute::GLMode mode,const bool enabled,ModeStack& ms) + { + if (ms.last_applied_value != enabled) + { + ms.last_applied_value = enabled; + + if (enabled) glEnable(mode); + else glDisable(mode); + + return true; + } + else + return false; + } + + /** apply an attribute if required, passing in attribute and appropriate attribute stack */ + inline const bool apply_attribute(const StateAttribute* attribute,AttributeStack& as) + { + if (as.last_applied_attribute != attribute) + { + as.last_applied_attribute = attribute; + attribute->apply(*this); + return true; + } + else + return false; + } + + typedef std::map ModeMap; + typedef std::map AttributeMap; + typedef std::vector > StateSetStack; + typedef std::vector > MatrixStack; + + ModeMap _modeMap; + AttributeMap _attributeMap; + StateSetStack _drawStateStack; + + bool _fineGrainedErrorDetection; - private : - GeoState *initial; - GeoState *req; - GeoState *current; }; }; diff --git a/include/osg/Switch b/include/osg/Switch index f2a1d2ae0..6ff0efa06 100644 --- a/include/osg/Switch +++ b/include/osg/Switch @@ -5,7 +5,7 @@ namespace osg { -/** Switch - Group node which allows switching between children. +/** Switch is a Group node which allows switching between children. Typical uses would be for objects which might need to be rendered differently at different times, for instance a switch could be used to represent the different states of a traffic light. @@ -14,30 +14,44 @@ class SG_EXPORT Switch : public Group { public : + /** + * Special mode values for the Switch. Use these if you want to + * turn on/off all child nodes. + */ enum SwitchType { - ALL_CHILDREN_ON=-1, - ALL_CHILDREN_OFF=-2 + /** Turn on all children. */ + ALL_CHILDREN_ON=-1, + /** Turn off all children. */ + ALL_CHILDREN_OFF=-2 }; Switch(); virtual Object* clone() const { return new Switch(); } - virtual bool isSameKindAs(Object* obj) { return dynamic_cast(obj)!=NULL; } + virtual bool isSameKindAs(const Object* obj) const { return dynamic_cast(obj)!=NULL; } virtual const char* className() const { return "Switch"; } virtual void accept(NodeVisitor& nv) { nv.apply(*this); } virtual void traverse(NodeVisitor& nv); - void setVal(int val) { _value = val; } - int getVal() const { return _value; } + /** + * Selects the active child Node or enables a special + * SwitchType mode. + * @param value the number of the active child + * (first child == number 0) or SwitchType. Invalid values + * will be ignored. + */ + inline void setValue(const int value) { _value = value; } + /** + * Returns the number of the active child Node or the SwitchType. + */ + inline const int getValue() const { return _value; } protected : virtual ~Switch() {} - virtual bool readLocalData(Input& fr); - virtual bool writeLocalData(Output& fw); - - int _value; + /** The current Switch value. */ + int _value; }; }; diff --git a/include/osg/TexEnv b/include/osg/TexEnv index 5bd4c64cf..3bd33c890 100644 --- a/include/osg/TexEnv +++ b/include/osg/TexEnv @@ -1,43 +1,41 @@ #ifndef OSG_TEXENV #define OSG_TEXENV 1 -#include #include -#include +#include namespace osg { - -class SG_EXPORT TexEnv : public Object +/** TexEnv - encapsulates the OpenGL glTexEnv (texture environment) state.*/ +class SG_EXPORT TexEnv : public StateAttribute { public : - enum TexEnvMode { - DECAL = GL_DECAL, - MODULATE = GL_MODULATE, - BLEND = GL_BLEND - }; - TexEnv( void ); - static TexEnv* instance(); virtual Object* clone() const { return new TexEnv(); } - virtual bool isSameKindAs(Object* obj) { return dynamic_cast(obj)!=NULL; } + virtual bool isSameKindAs(const Object* obj) const { return dynamic_cast(obj)!=0L; } virtual const char* className() const { return "TexEnv"; } + virtual const Type getType() const { return TEXENV; } - void setMode( TexEnvMode mode ); - void apply( void ); + enum Mode { + DECAL = GL_DECAL, + MODULATE = GL_MODULATE, + BLEND = GL_BLEND, + REPLACE = GL_REPLACE + }; + + void setMode( const Mode mode ); + + const Mode getMode() const { return _mode; } + + virtual void apply(State& state) const; protected : virtual ~TexEnv( void ); - virtual bool readLocalData(Input& fr); - virtual bool writeLocalData(Output& fw); - bool matchModeStr(const char* str,TexEnvMode& mode); - const char* getModeStr(TexEnvMode mode); - - TexEnvMode _mode; + Mode _mode; }; }; diff --git a/include/osg/TexGen b/include/osg/TexGen index e85f55884..3ec018d18 100644 --- a/include/osg/TexGen +++ b/include/osg/TexGen @@ -1,51 +1,72 @@ #ifndef OSG_TEXGEN #define OSG_TEXGEN 1 -#include -#include -#include -#include +#include +#include +#include namespace osg { - -class Input; -class Output; - -class SG_EXPORT TexGen : public Object +/** TexGen - encapsulates the OpenGL glTexGen (texture coordinate generation) state.*/ +class SG_EXPORT TexGen : public StateAttribute { public : - enum TexGenMode { + TexGen( void ); + virtual Object* clone() const { return new TexGen(); } + virtual bool isSameKindAs(const Object* obj) const { return dynamic_cast(obj)!=NULL; } + virtual const char* className() const { return "TexGen"; } + + virtual const Type getType() const { return TEXGEN; } + + virtual void setStateSetModes(StateSet& ds,const GLModeValue value) const + { + ds.setMode(GL_TEXTURE_GEN_S,value); + ds.setMode(GL_TEXTURE_GEN_T,value); + + // Not happy with turning all tex gen paramters on + // as the OSG currently only supports 2D textures and therefore + // only S and T will only be required, R&Q would be redundent... + // So commenting out the following until OSG supports 3D texures. + // I plan to revamp the OpenGL state management later so will + // tidy up then. Robert Osfield. Jan 2001. + + // The tidy up is now happening, but wiil have a think before + // resolving the below parameters. + + // ds.setMode(GL_TEXTURE_GEN_R,value); + // ds.setMode(GL_TEXTURE_GEN_Q,value); + + } + + virtual void apply(State& state) const; + + enum Mode { OBJECT_LINEAR = GL_OBJECT_LINEAR, EYE_LINEAR = GL_EYE_LINEAR, SPHERE_MAP = GL_SPHERE_MAP }; - TexGen( void ); - static TexGen* instance(); - virtual Object* clone() const { return new TexGen(); } - virtual bool isSameKindAs(Object* obj) { return dynamic_cast(obj)!=NULL; } - virtual const char* className() const { return "TexGen"; } + inline void setMode( const Mode mode ) { _mode = mode; } - static void enable( void ); - static void disable( void ); - - void apply( void ); + const Mode getMode() const { return _mode; } - void setMode( TexGenMode mode ) { _mode = mode; } + enum Coord { + S, T, R, Q + }; + + void setPlane(const Coord which, const Vec4& plane); + + const Vec4& getPlane(const Coord which) const; protected : virtual ~TexGen( void ); - virtual bool readLocalData(Input& fr); - virtual bool writeLocalData(Output& fw); + Mode _mode; - bool matchModeStr(const char* str,TexGenMode& mode); - const char* getModeStr(TexGenMode mode); - - TexGenMode _mode; + /// additional texgen coefficents for GL_OBJECT_PLANE or GL_EYE_PLANE, + Vec4 _plane_s, _plane_t, _plane_r, _plane_q; }; diff --git a/include/osg/TexMat b/include/osg/TexMat index fce835d9d..acd65c61b 100644 --- a/include/osg/TexMat +++ b/include/osg/TexMat @@ -1,26 +1,40 @@ #ifndef OSG_TEXMAT #define OSG_TEXMAT 1 -#include +#include #include namespace osg { -class SG_EXPORT TexMat : public Matrix +/** Texture Matrix state class for encapsulating OpenGL texture matrix functionality.*/ +class SG_EXPORT TexMat : public StateAttribute { public : TexMat( void ); - static TexMat* instance(); virtual Object* clone() const { return new TexMat(); } - virtual bool isSameKindAs(Object* obj) { return dynamic_cast(obj)!=NULL; } + virtual bool isSameKindAs(const Object* obj) const { return dynamic_cast(obj)!=NULL; } virtual const char* className() const { return "TexMat"; } - void apply( void ); + virtual const Type getType() const { return TEXMAT; } + + /** Set the texture matrix */ + inline void setMatrix(const Matrix& matrix) { _matrix = matrix; } + + /** Get the texture matrix */ + inline Matrix& getMatrix() { return _matrix; } + + /** Get the const texture matrix */ + inline const Matrix& getMatrix() const { return _matrix; } + + /** apply as OpenGL texture matrix.*/ + virtual void apply(State& state) const; protected: virtual ~TexMat( void ); + Matrix _matrix; + }; }; diff --git a/include/osg/Texture b/include/osg/Texture index da48e659d..62a9cfdca 100644 --- a/include/osg/Texture +++ b/include/osg/Texture @@ -1,33 +1,110 @@ +// -*-c++-*- + #ifndef OSG_TEXTURE #define OSG_TEXTURE 1 -#include #include -#include +#include #include +#include +#include +#include + +#include +#include +#include + +// if not defined by gl.h use the definition found in: +// http://oss.sgi.com/projects/ogl-sample/registry/EXT/texture_filter_anisotropic.txt +#ifndef GL_TEXTURE_MAX_ANISOTROPY_EXT +#define GL_TEXTURE_MAX_ANISOTROPY_EXT (GLenum)0x84fe +#endif + +#ifndef GL_ARB_texture_compression +#define GL_COMPRESSED_ALPHA_ARB 0x84E9 +#define GL_COMPRESSED_LUMINANCE_ARB 0x84EA +#define GL_COMPRESSED_LUMINANCE_ALPHA_ARB 0x84EB +#define GL_COMPRESSED_INTENSITY_ARB 0x84EC +#define GL_COMPRESSED_RGB_ARB 0x84ED +#define GL_COMPRESSED_RGBA_ARB 0x84EE +#define GL_TEXTURE_COMPRESSION_HINT_ARB 0x84EF +#define GL_TEXTURE_IMAGE_SIZE_ARB 0x86A0 +#define GL_TEXTURE_COMPRESSED_ARB 0x86A1 +#define GL_NUM_COMPRESSED_TEXTURE_FORMATS_ARB 0x86A2 +#define GL_COMPRESSED_TEXTURE_FORMATS_ARB 0x86A3 +#endif + +#ifndef GL_EXT_texture_compression_s3tc +#define GL_COMPRESSED_RGB_S3TC_DXT1_EXT 0x83F0 +#define GL_COMPRESSED_RGBA_S3TC_DXT1_EXT 0x83F1 +#define GL_COMPRESSED_RGBA_S3TC_DXT3_EXT 0x83F2 +#define GL_COMPRESSED_RGBA_S3TC_DXT5_EXT 0x83F3 +#endif + +#ifndef GL_MIRRORED_REPEAT_IBM +#define GL_MIRRORED_REPEAT_IBM 0x8370 +#endif + +#ifndef GL_GENERATE_MIPMAP_SGIS +#define GL_GENERATE_MIPMAP_SGIS (GLenum)0x8191 +#define GL_GENERATE_MIPMAP_HINT_SGIS 0x8192 +#endif + namespace osg { - -class Input; -class Output; - /** Texture state class which encapsulates OpenGl texture functionality.*/ -class SG_EXPORT Texture : public Object +class SG_EXPORT Texture : public StateAttribute { public : Texture(); - static Texture* instance(); virtual Object* clone() const { return new Texture(); } - virtual bool isSameKindAs(Object* obj) { return dynamic_cast(obj)!=NULL; } + virtual bool isSameKindAs(const Object* obj) const { return dynamic_cast(obj)!=0L; } virtual const char* className() const { return "Texture"; } + virtual const Type getType() const { return (Type)(TEXTURE_0+_textureUnit); } + + virtual void setStateSetModes(StateSet& ds,const GLModeValue value) const + { + ds.setMode(GL_TEXTURE_2D,value); + } + /** Set the texture image. */ void setImage(Image* image); + /** Get the texture image. */ - Image* getImage() const { return _image.get(); } + Image* getImage() { return _image.get(); } + + /** Get the const texture image. */ + inline const Image* getImage() const { return _image.get(); } + + /** Copy pixels into a 2D texture image.As per glCopyTexImage2D. + * Creates an OpenGL texture object from the current OpenGL background + * framebuffer contents at pos \a x, \a y with width \a width and + * height \a height. \a width and \a height must be a power of two. + */ + void copyTexImage2D(State& state, int x, int y, int width, int height ); + + /** Copy a two-dimensional texture subimage. As per glCopyTexSubImage2D. + * Updates portion of an exisiting OpenGL texture object from the current OpenGL background + * framebuffer contents at pos \a x, \a y with width \a width and + * height \a height. \a width and \a height must be a power of two, + * and writing into the texture with offset \a xoffset and \a yoffset. + */ + void copyTexSubImage2D(State& state, int xoffset, int yoffset, int x, int y, int width, int height ); + + /** Set the texture unit. + * Valid values are 0,1,2,3. + * Default value of texture unit is 0. + * note, multi-texturing not fully implemented yet... April 2001. + */ + inline void setTextureUnit(const unsigned int textureUnit) { _textureUnit = textureUnit; } + + /** get the texture unit.*/ + inline const unsigned int getTextureUnit() const { return _textureUnit; } + enum WrapParameter { WRAP_S, @@ -36,14 +113,15 @@ class SG_EXPORT Texture : public Object }; enum WrapMode { - CLAMP = GL_CLAMP, - REPEAT = GL_REPEAT + CLAMP = GL_CLAMP, + REPEAT = GL_REPEAT, + MIRROR = GL_MIRRORED_REPEAT_IBM }; /** Set the texture wrap mode.*/ - void setWrap(WrapParameter which, WrapMode wrap); + void setWrap(const WrapParameter which, const WrapMode wrap); /** Get the texture wrap mode.*/ - WrapMode getWrap(WrapParameter which) const; + const WrapMode getWrap(const WrapParameter which) const; enum FilterParameter { @@ -57,46 +135,161 @@ class SG_EXPORT Texture : public Object LINEAR_MIPMAP_NEAREST = GL_LINEAR_MIPMAP_NEAREST, NEAREST = GL_NEAREST, NEAREST_MIPMAP_LINEAR = GL_NEAREST_MIPMAP_LINEAR, - NEAREST_MIPMAP_NEAREST = GL_NEAREST_MIPMAP_NEAREST + NEAREST_MIPMAP_NEAREST = GL_NEAREST_MIPMAP_NEAREST, + ANISOTROPIC = GL_TEXTURE_MAX_ANISOTROPY_EXT }; /** Set the texture filter mode.*/ - void setFilter(FilterParameter which, FilterMode filter); + void setFilter(const FilterParameter which, const FilterMode filter); /** Get the texture filter mode.*/ - FilterMode getFilter(FilterParameter which) const; + const FilterMode getFilter(const FilterParameter which) const; - /** Enable OpenGL texturing.*/ - static void enable( void ); - /** Disable OpenGL texturing.*/ - static void disable( void ); + enum InternalFormatMode { + USE_IMAGE_DATA_FORMAT, + USE_USER_DEFINED_FORMAT, + USE_ARB_COMPRESSION, + USE_S3TC_DXT1_COMPRESSION, + USE_S3TC_DXT3_COMPRESSION, + USE_S3TC_DXT5_COMPRESSION + }; - /** On first apply, create the minmapped texture and bind it, - subsequent apply will simple bind to texture.*/ - void apply( void ); + /** Set the internal format mode. + * Note, If the mode is set USE_IMAGE_DATA_FORMAT, USE_ARB_COMPRESSION, + * USE_S3TC_COMPRESSION the internalFormat is automatically selected, + * and will overwrite the previous _internalFormatValue. + */ + inline void setInternalFormatMode(const InternalFormatMode mode) { _internalFormatMode = mode; } + + /** Get the internal format mode.*/ + inline const InternalFormatMode getInternalFormatMode() const { return _internalFormatMode; } + + /** Set the internal format to use when creating OpenGL textures. + * Also sets the internalFormatMode to USE_USER_DEFINED_FORMAT. + */ + inline void setInternalFormatValue(const int internalFormat) + { + _internalFormatMode = USE_USER_DEFINED_FORMAT; + _internalFormatValue = internalFormat; + } + + /** Get the internal format to use when creating OpenGL textures.*/ + inline const int getInternalFormatValue() const { return _internalFormatValue; } + + /** return the OpenGL texture object for specified context.*/ + inline const uint getTextureObject(const uint contextID) const { if (contextID<_handleList.size()) return _handleList[contextID]; else return 0;} + + /** return the memory size of texture object. + * Texture object size can be used for estimating the cost of + * uploading the texture to graphics hardware, which inturn can + * be used for setting texture residence priorities. */ + inline const uint getTextureObjectSize() const { return _textureObjectSize; } + + enum SubloadMode { + OFF, + AUTO, + IF_DIRTY + }; + + /** Set the texture subload mode. */ + inline void setSubloadMode(const SubloadMode mode) { _subloadMode = mode; } + + /** Get the texture subload mode. */ + inline const SubloadMode getSubloadMode() const { return _subloadMode; } + + /** Set the texture subload offsets. */ + inline void setSubloadOffset(const int x, const int y) { + _subloadOffsX = x; + _subloadOffsY = y; + } + + /** Get the texture subload offsets. */ + inline void getSubloadOffset(int& x, int& y) const { + x = _subloadOffsX; + y = _subloadOffsY; + } + + /** Get the handle to the texture object for the current context.*/ + inline uint& getHandle(const uint contextID) const + { + // pad out handle list if required. + while (_handleList.size()<=contextID) + _handleList.push_back(0); + + // get the globj for the current contextID. + return _handleList[contextID]; + } + + /** Force a recompile on next apply() of associated OpenGL texture objects.*/ + void dirtyTextureObject(); + + /** On first apply (unless already compiled), create the minmapped + * texture and bind it, subsequent apply will simple bind to texture.*/ + virtual void apply(State& state) const; + + /** Compile the texture mip maps. Implemented by simply calling apply().*/ + virtual void compile(State& state) const; + + + /** Method which does the creation of the texture itself, and + * does not set or use texture binding. */ + virtual void applyImmediateMode(State& state) const; + + + /** use deleteTextureObject instead of glDeleteTextures to allow + * OpenGL texture objects to cached until they can be deleted + * by the OpenGL context in which they were created, specified + * by contextID.*/ + static void deleteTextureObject(uint contextID,uint handle); + + /** flush all the cached display list which need to be deleted + * in the OpenGL context related to contextID.*/ + static void flushDeletedTextureObjects(uint contextID); + protected : virtual ~Texture(); - virtual bool readLocalData(Input& fr); - virtual bool writeLocalData(Output& fw); + typedef std::vector TextureNameList; + mutable TextureNameList _handleList; - uint _handle; + typedef std::vector ImageModifiedTag; + mutable ImageModifiedTag _modifiedTag; - ref_ptr _image; + // size of the created OpenGL texture object, may be estimated. + mutable uint _textureObjectSize; - bool matchWrapStr(const char* str,WrapMode& wrap); - const char* getWrapStr(WrapMode wrap); + // not ideal that _image is mutable, but its required since + // Image::ensureDimensionsArePowerOfTwo() can only be called + // in a valid OpenGL context, a therefore within an Texture::apply + // which is const... + mutable ref_ptr _image; - bool matchFilterStr(const char* str,FilterMode& filter); - const char* getFilterStr(FilterMode filter); + unsigned int _textureUnit; WrapMode _wrap_s; WrapMode _wrap_t; WrapMode _wrap_r; + FilterMode _min_filter; FilterMode _mag_filter; + + InternalFormatMode _internalFormatMode; + int _internalFormatValue; + + // subloaded images can have different texture and image sizes. + mutable unsigned int _textureWidth, _textureHeight; + + SubloadMode _subloadMode; + unsigned int _subloadOffsX, _subloadOffsY; + + // static cache of deleted display lists which can only + // by completely deleted once the appropriate OpenGL context + // is set. + typedef std::map > DeletedTextureObjectCache; + static DeletedTextureObjectCache s_deletedTextureObjectCache; + }; }; diff --git a/include/osg/Timer b/include/osg/Timer index f5f385ff5..d88cc8c4c 100644 --- a/include/osg/Timer +++ b/include/osg/Timer @@ -3,14 +3,22 @@ #include +#ifdef macintosh +//#define __TIMESIZE_DOUBLE__ +#include +#endif + namespace osg { #ifdef WIN32 typedef __int64 Timer_t; +#elif defined macintosh + typedef double Timer_t; #else typedef unsigned long long Timer_t; #endif +/** A high resolution, low latency time stamper.*/ class SG_EXPORT Timer { public: @@ -23,8 +31,8 @@ class SG_EXPORT Timer { #pragma optimize("",off) inline Timer_t tick( void ) { - volatile Timer_t ts; - volatile unsigned int HighPart; + volatile Timer_t ts; + volatile unsigned int HighPart; volatile unsigned int LowPart; _asm { @@ -32,23 +40,29 @@ class SG_EXPORT Timer { xor edx, edx // not supported or minimal overhead _emit 0x0f // desired _emit 0x31 // - mov HighPart,edx - mov LowPart,eax + mov HighPart,edx + mov LowPart,eax } - //ts = LowPart | HighPart >> 32; - *((unsigned int*)&ts) = LowPart; + //ts = LowPart | HighPart >> 32; + *((unsigned int*)&ts) = LowPart; *((unsigned int*)&ts+1) = HighPart; return ts; } #pragma optimize("",on) #endif -#ifdef __linux +#if defined(__linux) || defined(__FreeBSD__) #define CLK(x) __asm__ volatile (".byte 0x0f, 0x31" : "=A" (x)) inline Timer_t tick( void ) {Timer_t x;CLK(x);return x;} #endif #ifdef __sgi inline Timer_t tick( void ) { return *clk; } #endif + +#ifdef macintosh + // because __TIMESIZE_DOUBLE__ is defined + // clock resolution is now: 100000 CLOCKS_PER_SEC instead of 60 + inline Timer_t tick( void ) { return std::clock(); } +#endif double delta_s( Timer_t t1, Timer_t t2 ); double delta_m( Timer_t t1, Timer_t t2 ); diff --git a/include/osg/Transparency b/include/osg/Transparency index e06d5f6ba..25ad381be 100644 --- a/include/osg/Transparency +++ b/include/osg/Transparency @@ -1,17 +1,28 @@ #ifndef OSG_TRANSPARENCY #define OSG_TRANSPARENCY 1 -#include -#include -#include +#include +#include namespace osg { - -class SG_EXPORT Transparency : public Object +/** Transparancy - encapsulates the OpenGL transparancy state.*/ +class SG_EXPORT Transparency : public StateAttribute { public : + Transparency(); + virtual Object* clone() const { return new Transparency(); } + virtual bool isSameKindAs(const Object* obj) const { return dynamic_cast(obj)!=0L; } + virtual const char* className() const { return "Transparency"; } + + virtual const Type getType() const { return TRANSPARENCY; } + + virtual void setStateSetModes(StateSet& ds,const GLModeValue value) const + { + ds.setMode(GL_BLEND,value); + } + enum TransparencyMode { DST_ALPHA = GL_DST_ALPHA, DST_COLOR = GL_DST_COLOR, @@ -26,16 +37,19 @@ class SG_EXPORT Transparency : public Object ZERO = GL_ZERO }; - Transparency(); - static Transparency * instance(); - virtual Object* clone() const { return new Transparency(); } - virtual bool isSameKindAs(Object* obj) { return dynamic_cast(obj)!=NULL; } - virtual const char* className() const { return "Transparency"; } + inline void setFunction( const int source, const int destination ) + { + _source_factor = source; + _destination_factor = destination; + } - void setFunction( int source, int destination ); - static void enable( void ); - static void disable( void ); - void apply( void ); + void setSource(const int source) { _source_factor = source; } + inline const int getSource() const { return _source_factor; } + + void setDestination(const int destination) { _destination_factor = destination; } + inline const int getDestination() const { return _destination_factor; } + + virtual void apply(State& state) const; protected : diff --git a/include/osg/Types b/include/osg/Types index dbfff7976..da034b012 100644 --- a/include/osg/Types +++ b/include/osg/Types @@ -1,9 +1,6 @@ #ifndef OSG_TYPES #define OSG_TYPES 1 -#include -#include - namespace osg { typedef unsigned int uint; @@ -11,7 +8,7 @@ typedef unsigned short ushort; typedef unsigned char uchar; typedef uchar ubyte; -#ifdef WIN32 +#if defined(WIN32) || defined (macintosh) #define M_E 2.7182818284590452354 #define M_LOG2E 1.4426950408889634074 #define M_LOG10E 0.43429448190325182765 diff --git a/include/osg/Vec2 b/include/osg/Vec2 index 80112a60f..877839a35 100644 --- a/include/osg/Vec2 +++ b/include/osg/Vec2 @@ -1,7 +1,6 @@ #ifndef OSG_VEC2 #define OSG_VEC2 1 -#include #include #ifdef OSG_USE_IO_DOT_H @@ -29,7 +28,14 @@ class Vec2 float _v[2]; - bool operator == (const Vec2& v) const { return _v[0]==v._v[0] && _v[1]==v._v[1]; } + const bool operator == (const Vec2& v) const { return _v[0]==v._v[0] && _v[1]==v._v[1]; } + + const bool operator < (const Vec2& v) const + { + if (_v[0]v._v[0]) return false; + else return (_v[1] #include #ifdef OSG_USE_IO_DOT_H @@ -28,7 +27,16 @@ class Vec3 float _v[3]; - bool operator == (const Vec3& v) const { return _v[0]==v._v[0] && _v[1]==v._v[1] && _v[2]==v._v[2]; } + inline const bool operator == (const Vec3& v) const { return _v[0]==v._v[0] && _v[1]==v._v[1] && _v[2]==v._v[2]; } + + inline const bool operator < (const Vec3& v) const + { + if (_v[0]v._v[0]) return false; + else if (_v[1]v._v[1]) return false; + else return (_v[2] #include #ifdef OSG_USE_IO_DOT_H @@ -33,7 +32,18 @@ class Vec4 float _v[4]; - bool operator == (const Vec4& v) const { return _v[0]==v._v[0] && _v[1]==v._v[1] && _v[2]==v._v[2] && _v[3]==v._v[3]; } + inline const bool operator == (const Vec4& v) const { return _v[0]==v._v[0] && _v[1]==v._v[1] && _v[2]==v._v[2] && _v[3]==v._v[3]; } + + inline const bool operator < (const Vec4& v) const + { + if (_v[0]v._v[0]) return false; + else if (_v[1]v._v[1]) return false; + else if (_v[2]v._v[2]) return false; + else return (_v[3] +#include + +#include +#include + +#include +#include +//#include + +namespace osgDB { + + +/** Wrapper class for specifing read and write functions for extending + * the .osg file format. */ +class OSGDB_EXPORT DotOsgWrapper : public osg::Referenced +{ + public: + + typedef std::vector Associates; + typedef bool (*ReadFunc)(osg::Object&,osgDB::Input&); + typedef bool (*WriteFunc)(const osg::Object&,osgDB::Output&); + + enum ReadWriteMode + { + READ_AND_WRITE, + READ_ONLY + }; + + DotOsgWrapper(osg::Object* proto, + const std::string& name, + const std::string& associates, + ReadFunc readFunc, + WriteFunc writeFunc, + ReadWriteMode readWriteMode=READ_AND_WRITE); + + + inline const osg::Object* getPrototype() const { return _prototype.get(); } + inline const std::string& getName() const { return _name; } + inline const Associates& getAssociates() const { return _associates; } + inline ReadFunc getReadFunc() const { return _readFunc; } + inline WriteFunc getWriteFunc() const { return _writeFunc; } + inline ReadWriteMode getReadWriteMode() const { return _readWriteMode; } + + protected: + + /// protected to prevent inappropriate creation of wrappers. + DotOsgWrapper() {} + + /// protected to prevent inappropriate creation of wrappers. + DotOsgWrapper(DotOsgWrapper&):osg::Referenced() {} + + /// protected to prevent wrapper being created on stack. + virtual ~DotOsgWrapper() {} + + osg::ref_ptr _prototype; + + std::string _name; + Associates _associates; + + ReadFunc _readFunc; + WriteFunc _writeFunc; + + ReadWriteMode _readWriteMode; +}; + +}; + +#endif diff --git a/include/osgDB/DynamicLibrary b/include/osgDB/DynamicLibrary new file mode 100644 index 000000000..03f9ca7e1 --- /dev/null +++ b/include/osgDB/DynamicLibrary @@ -0,0 +1,63 @@ +#ifndef OSG_DYNAMICLIBRARY +#define OSG_DYNAMICLIBRARY 1 + +#include +#include + +#include + + +namespace osgDB { + +/** DynamicLibrary - encapsulates the loading and unloading of dynamic libraries, + typically used for loading ReaderWriter plug-ins. +*/ +class OSGDB_EXPORT DynamicLibrary : public osg::Referenced +{ + public: + + typedef void* HANDLE; + typedef void* PROC_ADDRESS; + + /** returns a pointer to a DynamicLibrary object on successfully + * opening of library returns NULL on failure. + */ + static DynamicLibrary* loadLibrary(const std::string& libraryName); + + /** return name of library stripped of path.*/ + const std::string& getName() const { return _name; } + + /** return name of library including full path to it.*/ + const std::string& getFullName() const { return _fullName; } + + /** return handle to .dso/.dll dynamic library itself.*/ + HANDLE getHandle() const { return _handle; } + + /** return address of function located in library.*/ + PROC_ADDRESS getProcAddress(const std::string& procName); + + protected: + + /** disallow default constructor.*/ + DynamicLibrary():osg::Referenced() {} + /** disallow copy constructor.*/ + DynamicLibrary(const DynamicLibrary&):osg::Referenced() {} + /** disallow copy operator.*/ + DynamicLibrary& operator == (const DynamicLibrary&) { return *this; } + + /** Disallow public construction so that users have to go + * through loadLibrary() above which returns NULL on + * failure, a valid DynamicLibrary object on success. + */ + DynamicLibrary(const std::string& name,HANDLE handle); + ~DynamicLibrary(); + + HANDLE _handle; + std::string _name; + std::string _fullName; + +}; + +}; + +#endif // __DYNAMIC_LIBRARY_H diff --git a/include/osgDB/Export b/include/osgDB/Export new file mode 100644 index 000000000..b0a7909ae --- /dev/null +++ b/include/osgDB/Export @@ -0,0 +1,21 @@ +#ifndef OSGDB_EXPORT_ +#define OSGDB_EXPORT_ 1 + +#ifdef WIN32 + #pragma warning( disable : 4251 ) + #pragma warning( disable : 4275 ) + #pragma warning( disable : 4786 ) + +#endif + +#if defined(_MSC_VER) + # ifdef OSGDB_LIBRARY + # define OSGDB_EXPORT __declspec(dllexport) + # else + # define OSGDB_EXPORT __declspec(dllimport) + # endif /* OSGDBSG_LIBRARY */ +#else + # define OSGDB_EXPORT +#endif + +#endif diff --git a/include/osgDB/Field b/include/osgDB/Field new file mode 100644 index 000000000..c15ab629c --- /dev/null +++ b/include/osgDB/Field @@ -0,0 +1,106 @@ +#ifndef OSGDB_FIELD +#define OSGDB_FIELD 1 + +#include +#include + +#include +#include + +namespace osgDB { + + +class OSGDB_EXPORT Field +{ + public: + + enum { + MIN_CACHE_SIZE = 256 + }; + + Field(); + Field(const Field& field); + virtual ~Field(); + + virtual Field& operator = (const Field& ic); + + void reset(); + void addChar(char c); + int getNoCharacters() const { return _fieldCacheSize; } + + void setWithinQuotes(bool withinQuotes=true); + bool getWithinQuotes(); + + void setNoNestedBrackets(int no); + int getNoNestedBrackets(); + + enum FieldType + { + OPEN_BRACKET, + CLOSE_BRACKET, + STRING, + WORD, + REAL, + INTEGER, + BLANK, + UNINTIALISED + }; + + FieldType getFieldType() const; + + bool isValid() const; + + bool isOpenBracket() const; + bool isCloseBracket() const; + + bool isWord() const; + bool matchWord(const char* str) const; + bool matchWord(const char* str,int noCharacters) const; + + bool isString() const; + bool matchString(const char* str) const; + bool matchString(const char* str,int noCharacters) const; + bool isQuotedString() const; + + const char* getStr() const; + char* takeStr(); + + bool isInt() const; + bool matchInt(int i) const; + bool getInt(int& i) const; + + bool isUInt() const; + bool matchUInt(osg::uint i) const; + bool getUInt(osg::uint& i) const; + + bool isFloat() const; + bool matchFloat(float f) const; + bool getFloat(float& f) const; + + bool isDouble() const; + bool matchDouble(double f) const; + bool getDouble(double& d) const; + + static FieldType calculateFieldType(const char* str,bool withinQuotes=false); + + protected: + + void _init(); + void _free(); + void _copy(const Field& ic); + + int _fieldCacheCapacity; + int _fieldCacheSize; + char* _fieldCache; + + mutable FieldType _fieldType; + + bool _withinQuotes; + + int _noNestedBrackets; + +}; + +}; + +#endif // __SG_FIELD_H diff --git a/include/osgDB/FieldReader b/include/osgDB/FieldReader new file mode 100644 index 000000000..4d27a4a6e --- /dev/null +++ b/include/osgDB/FieldReader @@ -0,0 +1,63 @@ +#ifndef OSGDB_FIELDREADER +#define OSGDB_FIELDREADER 1 + +#include + +#include +#include + +#ifdef OSG_USE_IO_DOT_H +#include +#else +#include +using namespace std; +#endif + +namespace osgDB { + +class Field; + +class OSGDB_EXPORT FieldReader +{ + public: + + FieldReader(); + FieldReader(const FieldReader& ic); + virtual ~FieldReader(); + + virtual FieldReader& operator = (const FieldReader& ic); + + void attach(istream* input); + void detach(); + + virtual bool eof() const; + + bool readField(Field& fieldPtr); + void ignoreField(); + + /** no of unmatched `{' encounterd so far in file*/ + int getNoNestedBrackets() const; + + private: + + bool _readField(Field* fieldPtr); + + void _init(); + void _free(); + void _copy(const FieldReader& ic); + + istream* _fin; + bool _eof; + + bool findStartOfNextField(); + + int _noNestedBrackets; + + bool _delimiterEatLookUp[256]; + bool _delimiterKeepLookUp[256]; + +}; + +}; + +#endif // __SG_FIELD_READER_H diff --git a/include/osgDB/FieldReaderIterator b/include/osgDB/FieldReaderIterator new file mode 100644 index 000000000..622c9aa69 --- /dev/null +++ b/include/osgDB/FieldReaderIterator @@ -0,0 +1,68 @@ +#ifndef OSGDB_FIELDREADERITERATOR +#define OSGDB_FIELDREADERITERATOR 1 + +#include +#include + +namespace osgDB { + + +class OSGDB_EXPORT FieldReaderIterator +{ + public: + + enum { + MINIMUM_FIELD_READER_QUEUE_SIZE = 10 + }; + + FieldReaderIterator(); + FieldReaderIterator(const FieldReaderIterator& ic); + virtual ~FieldReaderIterator(); + + virtual FieldReaderIterator& operator = (const FieldReaderIterator& ic); + + void attach(istream* input); + void detach(); + + virtual bool eof() const; + + FieldReader& getFieldReader() { return _reader; } + + void insert(int pos,Field* field); + void insert(int pos,const char* str); + + Field& operator [] (int pos); + Field& field (int pos); + + FieldReaderIterator& operator ++ (); + FieldReaderIterator& operator += (int no); + +/** increments the itetor of the next simple field or + whole block if the current field[0] is an open bracket */ + void advanceOverCurrentFieldOrBlock(); + void advanceToEndOfCurrentBlock(); + void advanceToEndOfBlock(int noNestBrackets); + + bool matchSequence(const char* str); + + private: + + void _init(); + void _free(); + void _copy(const FieldReaderIterator& ic); + + FieldReader _reader; + + Field _blank; + + Field* _previousField; + + Field** _fieldQueue; + int _fieldQueueSize; + int _fieldQueueCapacity; + +}; + +}; + +#endif // __OSGDB_FIELD_READER_QUEUE_H diff --git a/include/osgDB/FileNameUtils b/include/osgDB/FileNameUtils new file mode 100644 index 000000000..559214360 --- /dev/null +++ b/include/osgDB/FileNameUtils @@ -0,0 +1,21 @@ +#ifndef OSGDB_FILENAMEUTILS +#define OSGDB_FILENAMEUTILS 1 + +#include + +#include + +namespace osgDB { + +OSGDB_EXPORT extern std::string getFilePath(const std::string& filename); +OSGDB_EXPORT extern std::string getFileExtension(const std::string& filename); +OSGDB_EXPORT extern std::string getLowerCaseFileExtension(const std::string& filename); +OSGDB_EXPORT extern std::string getSimpleFileName(const std::string& fileName); +OSGDB_EXPORT extern std::string getStrippedName(const std::string& fileName); + +OSGDB_EXPORT extern bool equalCaseInsensitive(const std::string& lhs,const std::string& rhs); +OSGDB_EXPORT extern bool equalCaseInsensitive(const std::string& lhs,const char* rhs); + +}; + +#endif diff --git a/include/osgDB/FileUtils b/include/osgDB/FileUtils new file mode 100644 index 000000000..e1d5a0a07 --- /dev/null +++ b/include/osgDB/FileUtils @@ -0,0 +1,46 @@ +#ifndef OSGDB_FILEUTILS +#define OSGDB_FILEUTILS 1 + +#include + +#include +#include + + +namespace osgDB { + +/** initialize the data file path, + * uses OSGFILEPATH environmental + * variable to defined.*/ +OSGDB_EXPORT extern void initFilePath( void ); + +/** set the data file path.*/ +OSGDB_EXPORT extern void setFilePath( const char *_path ); + +/** set the data file path.*/ +OSGDB_EXPORT extern const char* getFilePath(); + +/** find specified file on the set data file path.*/ +OSGDB_EXPORT extern char *findFile( const char *file ); + +/** find specified dso/dll.*/ +OSGDB_EXPORT extern char *findDSO( const char *name ); + +/** simple list of names to represent a directory's contents. */ +typedef std::vector DirectoryContents; + +/** return the directory/filename of a file if its is contained within specified directory. + * return "" if directory does not contain file. If caseInsensitive is set to true then + * a case insenstive comparision is used to compare fileName to directory contents. + * This is useful when unix programs attempt read case insentive windows filenames. + */ +OSGDB_EXPORT extern std::string findFileInDirectory(const std::string& fileName,const std::string& dirName,bool caseInsensitive=false); + +/** return the contents of a directory. + * returns an empty array on any error.*/ +OSGDB_EXPORT extern DirectoryContents getDirectoryContents(const std::string& dirName); + + +}; + +#endif diff --git a/include/osgDB/Input b/include/osgDB/Input new file mode 100644 index 000000000..c6a58f4fe --- /dev/null +++ b/include/osgDB/Input @@ -0,0 +1,48 @@ +#ifndef OSGDB_INPUT +#define OSGDB_INPUT 1 + +#include +#include +#include +#include + +#include + +#include +#include + +namespace osgDB { + +/** Class for managing the reading of ASCII .osg files.*/ +class OSGDB_EXPORT Input : public FieldReaderIterator +{ + public: + + Input(); + virtual ~Input(); + + virtual osg::Object* readObjectOfType(const osg::Object& compObj); + + virtual osg::Object* readObject(); + virtual osg::Image* readImage(); + virtual osg::Drawable* readDrawable(); + virtual osg::StateAttribute* readStateAttribute(); + virtual osg::Node* readNode(); + + virtual osg::Object* readObject(const std::string& fileName); + virtual osg::Image* readImage(const std::string& fileName); + virtual osg::Node* readNode(const std::string& fileName); + + virtual osg::Object* getObjectForUniqueID(const std::string& uniqueID); + virtual void regisiterUniqueIDForObject(const std::string& uniqueID,osg::Object* obj); + + private: + + typedef std::map UniqueIDToObjectMapping; + UniqueIDToObjectMapping _uniqueIDToObjectMap; + +}; + +}; + +#endif // __SG_INPUT_H diff --git a/include/osgDB/Output b/include/osgDB/Output new file mode 100644 index 000000000..77a6b0532 --- /dev/null +++ b/include/osgDB/Output @@ -0,0 +1,120 @@ +#ifndef OSGDB_OUTPUT +#define OSGDB_OUTPUT 1 + +#include + +#include + +#include +#include + +#ifdef OSG_USE_IO_DOT_H +#include +#else +#include +using namespace std; +#endif + +namespace osgDB { + +/** ofstream wrapper class for adding support for indenting. + Used in output of .osg ASCII files to improve their readability.*/ +class OSGDB_EXPORT Output : public ofstream +{ + public: + + Output(); + Output(const char* name); + + virtual ~Output(); + + void open(const char *name); + void open(const char *name,int mode); + + Output& indent(); + + inline const int getIndentStep() const { return _indentStep; } + inline void setIndentStep(int step) { _indentStep = step; } + + inline const int getIndent() const { return _indent; } + inline void setIndent(int indent) { _indent = indent; } + + inline const int getNumIndicesPerLine() const { return _numIndicesPerLine; } + inline void setNumIndicesPerLine(int num) { _numIndicesPerLine = num; } + + void moveIn(); + void moveOut(); + + virtual bool writeObject(const osg::Object& obj); + + bool getUniqueIDForObject(const osg::Object* obj,std::string& uniqueID); + bool createUniqueIDForObject(const osg::Object* obj,std::string& uniqueID); + bool registerUniqueIDForObject(const osg::Object* obj,std::string& uniqueID); + + enum PathNameHint + { + AS_IS, + FULL_PATH, + RELATIVE_PATH, + FILENAME_ONLY + }; + + inline void setPathNameHint(const PathNameHint pnh) { _pathNameHint = pnh; } + inline const PathNameHint getPathNameHint() const { return _pathNameHint; } + + virtual const std::string getFileNameForOutput(const std::string& filename) const; + + protected: + + // prevent copy construction and assignment. + Output(const Output&) : ofstream() {} + Output& operator = (const Output&) { return *this; } + + virtual void init(); + + int _indent; + int _indentStep; + + int _numIndicesPerLine; + + typedef std::map UniqueIDToLabelMapping; + UniqueIDToLabelMapping _objectToUniqueIDMap; + + std::string _filename; + + PathNameHint _pathNameHint; + +}; + +template +bool writeArrayBlock(Output& fw,T* start,T* finish) +{ + fw.indent() << "{" << endl; + fw.moveIn(); + int numIndicesThisLine = 0; + for(T* itr=start;itr!=finish;++itr) + { + if (numIndicesThisLine>=fw.getNumIndicesPerLine()) + { + fw << endl; + numIndicesThisLine = 0; + } + + if (numIndicesThisLine==0) fw.indent(); + else fw << " "; + + fw << *itr; + + ++numIndicesThisLine; + + } + fw << endl; + fw.moveOut(); + fw.indent() << "}" << endl; + return true; +} + + +}; + +#endif // __SG_OUTPUT_H diff --git a/include/osgDB/ReadFile b/include/osgDB/ReadFile new file mode 100644 index 000000000..4d35879c1 --- /dev/null +++ b/include/osgDB/ReadFile @@ -0,0 +1,39 @@ +#ifndef OSGDB_READFILE +#define OSGDB_READFILE 1 + +#include +#include + +#include + +#include + +namespace osgDB { + +/** Read an osg::Object from file. + * Return valid osg::Object on sucess, + * return NULL on failure. + * The osgDB::Registry is used to load the appropriate ReaderWriter plugin + * for the filename extension, and this plugin then handles the request + * to read the specified file.*/ +OSGDB_EXPORT extern osg::Object* readObjectFile(const std::string& filename); + +/** Read an osg::Image from file. + * Return valid osg::Image on sucess, + * return NULL on failure. + * The osgDB::Registry is used to load the appropriate ReaderWriter plugin + * for the filename extension, and this plugin then handles the request + * to read the specified file.*/ +OSGDB_EXPORT extern osg::Image* readImageFile(const std::string& filename); + +/** Read an osg::Node from file. + * Return valid osg::Node on sucess, + * return NULL on failure. + * The osgDB::Registry is used to load the appropriate ReaderWriter plugin + * for the filename extension, and this plugin then handles the request + * to read the specified file.*/ +OSGDB_EXPORT extern osg::Node* readNodeFile(const std::string& filename); + +}; + +#endif diff --git a/include/osgDB/ReaderWriter b/include/osgDB/ReaderWriter new file mode 100644 index 000000000..cd632f197 --- /dev/null +++ b/include/osgDB/ReaderWriter @@ -0,0 +1,33 @@ +#ifndef OSGDB_READERWRITER +#define OSGDB_READERWRITER 1 + +#include +#include +#include + +#include + +namespace osgDB { + + +/** pure virtual base class for reading and writing of non native formats. */ +class OSGDB_EXPORT ReaderWriter : public osg::Referenced +{ + public: + virtual ~ReaderWriter() {} + virtual const char* className() = 0; + virtual bool acceptsExtension(const std::string& /*extension*/) { return false; } + + virtual osg::Object* readObject(const std::string& /*fileName*/) { return NULL; } + virtual osg::Image* readImage(const std::string& /*fileName*/) { return NULL; } + virtual osg::Node* readNode(const std::string& /*fileName*/) { return NULL; } + + virtual bool writeObject(const osg::Object& /*obj*/,const std::string& /*fileName*/) {return false; } + virtual bool writeImage(const osg::Image& /*image*/,const std::string& /*fileName*/) {return false; } + virtual bool writeNode(const osg::Node& /*node*/,const std::string& /*fileName*/) { return false; } +}; + + +}; + +#endif // OSG_READERWRITER diff --git a/include/osgDB/Registry b/include/osgDB/Registry new file mode 100644 index 000000000..d5719b256 --- /dev/null +++ b/include/osgDB/Registry @@ -0,0 +1,181 @@ +#ifndef OSGDB_REGISTRY +#define OSGDB_REGISTRY 1 + +#include +#include +#include + +#include + +#include +#include +#include + +namespace osgDB { + +/** + Registry is a singleton factory which stores + the Objects types available at runtime for loading, + and any Object reader or writers which are linked in + at runtime for reading non-native file formats. + + The RegisterObjectProxy can be used to automatically register + at runtime a Object with the Registry. + + The RegisterReaderWriterProxy can be used to automatically + register at runtime a reader/writer with the Registry. +*/ +class OSGDB_EXPORT Registry +{ + public: + + ~Registry(); + + static Registry* instance(); + + + /** register an .fileextension alias to mapExt toExt, the later + * should the the extension name of the readerwriter plugin library. + * For example to map .tif files to the tiff loader, use + * addExtAlias("tif","tiff") which will enable .tif to be read + * by the libdb_tiff readerwriter plugin.*/ + void addFileExtensionAlias(const std::string mapExt, const std::string toExt); + + void addDotOsgWrapper(DotOsgWrapper* wrapper); + void removeDotOsgWrapper(DotOsgWrapper* wrapper); + + void addReaderWriter(ReaderWriter* rw); + void removeReaderWriter(ReaderWriter* rw); + + /** create the platform specific library name associated with file.*/ + std::string createLibraryNameForFile(const std::string& fileName); + + /** create the platform specific library name associated with file extension.*/ + std::string createLibraryNameForExt(const std::string& ext); + + /** find the library in the SG_LIBRARY_PATH and load it.*/ + bool loadLibrary(const std::string& fileName); + /** close the attached library with specified name.*/ + bool closeLibrary(const std::string& fileName); + + osg::Object* readObjectOfType(const osg::Object& compObj,Input& fr); + + osg::Object* readObject(Input& fr); + osg::Image* readImage(Input& fr); + osg::Drawable* readDrawable(Input& fr); + osg::StateAttribute* readStateAttribute(Input& fr); + osg::Node* readNode(Input& fr); + + bool writeObject(const osg::Object& obj,Output& fw); + + + osg::Object* readObject(const std::string& fileName); + bool writeObject(const osg::Object& obj, const std::string& fileName); + + osg::Image* readImage(const std::string& fileName); + bool writeImage(const osg::Image& obj, const std::string& fileName); + + osg::Node* readNode(const std::string& fileName); + bool writeNode(const osg::Node& node, const std::string& fileName); + + void setCreateNodeFromImage(bool flag) { _createNodeFromImage = flag; } + bool getCreateNodeFromImage() const { return _createNodeFromImage; } + + private: + + typedef std::map > DotOsgWrapperMap; + typedef std::vector > ReaderWriterList; + typedef std::vector > DynamicLibraryList; + typedef std::map ExtensionAliasMap; + + /** constructor is private, as its a singleton, preventing + construction other than via the instance() method and + therefore ensuring only one copy is ever constructed*/ + Registry(); + + /** get the attached library with specified name.*/ + DynamicLibraryList::iterator getLibraryItr(const std::string& fileName); + DynamicLibrary* getLibrary(const std::string& fileName); + + bool _createNodeFromImage; + + osg::Object* readObject(DotOsgWrapperMap& dowMap,Input& fr); + + DotOsgWrapperMap _objectWrapperMap; + DotOsgWrapperMap _imageWrapperMap; + DotOsgWrapperMap _drawableWrapperMap; + DotOsgWrapperMap _stateAttrWrapperMap; + DotOsgWrapperMap _nodeWrapperMap; + + DotOsgWrapperMap _classNameWrapperMap; + + ReaderWriterList _rwList; + DynamicLibraryList _dlList; + + bool _openingLibrary; + + // map to alias to extensions to plugins. + ExtensionAliasMap _extAliasMap; + +}; + +/** Proxy class for automatic registration of DotOsgWrappers with the Registry.*/ +class RegisterDotOsgWrapperProxy +{ + public: + + RegisterDotOsgWrapperProxy(osg::Object* proto, + const std::string& name, + const std::string& associates, + DotOsgWrapper::ReadFunc readFunc, + DotOsgWrapper::WriteFunc writeFunc, + DotOsgWrapper::ReadWriteMode readWriteMode=DotOsgWrapper::READ_AND_WRITE) + { + if (Registry::instance()) + { + _wrapper = new DotOsgWrapper(proto,name,associates,readFunc,writeFunc,readWriteMode); + Registry::instance()->addDotOsgWrapper(_wrapper.get()); + } + } + + ~RegisterDotOsgWrapperProxy() + { + if (Registry::instance()) + { + Registry::instance()->removeDotOsgWrapper(_wrapper.get()); + } + } + + protected: + osg::ref_ptr _wrapper; +}; + +/** Proxy class for automatic registration of reader/writers with the Registry.*/ +template +class RegisterReaderWriterProxy +{ + public: + RegisterReaderWriterProxy() + { + if (Registry::instance()) + { + _rw = new T; + Registry::instance()->addReaderWriter(_rw.get()); + } + } + + ~RegisterReaderWriterProxy() + { + if (Registry::instance()) + { + Registry::instance()->removeReaderWriter(_rw.get()); + } + } + + protected: + osg::ref_ptr _rw; +}; + +}; + +#endif diff --git a/include/osgDB/Version b/include/osgDB/Version new file mode 100644 index 000000000..1975ee7b2 --- /dev/null +++ b/include/osgDB/Version @@ -0,0 +1,33 @@ +#ifndef OSG_VERSION +#define OSG_VERSION 1 + +#include + +extern "C" { + +/** + * osgDBGetVersion() returns the library version number. + * Numbering conventon : osg_src-0.8.31 will return 0.8.31 from getVersion_osg. + * + * This C function can be also used to check for the existance of the OpenSceneGraph + * library using autoconf and its m4 macro AC_CHECK_LIB. + * + * Here is the code to add to your configure.in: + \verbatim + # + # Check for the OpenSceneGraph (OSG) library + # + AC_CHECK_LIB(osg, osgDBGetVersion, , + [AC_MSG_ERROR(OpenSceneGraph DB library not found. See http://www.openscenegraph.org)],) + \endverbatim +*/ +extern OSGDB_EXPORT const char* osgDBGetVersion(); + +/** + * getLibraryName() returns the library name in human friendly form. +*/ +extern OSGDB_EXPORT const char* osgDBGetLibraryName(); + +}; + +#endif diff --git a/include/osgDB/WriteFile b/include/osgDB/WriteFile new file mode 100644 index 000000000..bdcb9f2ce --- /dev/null +++ b/include/osgDB/WriteFile @@ -0,0 +1,41 @@ +#ifndef OSGDB_FILEUTILS +#define OSGDB_FILEUTILS 1 + +#include +#include + +#include + +#include + +namespace osgDB { + +/** Write an osg::Object to file. + * Return true on sucess, + * return false on failure. + * The osgDB::Registry is used to load the appropriate ReaderWriter plugin + * for the filename extension, and this plugin then handles the request + * to write the specified file.*/ + +OSGDB_EXPORT extern bool writeObjectFile(const osg::Object& object, const std::string& filename); + +/** Write an osg::Image to file. + * Return true on sucess, + * return false on failure. + * The osgDB::Registry is used to load the appropriate ReaderWriter plugin + * for the filename extension, and this plugin then handles the request + * to write the specified file.*/ +OSGDB_EXPORT extern bool writeImageFile(const osg::Image& image, const std::string& filename); + +/** Write an osg::Node to file. + * Return true on sucess, + * return false on failure. + * The osgDB::Registry is used to load the appropriate ReaderWriter plugin + * for the filename extension, and this plugin then handles the request + * to write the specified file.*/ +OSGDB_EXPORT extern bool writeNodeFile(const osg::Node& node, const std::string& filename); + + +}; + +#endif diff --git a/include/osgGLUT/Version b/include/osgGLUT/Version index 105416b13..3a3862266 100755 --- a/include/osgGLUT/Version +++ b/include/osgGLUT/Version @@ -7,8 +7,8 @@ extern "C" { /** - * getVersion_osgGLUT() returns the library version number. - * Numbering conventon : osg_src-0.8-31 will return 0.8.31 from getVersion_osgGLUT. + * osgGLUTGetVersion() returns the library version number. + * Numbering conventon : osg_src-0.8.31 will return 0.8.31. * * This C function can be also used to check for the existance of the OpenSceneGraph * library using autoconf and its m4 macro AC_CHECK_LIB. diff --git a/include/osgGLUT/Viewer b/include/osgGLUT/Viewer index 1871f9226..232b24959 100644 --- a/include/osgGLUT/Viewer +++ b/include/osgGLUT/Viewer @@ -1,12 +1,7 @@ #ifndef OSGGLUT_VIEWER #define OSGGLUT_VIEWER 1 -#include -#include -#include #include -#include -#include #include #include #include @@ -33,9 +28,9 @@ using namespace std; namespace osgGLUT{ /** A basic viewer base class which provides a window, simple keyboard and mouse interaction. - * Please note, this viewer class has been developed via a rather haphazzard - * path and *needs* a total rewrite. It currently surfices for osg demo's - * but shouldn't be viewed as the be all or end of osg viewer classes. + * Please note, this viewer class has been developed via a rather haphazard + * path and needs a total rewrite. It currently suffices for osg demo's + * but shouldn't be viewed as the be all and end of osg viewer classes. * Someone please rewrite it :-) */ class OSGGLUT_EXPORT Viewer : public osgUtil::GUIActionAdapter @@ -45,14 +40,34 @@ class OSGGLUT_EXPORT Viewer : public osgUtil::GUIActionAdapter Viewer(); virtual ~Viewer(); - virtual bool init( osg::Node* ); + void setWindowOrigin(int x, int y) { wx = x, wy = y; }; + void setWindowSize(int width, int height) { ww = width, wh = height; }; + void setWindowTitle(const std::string& title) { _title = title; } + /** init is deprecated, you should use addViewport instead. init is + * only available for backwards compatibility.*/ + virtual void init(osg::Node* rootnode); + + virtual void addViewport(osgUtil::SceneView* sv, + float x = 0.0, float y = 0.0, + float width = 1.0, float height = 1.0); + + virtual void addViewport(osg::Node*, + float x = 0.0, float y = 0.0, + float width = 1.0, float height = 1.0); + + const int getNumViewports() const { return _viewportList.size(); } + + osgUtil::SceneView* getViewportSceneView(unsigned int pos) + { return _viewportList[pos].sceneView.get(); } + + virtual bool open(); virtual bool run(); - // called on each frame redraw.. - virtual bool update(); - virtual bool traverse(); - virtual bool draw(); + // called on each frame redraw..return the time in ms for each operation. + virtual float app(unsigned int viewport); + virtual float cull(unsigned int viewport); + virtual float draw(unsigned int viewport); // initialize the clock. long initClock(); @@ -69,18 +84,20 @@ class OSGGLUT_EXPORT Viewer : public osgUtil::GUIActionAdapter void help(ostream& fout); // hande multiple camera. - void registerCameraManipulator(osgUtil::CameraManipulator* cm); - void selectCameraManipulator(unsigned int pos); + unsigned int registerCameraManipulator(osgUtil::CameraManipulator* cm, + unsigned int viewport = 0); + void selectCameraManipulator(unsigned int pos, + unsigned int viewport = 0); // derived from osgUtil::GUIActionAdapter - virtual void needRedraw(bool /*needed*/) {} // redraw always done. - virtual void needContinuousUpdate(bool /*needed*/) {} // continous update always - virtual void needWarpPointer(int x,int y); + virtual void requestRedraw() {} // redraw always by iddle callback done. + virtual void requestContinuousUpdate(bool /*needed*/) {} // continous update always + virtual void requestWarpPointer(int x,int y); protected: static void displayCB(); - static void reshapeCB(GLint w, GLint h); + static void reshapeCB(int w, int h); static void visibilityCB(int state); static void mouseMotionCB(int x, int y); static void mousePassiveMotionCB(int x, int y); @@ -94,25 +111,39 @@ class OSGGLUT_EXPORT Viewer : public osgUtil::GUIActionAdapter virtual void mousePassiveMotion(int x, int y); virtual void mouse(int button, int state, int x, int y); virtual void keyboard(unsigned char key, int x, int y); + + void setFocusedViewport(unsigned int pos); + int mapWindowXYToSceneView(int x, int y); + void showStats(void); static Viewer* s_theViewer; - osg::ref_ptr _sceneView; - typedef std::vector > CameraManipList; - osg::ref_ptr _cameraManipulator; - CameraManipList _cameraManipList; + struct ViewportDef + { + osg::ref_ptr sceneView; + float viewport[4]; // Win-size-relative [0,1] + osg::ref_ptr _cameraManipulator; + CameraManipList _cameraManipList; + }; + + typedef std::vector ViewportList; + ViewportList _viewportList; + unsigned int _focusedViewport; + std::string _saveFileName; - int ww, wh; + std::string _title; + int wx, wy, ww, wh; + int _is_open; #ifdef SGV_USE_RTFS - unsigned int frame_rate; - RTfs *fs; - #endif + unsigned int frame_rate; + RTfs *fs; + #endif bool _viewFrustumCullingActive; bool _smallFeatureCullingActive; @@ -125,8 +156,13 @@ class OSGGLUT_EXPORT Viewer : public osgUtil::GUIActionAdapter int flat_shade; int _two_sided_lighting; bool fullscreen; - int _saved_ww,_saved_wh; - bool _printStats; + int _saved_wx, _saved_wy, _saved_ww,_saved_wh; + float frRate; // gwm Jul 2001 added convolved ('averaged') frame rate + int _printStats; // gwm Jul 2001 change from bool + struct { // gwm Jul 2001, added for display of statistics + float timeApp, timeCull, timeDraw, timeFrame; + osg::Timer_t frameend; + } times[3]; // store up to 3 frames worth of times bool _useDisplayLists; osg::Timer _timer; diff --git a/include/osgUtil/CameraManipulator b/include/osgUtil/CameraManipulator index c4ffe8c30..a3f4a979e 100644 --- a/include/osgUtil/CameraManipulator +++ b/include/osgUtil/CameraManipulator @@ -1,15 +1,17 @@ #ifndef OSGUTIL_CAMERAMANIPULATOR #define OSGUTIL_CAMERAMANIPULATOR 1 -#include #include +#include + #include +#include #include #include namespace osgUtil{ -class OSGUTIL_EXPORT CameraManipulator : public osg::Referenced +class OSGUTIL_EXPORT CameraManipulator : public GUIEventHandler { public: @@ -20,7 +22,7 @@ class OSGUTIL_EXPORT CameraManipulator : public osg::Referenced virtual void setCamera(osg::Camera*); /** get the attached a camera.*/ - virtual osg::Camera * getCamera() const; + virtual const osg::Camera * getCamera() const; /** Attach a node to the manipulator. Automatically detaches previously attached node. @@ -29,17 +31,17 @@ class OSGUTIL_EXPORT CameraManipulator : public osg::Referenced virtual void setNode(osg::Node*) {} /** Return node if attached.*/ - virtual osg::Node* getNode() const { return NULL; } + virtual const osg::Node* getNode() const { return NULL; } /** Move the camera to the default position. May be ignored by manipulators if home functionality is not appropriate.*/ - virtual void home(GUIEventAdapter& ,GUIActionAdapter&) {} + virtual void home(const GUIEventAdapter& ,GUIActionAdapter&) {} /** Start/restart the manipulator.*/ - virtual void init(GUIEventAdapter& ,GUIActionAdapter&) {} + virtual void init(const GUIEventAdapter& ,GUIActionAdapter&) {} /** Handle events, return true if handled, false otherwise.*/ - virtual bool update(GUIEventAdapter& ea,GUIActionAdapter& us); + virtual bool handle(const GUIEventAdapter& ea,GUIActionAdapter& us); protected: diff --git a/include/osgUtil/DisplayListVisitor b/include/osgUtil/DisplayListVisitor index e38874ba6..d01e64172 100644 --- a/include/osgUtil/DisplayListVisitor +++ b/include/osgUtil/DisplayListVisitor @@ -1,15 +1,17 @@ -#ifndef OSGUTIL_COMPILEGEOSETVISITOR -#define OSGUTIL_COMPILEGEOSETVISITOR 1 +#ifndef OSGUTIL_DISPLAYLISTVISITOR +#define OSGUTIL_DISPLAYLISTVISITOR 1 #include #include +#include #include namespace osgUtil { -/** Visitor for traversing scene set each osg::GeoSet's _useDisplayList flag, or - * immediately compiling osg::GeoSet's OpenGL Display lists. The mode of operation +/** Visitor for traversing scene graph and setting each osg::GeoSet's _useDisplayList flag, + * with option to immediately compile osg::GeoSet's OpenGL Display lists. + * The mode of operation * of the vistor is controlled by setting the DisplayListMode either on visitor * constructor or via the setDisplayListMode() method. DisplayListMode options are: * _displayListMode == SWITCH_ON_AND_COMPILE_DISPLAY_LISTS cals gset->compile() on @@ -33,6 +35,7 @@ class OSGUTIL_EXPORT DisplayListVisitor : public osg::NodeVisitor enum DisplayListMode { SWITCH_ON_AND_COMPILE_DISPLAY_LISTS, + COMPILE_ON_DISPLAY_LISTS, SWITCH_ON_DISPLAY_LISTS, SWITCH_OFF_DISPLAY_LISTS }; @@ -48,6 +51,20 @@ class OSGUTIL_EXPORT DisplayListVisitor : public osg::NodeVisitor /** Get the operational mode.*/ DisplayListMode getDisplayListMode() const { return _displayListMode; } + + /** Set the State to use during traversal. */ + void setState(osg::State* state) + { + _externalState = state; + if (_externalState.valid()) _activeState = _externalState; + else _activeState = _localState; + } + + osg::State* getState() + { + return _activeState.get(); + } + /** Simply traverse using standard NodeVisitor traverse method.*/ virtual void apply(osg::Node& node) @@ -63,6 +80,13 @@ class OSGUTIL_EXPORT DisplayListVisitor : public osg::NodeVisitor protected: DisplayListMode _displayListMode; + + /** local state is created in constructor and used as the default state during traversal.*/ + osg::ref_ptr _localState; + /** external state is used to override the default state.*/ + osg::ref_ptr _externalState; + /** active state is equal to _externalState when it is valid, otherwise defaults to _localState.*/ + osg::ref_ptr _activeState; }; diff --git a/include/osgUtil/DriveManipulator b/include/osgUtil/DriveManipulator index 6996b3971..1d32d284b 100644 --- a/include/osgUtil/DriveManipulator +++ b/include/osgUtil/DriveManipulator @@ -19,32 +19,32 @@ class OSGUTIL_EXPORT DriveManipulator : public CameraManipulator virtual void setNode(osg::Node*); /** Return node if attached.*/ - virtual osg::Node* getNode() const; + virtual const osg::Node* getNode() const; /** Move the camera to the default position. May be ignored by manipulators if home functionality is not appropriate.*/ - virtual void home(GUIEventAdapter& ea,GUIActionAdapter& us); + virtual void home(const GUIEventAdapter& ea,GUIActionAdapter& us); /** Start/restart the manipulator.*/ - virtual void init(GUIEventAdapter& ea,GUIActionAdapter& us); + virtual void init(const GUIEventAdapter& ea,GUIActionAdapter& us); /** handle events, return true if handled, false otherwise.*/ - virtual bool update(GUIEventAdapter& ea,GUIActionAdapter& us); + virtual bool handle(const GUIEventAdapter& ea,GUIActionAdapter& us); private: /** Reset the internal GUIEvent stack.*/ void flushMouseEventStack(); /** Add the current mouse GUIEvent to internal stack.*/ - void addMouseEvent(GUIEventAdapter& ea); + void addMouseEvent(const GUIEventAdapter& ea); /** For the give mouse movement calculate the movement of the camera. Return true is camera has moved and a redraw is required.*/ bool calcMovement(); // Internal event stack comprising last three mouse events. - osg::ref_ptr _ga_t1; - osg::ref_ptr _ga_t0; + osg::ref_ptr _ga_t1; + osg::ref_ptr _ga_t0; osg::ref_ptr _node; diff --git a/include/osgUtil/FlightManipulator b/include/osgUtil/FlightManipulator index 9872e4c33..352405448 100644 --- a/include/osgUtil/FlightManipulator +++ b/include/osgUtil/FlightManipulator @@ -19,17 +19,17 @@ class OSGUTIL_EXPORT FlightManipulator : public CameraManipulator virtual void setNode(osg::Node*); /** Return node if attached.*/ - virtual osg::Node* getNode() const; + virtual const osg::Node* getNode() const; /** Move the camera to the default position. May be ignored by manipulators if home functionality is not appropriate.*/ - virtual void home(GUIEventAdapter& ea,GUIActionAdapter& us); + virtual void home(const GUIEventAdapter& ea,GUIActionAdapter& us); /** Start/restart the manipulator.*/ - virtual void init(GUIEventAdapter& ea,GUIActionAdapter& us); + virtual void init(const GUIEventAdapter& ea,GUIActionAdapter& us); /** handle events, return true if handled, false otherwise.*/ - virtual bool update(GUIEventAdapter& ea,GUIActionAdapter& us); + virtual bool handle(const GUIEventAdapter& ea,GUIActionAdapter& us); enum YawControlMode { YAW_AUTOMATICALLY_WHEN_BANKED, @@ -44,15 +44,15 @@ class OSGUTIL_EXPORT FlightManipulator : public CameraManipulator /** Reset the internal GUIEvent stack.*/ void flushMouseEventStack(); /** Add the current mouse GUIEvent to internal stack.*/ - void addMouseEvent(GUIEventAdapter& ea); + void addMouseEvent(const GUIEventAdapter& ea); /** For the give mouse movement calculate the movement of the camera. Return true is camera has moved and a redraw is required.*/ bool calcMovement(); // Internal event stack comprising last three mouse events. - osg::ref_ptr _ga_t1; - osg::ref_ptr _ga_t0; + osg::ref_ptr _ga_t1; + osg::ref_ptr _ga_t0; osg::ref_ptr _node; diff --git a/include/osgUtil/GUIActionAdapter b/include/osgUtil/GUIActionAdapter index ce9db5a10..42b9c45dd 100644 --- a/include/osgUtil/GUIActionAdapter +++ b/include/osgUtil/GUIActionAdapter @@ -6,14 +6,42 @@ namespace osgUtil{ -/** Pure virtual base class for adapting the GUI actions for use in CameraManipulators.*/ +/** Pure virtual base class for adapting the GUI actions requested by CameraManipulators + * into actions which are handled by the GUI toolkit of the users application. + * + * There are several was of using the ActionAdapter either inheriting it as + * done with osgGLUT::Viewer class or passing a simple struct to the camera + * manipulator then unpacking the results and working out what to do to respond + * to the requests. + * + * Also there are several ways to run your app and handle the updating of + * the window. osgGLUT::Viewer always has a idle callback registered which does a + * redraw all the time. osgGLUT::Viewer can safely ignore both requestRedraw() and + * requestContinousUpdate() as these are happening all the time anyway. + * + * Other apps will probably want to respond to the requestRedraw() and + * requestContinousUpdate(bool) and again there is more than one way to handle it. + * You can override requestRedraw() and implement to call your own window + * redraw straight away. Or you can implement so that a flag is set and + * then you then respond the flag being set in your own leisure. + * + * requestContinousUpdate(bool) is for enabling a throw or idle + * callback to be requested by the camera manipulator. Again you can respond + * to this immediately by registering a idle callback or a timed callback, or + * you can delay setting the callback and do at you own leisure. + * + * requestWarpPointer(int,int) is requesting a respositioning of a mouse pointer + * to a specified x,y location on the window. Used by some camera manipulators + * to initialize the mouse pointer when mouse position relative to a controls + * neutral mouse position is required, i.e when mimicking a aircrafts joystick. + */ class GUIActionAdapter { public: - virtual void needRedraw(bool needed=true) = 0; - virtual void needContinuousUpdate(bool needed=true) = 0; - virtual void needWarpPointer(int x,int y) = 0; + virtual void requestRedraw() = 0; + virtual void requestContinuousUpdate(bool needed=true) = 0; + virtual void requestWarpPointer(int x,int y) = 0; }; diff --git a/include/osgUtil/GUIEventAdapter b/include/osgUtil/GUIEventAdapter index 78929367a..700f537c3 100644 --- a/include/osgUtil/GUIEventAdapter +++ b/include/osgUtil/GUIEventAdapter @@ -7,8 +7,13 @@ namespace osgUtil{ -/** Pure virtual base class for adapting platform specfic events into - generic keyboard and mouse events. */ +/** Pure virtual base class for adapting platform specific events into + * generic keyboard and mouse events. + * + * Used as GUI toolkit independent input into the osgUtil::CameraManipualor's. + * For an example of how GUIEventAdapter is specialised for a particular GUI + * Toolkit see osgGLUT::GLUTEventAdapter. + */ class GUIEventAdapter : public osg::Referenced { public: @@ -36,7 +41,7 @@ class GUIEventAdapter : public osg::Referenced /** Get the EventType of the GUI event.*/ virtual EventType getEventType() const = 0; - /** key pressed, return -1 if inapropriate for this event. */ + /** key pressed, return -1 if inappropriate for this event. */ virtual int getKey() const = 0; /** button pressed/released, return -1 if inappropriate for this event.*/ @@ -69,7 +74,7 @@ class GUIEventAdapter : public osg::Referenced protected: - /** Force users to create on heap, so that mulitple referencing is safe.*/ + /** Force users to create on heap, so that multiple referencing is safe.*/ virtual ~GUIEventAdapter() {} }; diff --git a/include/osgUtil/IntersectVisitor b/include/osgUtil/IntersectVisitor index 2ae17a1ac..49ad3f429 100644 --- a/include/osgUtil/IntersectVisitor +++ b/include/osgUtil/IntersectVisitor @@ -2,8 +2,9 @@ #define OSGUTIL_INTERSECTVISITOR 1 #include -#include +#include #include +#include #include #include @@ -23,15 +24,15 @@ class OSGUTIL_EXPORT IntersectState : public osg::Referenced osg::Matrix* _matrix; osg::Matrix* _inverse; - typedef std::vector< std::pair > SegList; - SegList _segList; + typedef std::vector< std::pair > LineSegmentList; + LineSegmentList _segList; - typedef unsigned int SegmentMask; - typedef std::vector SegmentMaskStack; - SegmentMaskStack _segmentMaskStack; + typedef unsigned int LineSegmentmentMask; + typedef std::vector LineSegmentmentMaskStack; + LineSegmentmentMaskStack _segmentMaskStack; - bool isCulled(const osg::BoundingSphere& bs,SegmentMask& segMaskOut); - bool isCulled(const osg::BoundingBox& bb,SegmentMask& segMaskOut); + bool isCulled(const osg::BoundingSphere& bs,LineSegmentmentMask& segMaskOut); + bool isCulled(const osg::BoundingBox& bb,LineSegmentmentMask& segMaskOut); protected: @@ -52,14 +53,14 @@ class OSGUTIL_EXPORT Hit : public osg::Referenced bool operator < (const Hit& hit) const { - if (_originalSeghit._originalSeg) return false; + if (_originalLineSegmenthit._originalLineSegment) return false; return _ratio HitList; typedef std::vector HitList; - typedef std::map SegHitListMap; - HitList& getHitList(osg::Seg* seg) { return _segHitList[seg]; } - int getNumHits(osg::Seg* seg) { return _segHitList[seg].size(); } + typedef std::map LineSegmentHitListMap; + HitList& getHitList(osg::LineSegment* seg) { return _segHitList[seg]; } + int getNumHits(osg::LineSegment* seg) { return _segHitList[seg].size(); } bool hits(); @@ -111,10 +112,9 @@ class OSGUTIL_EXPORT IntersectVisitor : public osg::NodeVisitor virtual void apply(osg::Billboard& node); virtual void apply(osg::Group& node); - virtual void apply(osg::DCS& node); + virtual void apply(osg::Transform& node); virtual void apply(osg::Switch& node); virtual void apply(osg::LOD& node); - virtual void apply(osg::Scene& node); protected: @@ -127,13 +127,13 @@ class OSGUTIL_EXPORT IntersectVisitor : public osg::NodeVisitor bool enterNode(osg::Node& node); void leaveNode(); - typedef std::vector IntersectStateStack; + typedef std::vector > IntersectStateStack; IntersectStateStack _intersectStateStack; - osg::NodePath _nodePath; + osg::NodePath _nodePath; HitReportingMode _hitReportingMode; - SegHitListMap _segHitList; + LineSegmentHitListMap _segHitList; }; }; diff --git a/include/osgUtil/SceneView b/include/osgUtil/SceneView index 8749ebcec..12d98cf00 100644 --- a/include/osgUtil/SceneView +++ b/include/osgUtil/SceneView @@ -2,13 +2,11 @@ #define OSGUTIL_SCENEVIEW 1 #include -#include +#include #include #include -#include - -#include +#include namespace osgUtil { @@ -33,6 +31,11 @@ class OSGUTIL_EXPORT SceneView : public osg::Referenced */ osg::Node* getSceneData() { return _sceneData.get(); } + /** Get the const scene data which to view. The data will typically be + * an osg::Scene but can be any osg::Node type. + */ + const osg::Node* getSceneData() const { return _sceneData.get(); } + /** Set the viewport of the scene view. */ void setViewport(int x,int y,int width,int height) { @@ -62,8 +65,9 @@ class OSGUTIL_EXPORT SceneView : public osg::Referenced /** Get the background color.*/ const osg::Vec4& getBackgroundColor() const { return _backgroundColor; } - void setGlobalState(osg::GeoState* state) { _globalState = state; } - osg::GeoState* getGlobalState() const { return _globalState.get(); } + void setGlobalState(osg::StateSet* state) { _globalState = state; } + osg::StateSet* getGlobalState() { return _globalState.get(); } + const osg::StateSet* getGlobalState() const { return _globalState.get(); } enum LightingMode { HEADLIGHT, // default @@ -75,13 +79,33 @@ class OSGUTIL_EXPORT SceneView : public osg::Referenced LightingMode getLightingMode() const { return _lightingMode; } void setLight(osg::Light* light) { _light = light; } - osg::Light* getLight() const { return _light.get(); } + osg::Light* getLight() { return _light.get(); } + const osg::Light* getLight() const { return _light.get(); } void setCamera(osg::Camera* camera) { _camera = camera; } - osg::Camera* getCamera() const { return _camera.get(); } + osg::Camera* getCamera() { return _camera.get(); } + const osg::Camera* getCamera() const { return _camera.get(); } - void setRenderVisitor(osgUtil::RenderVisitor* rv) { _renderVisitor = rv; } - osgUtil::RenderVisitor* getRenderVisitor() const { return _renderVisitor.get(); } + void setState(osg::State* state) { _state = state; } + osg::State* getState() { return _state.get(); } + const osg::State* getState() const { return _state.get(); } + + + void setAppVisitor(osg::NodeVisitor* av) { _appVisitor = av; } + osg::NodeVisitor* getAppVisitor() { return _appVisitor.get(); } + const osg::NodeVisitor* getAppVisitor() const { return _appVisitor.get(); } + + void setCullVisitor(osgUtil::CullVisitor* cv) { _cullVisitor = cv; } + osgUtil::CullVisitor* getCullVisitor() { return _cullVisitor.get(); } + const osgUtil::CullVisitor* getCullVisitor() const { return _cullVisitor.get(); } + + void setRenderGraph(osgUtil::RenderGraph* rg) { _rendergraph = rg; } + osgUtil::RenderGraph* getRenderGraph() { return _rendergraph.get(); } + const osgUtil::RenderGraph* getRenderGraph() const { return _rendergraph.get(); } + + void setRenderStage(osgUtil::RenderStage* rs) { _renderStage = rs; } + osgUtil::RenderStage* getRenderStage() { return _renderStage.get(); } + const osgUtil::RenderStage* getRenderStage() const { return _renderStage.get(); } void setLODBias(float bias) { _lodBias = bias; } float getLODBias() const { return _lodBias; } @@ -94,7 +118,14 @@ class OSGUTIL_EXPORT SceneView : public osg::Referenced /** return true if SceneView automatically caclculates near and far clipping planes for each frame. */ - bool getCalcNearFar() { return _calc_nearfar; } + bool getCalcNearFar() const { return _calc_nearfar; } + + /** set whether the draw method should call renderer->prioritizeTexture.*/ + void setPrioritizeTextures(bool pt) { _prioritizeTextures = pt; } + + /** get whether the draw method should call renderer->prioritizeTexture.*/ + bool getPrioritizeTextures() const { return _prioritizeTextures; } + /** Calculate, via glUnProject, the object coordinates of a window point. Note, current implementation requires that SceneView::draw() has been previously called @@ -124,7 +155,13 @@ class OSGUTIL_EXPORT SceneView : public osg::Referenced bool projectObjectIntoWindow(const osg::Vec3& object,osg::Vec3& window) const; + /** do app traversal of attached scene graph using App NodeVisitor.*/ + virtual void app(); + + /** do cull traversal of attached scene graph using App CullVisitor.*/ virtual void cull(); + + /** do draw traversal of draw bins generated by cull traversal.*/ virtual void draw(); protected: @@ -132,11 +169,17 @@ class OSGUTIL_EXPORT SceneView : public osg::Referenced virtual ~SceneView(); osg::ref_ptr _sceneData; - osg::ref_ptr _globalState; + osg::ref_ptr _globalState; osg::ref_ptr _light; osg::ref_ptr _camera; - osg::ref_ptr _renderVisitor; + osg::ref_ptr _state; + osg::ref_ptr _appVisitor; + osg::ref_ptr _cullVisitor; + osg::ref_ptr _rendergraph; + osg::ref_ptr _renderStage; + + bool _need_compile; bool _calc_nearfar; @@ -150,13 +193,11 @@ class OSGUTIL_EXPORT SceneView : public osg::Referenced // viewport x,y,width,height respectiveyly. GLint _view[4]; - // model and project matices, used by glUnproject to get - // to generate rays form the eyepoint through the mouse x,y. - GLdouble _model[16]; - GLdouble _proj[16]; - LightingMode _lightingMode; - + + bool _prioritizeTextures; + + int _frameNumber; }; }; diff --git a/include/osgUtil/TrackballManipulator b/include/osgUtil/TrackballManipulator index 47aad565b..6d21505ba 100644 --- a/include/osgUtil/TrackballManipulator +++ b/include/osgUtil/TrackballManipulator @@ -19,25 +19,25 @@ class OSGUTIL_EXPORT TrackballManipulator : public CameraManipulator virtual void setNode(osg::Node*); /** Return node if attached.*/ - virtual osg::Node* getNode() const; + virtual const osg::Node* getNode() const; /** Move the camera to the default position. May be ignored by manipulators if home functionality is not appropriate.*/ - virtual void home(GUIEventAdapter& ea,GUIActionAdapter& us); + virtual void home(const GUIEventAdapter& ea,GUIActionAdapter& us); /** Start/restart the manipulator.*/ - virtual void init(GUIEventAdapter& ea,GUIActionAdapter& us); + virtual void init(const GUIEventAdapter& ea,GUIActionAdapter& us); /** handle events, return true if handled, false otherwise.*/ - virtual bool update(GUIEventAdapter& ea,GUIActionAdapter& us); + virtual bool handle(const GUIEventAdapter& ea,GUIActionAdapter& us); private: /** Reset the internal GUIEvent stack.*/ void flushMouseEventStack(); /** Add the current mouse GUIEvent to internal stack.*/ - void addMouseEvent(GUIEventAdapter& ea); + void addMouseEvent(const GUIEventAdapter& ea); /** For the give mouse movement calculate the movement of the camera. Return true is camera has moved and a redraw is required.*/ @@ -52,8 +52,8 @@ class OSGUTIL_EXPORT TrackballManipulator : public CameraManipulator bool isMouseMoving(); // Internal event stack comprising last three mouse events. - osg::ref_ptr _ga_t1; - osg::ref_ptr _ga_t0; + osg::ref_ptr _ga_t1; + osg::ref_ptr _ga_t0; osg::ref_ptr _node; diff --git a/include/osgWX/Export b/include/osgWX/Export new file mode 100644 index 000000000..94f264405 --- /dev/null +++ b/include/osgWX/Export @@ -0,0 +1,22 @@ +// The following symbole has a underscore suffix for compatibility. +#ifndef OSGWX_EXPORT_ +#define OSGWX_EXPORT_ 1 + +#ifdef WIN32 + #pragma warning( disable : 4251 ) + #pragma warning( disable : 4275 ) + #pragma warning( disable : 4786 ) +#endif + +#if defined(_MSC_VER) + # ifdef OSGWX_LIBRARY + # define OSGWX_EXPORT __declspec(dllexport) + # else + # define OSGWX_EXPORT __declspec(dllimport) + #endif /* OSGWX_LIBRARY */ +#else + #define OSGWX_EXPORT +#endif + +#endif + diff --git a/include/osgWX/Version b/include/osgWX/Version new file mode 100644 index 000000000..2c7ca857e --- /dev/null +++ b/include/osgWX/Version @@ -0,0 +1,35 @@ +#ifndef OSGWX_VERSION +#define OSGWX_VERSION 1 + +#include + + +extern "C" { + +/** + * osgWXGetVersion() returns the library version number. + * Numbering conventon : osg_src-0.8.31 will return 0.8.31. + * + * This C function can be also used to check for the existance of the OpenSceneGraph + * library using autoconf and its m4 macro AC_CHECK_LIB. + * + * Here is the code to add to your configure.in: + \verbatim + # + # Check for the OpenSceneGraph (OSG) WX library + # + AC_CHECK_LIB(osg, osgWXGetVersion, , + [AC_MSG_ERROR(OpenSceneGraph WX library not found. See http://www.openscenegraph.org)],) + \endverbatim +*/ +extern OSGWX_EXPORT const char* osgWXGetVersion(); + +/** + * getLibraryName_osgWX() returns the library name in human friendly form. +*/ +extern OSGWX_EXPORT const char* osgWXGetLibraryName(); + +}; + +#endif + diff --git a/include/osgWX/WXEventAdapter b/include/osgWX/WXEventAdapter new file mode 100644 index 000000000..6f94cb1c1 --- /dev/null +++ b/include/osgWX/WXEventAdapter @@ -0,0 +1,106 @@ + +#ifndef OSGWX_WXEVENTADAPTER +#define OSGWX_WXEVENTADAPTER 1 + +#include + +#include + +namespace osgWX { + +/** Class for adapting WX events so that they can be used as input to + osgUtil::CameraManipulators.*/ +class OSGWX_EXPORT WXEventAdapter : public osgUtil::GUIEventAdapter +{ +public: + WXEventAdapter(); + virtual ~WXEventAdapter() {} + + /** Get the EventType of the GUI event.*/ + virtual EventType getEventType() const { return _eventType; } + + /** key pressed, return -1 if inapropriate for this event. */ + virtual int getKey() const { return _key; } + + /** button pressed/released, return -1 if inappropriate for this event.*/ + virtual int getButton() const { return _button; } + + /** window minimum x. */ + virtual int getXmin() const { return _Xmin; } + + /** window maximum x. */ + virtual int getXmax() const { return _Xmax; } + + /** window minimum y. */ + virtual int getYmin() const { return _Ymin; } + + /** window maximum y. */ + virtual int getYmax() const { return _Ymax; } + + /** current mouse x position.*/ + virtual int getX() const { return _mx; } + + /** current mouse y position.*/ + virtual int getY() const { return _my; } + + /** current mouse button state */ + virtual unsigned int getButtonMask() const { return _buttonMask; } + + /** time in seconds of event. */ + virtual float time() const { return _time; } + + /** static method for setting window dimensions.*/ + static void setWindowSize(int Xmin, int Ymin, int Xmax, int Ymax); + + /** static method for setting button state.*/ + static void setButtonMask(unsigned int buttonMask); + + /** method for adapting resize events. */ + void adaptResize(float t, int Xmin, int Ymin, int Xmax, int Ymax); + + /** method for adapting mouse motion events whilst mouse buttons are pressed.*/ + void adaptMouseMotion(float t, int x, int y); + + /** method for adapting mouse motion events whilst no mouse button are pressed.*/ + void adaptMousePassiveMotion(float t,int x, int y); + + /** method for adapting mouse button pressed/released events.*/ + void adaptMouse(float t, class wxMouseEvent *event); + + /** method for adapting keyboard events.*/ + void adaptKeyboard(float t,unsigned char key, int x, int y ); + + /** method for adapting frame events, i.e. iddle/display callback.*/ + void adaptFrame(float t); + + void copyStaticVariables(); + +protected: + EventType _eventType; + int _key; + int _button; + int _Xmin,_Xmax; + int _Ymin,_Ymax; + int _mx; + int _my; + unsigned int _buttonMask; + float _time; + + // used to accumulate the button mask state, it represents + // the current button mask state, which is modified by the + // adaptMouse() method which then copies it to value _buttonMask + // which required the mouse buttons state at the time of the event. + static unsigned int _s_accumulatedButtonMask; + + // used to store window min and max values. + static int _s_Xmin; + static int _s_Xmax; + static int _s_Ymin; + static int _s_Ymax; + static int _s_mx; + static int _s_my; +}; + +} // namespace osgWX + +#endif diff --git a/index.html b/index.html index 391db30c9..e6f5bdca7 100644 --- a/index.html +++ b/index.html @@ -5,157 +5,355 @@ OSG Distribution - - -
-

-Open Scene Graph

-The Open Scene Graph (OSG) is an Open Source (LGPL), Stanadard C++, OpenGL -based scene graph for cross-platform 3D real-time visualisation..  + + +
Installation    Contents +of Distribution    Documentation   Plugin +Dependencies   Data Sources   +Contacts +

The Open Scene Graph (OSG) is an Open Source (LGPL), Standard C++, OpenGL +based scene graph for cross platform 3D real-time visualisation.  The OSG is simply a scene graph and by design does not attempt to encompass application frame works and user interface, the design is kept focused on the issues of representing a 3D scene and rendering it in real-time. -

There are also support libraries such as osgGLUT for bringing up a basic +The OSG currently supports Linux, IRIX, Windows and FreeBSD platforms with +the potential of support for further platforms. A Mac port is already underway. +

The OSG is composed of a core scene graph library (osg) which is the +basis for all osg apps, an optional scene graph utility library (osgUtil) +which can be used for higher level functionality such cullers and renderers +and a database utility library (osgDB) coupled with a set of plug-ins +(osgPlugins) which are dynamically loaded by the osgDB library to support +the reading and writing of file formats or node toolkits. +

There are also support libraries such as osgGLUT for bringing up a basic UI, however this is not the focus of the OSG.  For more sophisticated -user interfaces it is recommended to intergrate the OSG graphics with a -fully fledge UI toolkit, this has already been done by users for FLTK, -WxWindows and X, with the potential for many more. -

This release is a ALPHA version, and is subject to continuous development -with the API of features subject to change. +user interfaces it is recommended to integrate the OSG graphics with a +fully fledge UI toolkit, this has already been done by users for FLTK, SDL, +WxWindows, Qt and X, with the potential for many more. For example, osgWX is +also included to assist integration of wxWindows with the OSG and demonstrated +in the wxsgv demo, however both these libraries are not compiled by default +since most systems won't have wxWindows installed. Check the mailing list +archives for info on these developments. +

For the purpose of demonstating the functionality of the osg, nine demo +apps are provided, sgv (a scene graph viewer), osgconv (a command line +utility for converted multiple input files into a native .osg target file),  +hangglide (a flight simulation demo over small hang gliding site), osgcube +(a very simple demo of an animated cube) and osgreflect (a demo of how planar +reflections can be achieved), osgtexture (a demo of some of the various +texture modes that the OSG supports), osgimpostor (a demo of impostors in +action) and osgviews (a demo of using mulitple viewports on the same or +multiple scenes), and finally wxsgv a viewer demostrating osg integration +with wxWindows applications (not compiled by default.) +

This release is a ALPHA version, and is under continuous development +with the API and features subject to change. If you plan to use the OSG +then please join the mailing list and provide us with feedback on how +you're getting on or the problems that you come across. This helps keep +the OSG development going in the right direction and ensures the problems +are fixed as early on in the development as possible.

+

For instructions of how to compile, install the osg libraries and to -run the demos please read the README file. -

Regards, +run the demos please read the INSTALL file. + +

Robert Osfield. -
January 2001. +

robert@openscenegraph.com. +
August 2001.


-

Contacts -

The OSG's website is http://www.openscenegraph.org +

Contacts +

The OSG's web site is http://www.openscenegraph.org/

The OSG's mailing list and mirror of downloads can be accessed at
source forge -  http://sourceforge.net/projects/openscenegraph -

Bugs, patches, querries can be sent to the info@openscenegraph.org +

Bugs, patches, queries can be sent to the robert@openscenegraph.com or to the mailing list. +

Patches are best sent as complete files, as tarball if numerous file +changes have been made.


-

Contents of distribution -

./        Root directory. -

README       -text file containing guide of how to get the OSG compiling, and running -the demos. -
COPYING    text  file containing -the details of the Open Source LGPL license which the OSG is released under -
AUTHORS    text file containing -names of contributors to the osg. -
NEWS           -text file listing coarsed grained changes between releases. -
ChangeLog     text file -listing fine grained changes between releases. -
TODO           -text file listing  left to implement/extend/rewrite. -
FAQ              -text file listing Fequently asked quesions. -
Makefile         -Unix makefile. -
index.html       This file!
+

+Contents of distribution

+./        Root directory. +
README     text +bare bones readme file. +
INSTALL    text file +containing guide of how to get the OSG compiling, and running the demos. +
COPYING    text  +file containing the details of the OSG's Open Source LGPL license. +
AUTHORS    text file +containing names of contributors to the osg. +
NEWS       text +file listing coarse grained changes between releases. +
ChangeLog  text file listing +fine grained changes between releases. +
TODO       text +file listing  left to implement/extend/rewrite. +
FAQ         +text file listing Frequently asked questions. +
Makefile   Unix makefile. +
index.html This file!


doc/   Documentation directory -

index.html      -Documentation index. -
osg/               -core scene graph reference guide. -
osgUtil/          -scene graph utilities reference guide. -
osgGLUT/     -simple GLUT based viewer base classes reference guide.
+
index.html       +Documentation index +
osg/             +Scene graph reference guide. +
osgUtil/         +Scene graph utilities reference guide. +
osgDB/           +Scene graph database utilities reference guide. +
osgGLUT/         +Simple GLUT based viewer base classes reference guide. +
osgWX/           +wxWindows integration classes reference guide
-


include/     External -includes (i.e. files which would be installed in /usr/include) -

include/osg/             -The OSG library header files. -
include/osgUtil/        -The OSG Utility library header files. -
include/osgGLUT/   The OSG -GLUT library header files.
-


src/    source files (including -internal includes) -

src/osg           -The OSG library source files. -
                      -Contians all core osg classes, including -
                      -reader/writer support for the .osg ascii format, -
                      -and sgi's rgb image format. -

src/osgUtil      -The OSG utility library source files. -
                      -Contains useful utility classes such as for setting -
                       -up and rendering/draw. -

src/osgGLUT  The OSG GLUT library source -files. -
                       -Contains basic GLUT viewer base classes used by -
                       -demo prgrams to bring up window and provide keyboard -
                       -and mouse interaction. -

src/osgPlugins/  Import/Export/Node -kit plug-ins to the OSG. -
                        -flt/      Open -Flight reader plugin. -
                        -fly/      Hang -gliding flying site reader plugin. -
                        -pfb/      Performer -reader and writer plugin. -
                        -png/      PNG -image file format reader plugin. -
                        -gif/      GIF -image file format reader plugin. -
                        -jpeg/     JPEG image -file format reader plugin. -
                        -pic/      PIC -image file format reader plugin. -
                        -tga/      TGA -image file format reader plugin. -
                        -tiff/     TIFF image -file format reader plugin. -

src/Demos/      sgv/      -A basic scene graph viewer for the OSG which is able to load .osg file -and above formats. -
                       -cube/    A basic animation -of an oscillating cube.

+

include/     External includes +(i.e. files which would be installed in /usr/include) +

include/osg/       +The OSG library header files. +
include/osgUtil/  The OSG +Util library header files. +
include/osgDB/    The +OSG Database library header files. +
include/osgGLUT/  The OSG +GLUT utiltiy library header files. +
include/osgWX/    The OSG +WX utiltiy library header files.
-


lib/                         -The local repository for the OSG library and plugins (files to be installed -in /usr/lib/ or /usr/local/lib) -
lib/osgPlugins/        -The local repository for the OSG plugins (files to be installed in /usr/lib/osgPlugins -or -
                             -/usr/local/lib/osgPlugins) -

bin/                        -The local repository for the OSG binary files (files to be installed in -/usr/bin or /usr/local/bin) -

Make/                    -Unix platform specific make rules and dependancies. -

VisualStudio/          -MS VisualC++ 6.0 Make/Workspace files. -

dist/                        -Distribution make files for RedHat Linux. -

NSPlugin/               -Netscape plugin viewer for Linux. + +

src/    source files (including internal +includes) +

src/osg       +The OSG library source files. +
              +Contains all core osg classes, including reader/writer support for +
              +the .osg ascii format, and sgi's rgb image format. +

src/osgUtil  The OSG utility +library source files. +
              +Contains useful utility classes such as for setting +
              +up and rendering/draw. +

src/osgDB    The OSG +database utility library source files. +
              +Contains useful utility classes such as for reading +
              +and writing 3D databases and image files. +

src/osgGLUT  The OSG GLUT library +source files. +
              +Contains basic GLUT viewer base classes used by +
              +demo programs to bring up window and provide keyboard +
              +and mouse interaction. +

src/osgWX    The OSG WX library +source files. +
              +Contains WXEventAdapter to assist integration of wxWindnows with the OSG. +

src/osgPlugins/     +Import/Export/Node kit plug-ins to the OSG. +
           osg/     +.osg native ASCII reader/write plugin. +
           flt/     +.flt Open Flight reader plugin. +
           lib3ds/  +.3ds Auto Studio Maxx reader plugin. +
           lwo/     +.lwo Light Wave binary (.lwo,.lw & .geo) reader plugin. +
           obj/     +.obj Alias Wavefront reader plugin. +
           pfb/     +.pfb (and others) Performer reader and writer plugin. +
           dw/      +.dw Design Workshop reader plugin. +
           rgb/     +.rgb RGB image file format reader plugin. +
           png/     +.png PNG image file format reader plugin. +
           gif/     +.gif GIF image file format reader plugin. +
           jpeg/    +.jpg JPEG image file format reader plugin. +
           pic/     +.pic PIC image file format reader plugin. +
           tga/     +.tga TGA image file format reader plugin. +
           tiff/    +.tif TIFF image file format reader plugin. +

src/Demos/ sgv/           +A basic scene graph viewer for the OSG which is loads .osg files and +above formats. +
           osgconv/       +A program which reads input files into a single scene graph and outputs +the results. +
           hangglide/     +A program which of creates a flying site and allows users to fly over +the scene. +
           osgtexture/    +A simple program which demonstrates how to use various textures modes. +
           osgcube/       +A basic animation of an oscillating cube. +
           osgreflect/    +A demonstration of multi-pass stencil buffer based planar reflections. +
           osgimpostor/   +A basic demo to show how to use the osg::Impostor node. +
           osgviews/      +A demo of multiple views of the same or multiple scenes. +
           wxsgv/         +A demo of wxWindows viewer integrated with the OSG. +

+ +


lib/             +The local repository for the OSG library and plugins (files to be +installed in /usr/lib/ or /usr/local/lib) +

lib/osgPlugins/  The local +repository for the OSG plugins (files to be installed in /usr/lib/osgPlugins +or /usr/local/lib/osgPlugins) +

bin/             +The local repository for the OSG binary files (files to be installed +in /usr/bin or /usr/local/bin) +

Make/            +Unix platform specific make rules and dependencies. +

VisualStudio/    MS +VisualC++ 6.0 Make/Workspace files for Windows. +

Metrowerks/      +CodeWarroir's Make/Workspace files for Mac. +

dist/            +Distribution make files for RedHat Linux and IRIX. +
. +
+


+

+Plug-in dependencies

+Follows is the list of depedencies which some of the osgPlugins require, +note the core osg and viewer do not need the following dependencies, you +only need the following if you require each specific plugin.  Note, +the flt, 3ds, pic, tga, do not have any dependencies other than Standard +C++ so will compile straight of the bag.  Under Linux the majority +of the depedancies below come as standard +
with distributions so you may not need to download them at all.  +Its best to try out a straight compile of the osg, if you get missing includes/libs +errors then chase up the below. +
    +
  • +src/osgPlugins/pfb
  • + +
    There is a Performer plugin in this distribution for converting from +Performer to OSG and from OSG to Performer.  This plugin requires +Performer to be installed and therefore is not compiled by default. If +you have Performer (available under Linux and IRIX) then edit src/osgPlugins/Make +to compile under the plugin.  Performer can be downloaded from : + + +
  • +src/osgPlugins/png
  • + +
    The png plugin depends upon the libpng and zlib (for compression) libraries, +if you don't already have it installed, you'll need to download, compile +and install it. Project home pages are: + + +
  • +src/osgPlugins/gif
  • + +
    The gif plugin depends upon the libungif library, if you don't already +have it installed, you'll need to download, compile and install it. Project +home page is: + +Ftp download at : + + +
  • +src/osgPlugins/jpeg
  • + +
    The jpeg plugin depends upon the libjpeg library, if you don't already +have it installed, you'll need to download, compile and install it. Project +home page is: + + +
  • +src/osgPlugins/tiff
  • + +
    The tiff plugin depends upon the libtiff library, if you don't already +have it installed, you'll need to download, compile and install it. Project +home page is: + + +
  • +src/osgPlugins/zip
  • + +
    The zip compressed archive plugin depends upon the unzip executable +being available on your system.  If it is not then you'll be able +to find binaries at: + + +
  • +src/osgPlugins/tgz
  • + +
    The tgz compressed archive plugin depends upon the unzip executable +being available on your system.  If it is not then you'll be able +to find binaries at: + + +
  • +src/osgPlugins/osgtgz
  • + +
    Has the same dependencies as the tgz plugin above.
+ +


+


+

+Data Sources

+ + + diff --git a/src/Demos/Makefile b/src/Demos/Makefile index 09e0afd30..c900c2b63 100644 --- a/src/Demos/Makefile +++ b/src/Demos/Makefile @@ -1,29 +1,32 @@ #!smake SHELL=/bin/sh -DIRS = sgv cube +DIRS = sgv osgconv osgcube osgreflect osgtexture osgimpostor osgviews hangglide all : - for f in $(DIRS) ; do cd $$f; make ; cd ..; done + for f in $(DIRS) ; do cd $$f; $(MAKE) || exit 1; cd ..; done clean : - for f in $(DIRS) ; do cd $$f; make clean; cd ..; done + for f in $(DIRS) ; do cd $$f; $(MAKE) clean; cd ..; done clobber : - for f in $(DIRS) ; do cd $$f; make clobber; cd ..; done + for f in $(DIRS) ; do cd $$f; $(MAKE) clobber; cd ..; done depend : - for f in $(DIRS) ; do cd $$f; make depend; cd ..; done + for f in $(DIRS) ; do cd $$f; $(MAKE) depend; cd ..; done to_unix : for f in $(DIRS) ; do cd $$f; to_unix Makefile Makefile; cd ..; done - for f in $(DIRS) ; do cd $$f; make to_unix; cd ..; done + for f in $(DIRS) ; do cd $$f; $(MAKE)to_unix; cd ..; done + +beautify : + for f in $(DIRS) ; do cd $$f; $(MAKE)beautify; cd ..; done install : - for f in $(DIRS) ; do cd $$f; make install; cd ..; done + for f in $(DIRS) ; do cd $$f; $(MAKE) install; cd ..; done instlinks : - for f in $(DIRS) ; do cd $$f; make instlinks; cd ..; done + for f in $(DIRS) ; do cd $$f; $(MAKE) instlinks; cd ..; done instclean : - for f in $(DIRS) ; do cd $$f; make instclean; cd ..; done + for f in $(DIRS) ; do cd $$f; $(MAKE) instclean; cd ..; done diff --git a/src/Demos/hangglide/GliderManipulator.cpp b/src/Demos/hangglide/GliderManipulator.cpp new file mode 100644 index 000000000..0d77c577f --- /dev/null +++ b/src/Demos/hangglide/GliderManipulator.cpp @@ -0,0 +1,229 @@ +#include +#include + +#include "GliderManipulator.h" + +using namespace osg; +using namespace osgUtil; + +GliderManipulator::GliderManipulator() +{ + _modelScale = 0.01f; + _velocity = 0.0f; + _yawMode = YAW_AUTOMATICALLY_WHEN_BANKED; +} + + +GliderManipulator::~GliderManipulator() +{ +} + + +void GliderManipulator::setNode(osg::Node* node) +{ + _node = node; + if (_node.get()) + { + const osg::BoundingSphere& boundingSphere=_node->getBound(); + _modelScale = boundingSphere._radius; + } +} + + +const osg::Node* GliderManipulator::getNode() const +{ + return _node.get(); +} + + +void GliderManipulator::home(const GUIEventAdapter& ea,GUIActionAdapter& us) +{ + if(_node.get() && _camera.get()) + { + + const osg::BoundingSphere& boundingSphere=_node->getBound(); + + osg::Vec3 eye = boundingSphere._center+osg::Vec3(-boundingSphere._radius*0.15f,-boundingSphere._radius*0.15f,-boundingSphere._radius*0.03f); + + _camera->setView(eye, + eye+osg::Vec3(1.0f,1.0f,-0.1f), + osg::Vec3(0.0f,0.0f,1.0f)); + + _velocity = boundingSphere._radius*0.01f; + + us.requestRedraw(); + + us.requestWarpPointer((ea.getXmin()+ea.getXmax())/2,(ea.getYmin()+ea.getYmax())/2); + + flushMouseEventStack(); + + } + +} + + +void GliderManipulator::init(const GUIEventAdapter& ea,GUIActionAdapter& us) +{ + flushMouseEventStack(); + + us.requestContinuousUpdate(false); + + const osg::BoundingSphere& boundingSphere=_node->getBound(); + _velocity = boundingSphere._radius*0.01f; + + us.requestWarpPointer((ea.getXmin()+ea.getXmax())/2,(ea.getYmin()+ea.getYmax())/2); + +} + + +bool GliderManipulator::handle(const GUIEventAdapter& ea,GUIActionAdapter& us) +{ + if(!_camera.get()) return false; + + switch(ea.getEventType()) + { + case(GUIEventAdapter::PUSH): + { + + addMouseEvent(ea); + us.requestContinuousUpdate(true); + if (calcMovement()) us.requestRedraw(); + + } + return true; + case(GUIEventAdapter::RELEASE): + { + + addMouseEvent(ea); + us.requestContinuousUpdate(true); + if (calcMovement()) us.requestRedraw(); + + } + return true; + case(GUIEventAdapter::DRAG): + { + + addMouseEvent(ea); + us.requestContinuousUpdate(true); + if (calcMovement()) us.requestRedraw(); + + } + return true; + case(GUIEventAdapter::MOVE): + { + + addMouseEvent(ea); + us.requestContinuousUpdate(true); + if (calcMovement()) us.requestRedraw(); + + } + return true; + + case(GUIEventAdapter::KEYBOARD): + if (ea.getKey()==' ') + { + flushMouseEventStack(); + home(ea,us); + us.requestRedraw(); + us.requestContinuousUpdate(false); + return true; + } + return false; + case(GUIEventAdapter::FRAME): + addMouseEvent(ea); + if (calcMovement()) us.requestRedraw(); + return true; + case(GUIEventAdapter::RESIZE): + { + init(ea,us); + us.requestRedraw(); + } + return true; + default: + return false; + } +} + + +void GliderManipulator::flushMouseEventStack() +{ + _ga_t1 = NULL; + _ga_t0 = NULL; +} + + +void GliderManipulator::addMouseEvent(const GUIEventAdapter& ea) +{ + _ga_t1 = _ga_t0; + _ga_t0 = &ea; +} + + +bool GliderManipulator::calcMovement() +{ + // return if less then two events have been added. + if (_ga_t0.get()==NULL || _ga_t1.get()==NULL) return false; + + float dt = _ga_t0->time()-_ga_t1->time(); + + if (dt<0.0f) + { + notify(WARN) << "warning dt = "<getButtonMask(); + if (buttonMask==GUIEventAdapter::LEFT_BUTTON) + { + // pan model. + + _velocity += dt*_modelScale*0.05f; + + } + else if (buttonMask==GUIEventAdapter::MIDDLE_BUTTON || + buttonMask==(GUIEventAdapter::LEFT_BUTTON|GUIEventAdapter::RIGHT_BUTTON)) + { + + _velocity = 0.0f; + + } + else if (buttonMask==GUIEventAdapter::RIGHT_BUTTON) + { + + _velocity -= dt*_modelScale*0.05f; + + } + + float mx = (_ga_t0->getXmin()+_ga_t0->getXmax())/2.0f; + float my = (_ga_t0->getYmin()+_ga_t0->getYmax())/2.0f; + + float dx = _ga_t0->getX()-mx; + float dy = _ga_t0->getY()-my; + + osg::Vec3 center = _camera->getEyePoint(); + osg::Vec3 sv = _camera->getSideVector(); + osg::Vec3 lv = _camera->getLookVector(); + + float pitch = -dy*0.15f*dt; + float roll = -dx*0.1f*dt; + + osg::Matrix mat; + mat.makeTrans(-center.x(),-center.y(),-center.z()); + mat.postRot(pitch,sv.x(),sv.y(),sv.z()); + mat.postRot(roll,lv.x(),lv.y(),lv.z()); + if (_yawMode==YAW_AUTOMATICALLY_WHEN_BANKED) + { + float bank = asinf(sv.z()); + float yaw = (-bank*180.0f/M_PI)*dt; + mat.postRot(yaw,0.0f,0.0f,1.0f); + } + mat.postTrans(center.x(),center.y(),center.z()); + + lv *= (_velocity*dt); + + mat.postTrans(lv.x(),lv.y(),lv.z()); + + _camera->transformLookAt(mat); + + return true; +} diff --git a/src/Demos/hangglide/GliderManipulator.h b/src/Demos/hangglide/GliderManipulator.h new file mode 100644 index 000000000..c3fa4cc48 --- /dev/null +++ b/src/Demos/hangglide/GliderManipulator.h @@ -0,0 +1,65 @@ +#ifndef HANGGLIDE_GLIDERMANIPULATOR +#define HANGGLIDE_GLIDERMANIPULATOR 1 + +#include + +class GliderManipulator : public osgUtil::CameraManipulator +{ + public: + + GliderManipulator(); + virtual ~GliderManipulator(); + + /** Attach a node to the manipulator. + Automatically detaches previously attached node. + setNode(NULL) detaches previously nodes. + Is ignored by manipulators which do not require a reference model.*/ + virtual void setNode(osg::Node*); + + /** Return node if attached.*/ + virtual const osg::Node* getNode() const; + + /** Move the camera to the default position. + May be ignored by manipulators if home functionality is not appropriate.*/ + virtual void home(const osgUtil::GUIEventAdapter& ea,osgUtil::GUIActionAdapter& us); + + /** Start/restart the manipulator.*/ + virtual void init(const osgUtil::GUIEventAdapter& ea,osgUtil::GUIActionAdapter& us); + + /** handle events, return true if handled, false otherwise.*/ + virtual bool handle(const osgUtil::GUIEventAdapter& ea,osgUtil::GUIActionAdapter& us); + + enum YawControlMode { + YAW_AUTOMATICALLY_WHEN_BANKED, + NO_AUTOMATIC_YAW + }; + + /** Set the yaw control between no yaw and yawing when banked.*/ + void setYawControlMode(YawControlMode ycm) { _yawMode = ycm; } + + private: + + /** Reset the internal GUIEvent stack.*/ + void flushMouseEventStack(); + /** Add the current mouse GUIEvent to internal stack.*/ + void addMouseEvent(const osgUtil::GUIEventAdapter& ea); + + /** For the give mouse movement calculate the movement of the camera. + Return true is camera has moved and a redraw is required.*/ + bool calcMovement(); + + // Internal event stack comprising last three mouse events. + osg::ref_ptr _ga_t1; + osg::ref_ptr _ga_t0; + + osg::ref_ptr _node; + + float _modelScale; + float _velocity; + + YawControlMode _yawMode; + +}; + +#endif + diff --git a/src/Demos/hangglide/Makedepend b/src/Demos/hangglide/Makedepend new file mode 100644 index 000000000..e69de29bb diff --git a/src/Demos/hangglide/Makefile b/src/Demos/hangglide/Makefile new file mode 100644 index 000000000..2c11e1cdc --- /dev/null +++ b/src/Demos/hangglide/Makefile @@ -0,0 +1,28 @@ +#!smake +include ../../../Make/makedefs + +C++FILES = \ + hangglide.cpp\ + ReaderWriterFLY.cpp\ + GliderManipulator.cpp\ + hat.cpp\ + terrain.cpp\ + tank.cpp\ + sky.cpp\ + base.cpp\ + trees.cpp\ + +TARGET = ../../../bin/hangglide + +TARGET_BIN_FILES = hangglide + +#note, use this library list when using the Performer osgPlugin. +#LIBS = ${PFLIBS} -losgGLUT -losgUtil -losgDB -losg $(GLUTLIB) -lGLU -lGL -lm -lXmu -lX11 -lXi + +#note, standard library list. +LIBS = -losgGLUT -losgUtil -losgDB -losg $(GLUTLIB) -lGLU -lGL -lm -lXmu -lX11 -lXi + +C++FLAGS += -I. -I../../../include +LDFLAGS += -L../../../lib + +include ../../../Make/makerules diff --git a/src/Demos/hangglide/README b/src/Demos/hangglide/README new file mode 100644 index 000000000..ce005c1cd --- /dev/null +++ b/src/Demos/hangglide/README @@ -0,0 +1,13 @@ +A simple hang gliding flight simulator demo. The current GliderManipulator +does not yet have any dynamics built into it, something TODO... + +A small database is built into the program - Ed Levin park, Don's local flying +to be precise! You'll need the textures found in the OpenSceneGraph-Data +distribution. To run type : + + hangglide + +To run type with other databases, treat it just like sgv such as : + + hangglide town.osg + diff --git a/src/Demos/hangglide/ReaderWriterFLY.cpp b/src/Demos/hangglide/ReaderWriterFLY.cpp new file mode 100644 index 000000000..244baf26a --- /dev/null +++ b/src/Demos/hangglide/ReaderWriterFLY.cpp @@ -0,0 +1,101 @@ +#include +#include + +#include +#include +#include + +#include +#include + +using namespace osg; + +extern Node *makeTerrain( void ); +extern Node *makeTrees( void ); +extern Node *makeTank( void ); +extern Node *makeWindsocks( void ); +extern Node *makeGliders( void ); +extern Node *makeGlider( void ); +extern Node *makeSky( void ); +extern Node *makeBase( void ); +extern Node *makeClouds( void ); + +static struct _nodes +{ + char *name; + Node *(*fptr)(void); +} + + +nodes[] = +{ + { "terrain", makeTerrain }, + { "tank", makeTank }, + { "sky", makeSky }, + { "base", makeBase }, + { "trees", makeTrees }, + // { "gliders", makeGliders }, + // { "clouds", makeClouds }, + + { 0L, 0L } +}; + +class ReaderWriterFLY : public osgDB::ReaderWriter +{ + public: + virtual const char* className() { return "FLY Database Reader"; } + + virtual bool acceptsExtension(const std::string& extension) + { + return osgDB::equalCaseInsensitive(extension,"fly"); + } + + virtual Node* readNode(const std::string& fileName) + { + + std::string ext = osgDB::getFileExtension(fileName); + if (!acceptsExtension(ext)) return NULL; + + char buff[256]; + + notify(INFO)<< "ReaderWriterFLY::readNode( "<name; nptr ++ ) + { + if( !strncmp( buff, nptr->name, strlen( nptr->name ) )) + { + Node *node = nptr->fptr(); + node->setName( nptr->name ); + grp->addChild( node ); + break; + } + } + } + fclose( fp ); + + return grp; + + } + +}; + +// now register with osg::Registry to instantiate the above +// reader/writer. +osgDB::RegisterReaderWriterProxy g_readerWriter_FLY_Proxy; + diff --git a/src/Demos/hangglide/base.cpp b/src/Demos/hangglide/base.cpp new file mode 100644 index 000000000..38531024e --- /dev/null +++ b/src/Demos/hangglide/base.cpp @@ -0,0 +1,94 @@ +#include + +#include +#include +#include +#include +#include + +#include + +using namespace osg; + +Node *makeBase( void ) +{ + int i, c; + float theta; + float ir, ori; + ir = 6.0; + ori = 20.0; + + Vec3 *coords = new Vec3[38]; + Vec2 *tcoords = new Vec2[38]; + Vec4 *colors = new Vec4[1]; + int *lengths = new int[1]; + + colors[0][0] = colors[0][1] = colors[0][2] = colors[0][3] = 1; + + c = 0; + for( i = 0; i <= 18; i++ ) + { + theta = (float)i * 20.0 * M_PI/180.0; + + coords[c][0] = ir * cosf( theta ); + coords[c][1] = ir * sinf( theta ); + coords[c][2] = 0.0; + tcoords[c][0] = coords[c][0]/36.; + tcoords[c][1] = coords[c][1]/36.; + + c++; + + coords[c][0] = ori * cosf( theta ); + coords[c][1] = ori * sinf( theta ); + coords[c][2] = 0.0f; + + tcoords[c][0] = coords[c][0]/36.; + tcoords[c][1] = coords[c][1]/36.; + + c++; + } + *lengths = 38; + + GeoSet *gset = new GeoSet; + + gset->setCoords( coords ); + + gset->setTextureCoords( tcoords ); + gset->setTextureBinding( GeoSet::BIND_PERVERTEX ); + + gset->setColors( colors ); + gset->setColorBinding( GeoSet::BIND_OVERALL ); + + gset->setPrimType( GeoSet::TRIANGLE_STRIP ); + gset->setNumPrims( 1 ); + gset->setPrimLengths( lengths ); + + Texture *tex = new Texture; + + tex->setImage(osgDB::readImageFile("water.rgb")); + tex->setWrap( Texture::WRAP_S, Texture::REPEAT ); + tex->setWrap( Texture::WRAP_T, Texture::REPEAT ); + + StateSet *dstate = new StateSet; + dstate->setMode( GL_LIGHTING, StateAttribute::OFF ); + dstate->setAttributeAndModes( tex, StateAttribute::ON ); + + dstate->setAttribute( new TexEnv ); + /* + pfFog *fog = new pfFog; + + fog->setFogType( PFFOG_PIX_EXP2 ); + fog->setColor( 0.1, 0.2, 0.2 ); + fog->setRange( 16.0, 22.0 ); + + gstate->setMode( PFSTATE_ENFOG, PF_ON ); + gstate->setAttr( PFSTATE_FOG, fog ); + */ + + gset->setStateSet( dstate ); + + Geode *geode = new Geode; + geode->addDrawable( gset ); + + return geode; +} diff --git a/src/Demos/hangglide/hangglide.cpp b/src/Demos/hangglide/hangglide.cpp new file mode 100644 index 000000000..8327ab0c1 --- /dev/null +++ b/src/Demos/hangglide/hangglide.cpp @@ -0,0 +1,152 @@ +#include +#include + +#include +#include + +#include +#include + +#include "GliderManipulator.h" + +extern osg::Node *makeTerrain( void ); +extern osg::Node *makeTrees( void ); +extern osg::Node *makeTank( void ); +extern osg::Node *makeWindsocks( void ); +extern osg::Node *makeGliders( void ); +extern osg::Node *makeGlider( void ); +extern osg::Node *makeSky( void ); +extern osg::Node *makeBase( void ); +extern osg::Node *makeClouds( void ); + +/* + * Function to read several files (typically one) as specified on the command + * line, and return them in an osg::Node + */ +osg::Node* getNodeFromFiles(int argc,char **argv) +{ + + int i; + + typedef std::vector NodeList; + NodeList nodeList; + for( i = 1; i < argc; i++ ) + { + + if (argv[i][0]=='-') + { + switch(argv[i][1]) + { + case('l'): + ++i; + if (iloadLibrary(argv[i]); + } + break; + case('e'): + ++i; + if (icreateLibraryNameForExt(argv[i]); + osgDB::Registry::instance()->loadLibrary(libName); + } + break; + } + } else + { + osg::Node *node = osgDB::readNodeFile( argv[i] ); + + if( node != (osg::Node *)0L ) + { + if (node->getName().empty()) node->setName( argv[i] ); + nodeList.push_back(node); + } + } + + } + + if (nodeList.size()==0) + { + osg::notify(osg::INFO) << "No data loaded."<1 + { + osg::Group* group = new osg::Group(); + for(NodeList::iterator itr=nodeList.begin(); + itr!=nodeList.end(); + ++itr) + { + group->addChild(*itr); + } + + rootnode = group; + } + + return rootnode; +} + + +int main( int argc, char **argv ) +{ + + // if (argc<2) + // { + // osg::notify(osg::NOTICE)<<"usage:"<addChild(makeTerrain()); + group->addChild(makeTank()); + group->addChild(makeSky()); + group->addChild(makeBase()); + group->addChild(makeTrees()); + // add the following in the future... + // makeGliders + // makeClouds + + } + + glutInit( &argc, argv ); + + osgGLUT::Viewer viewer; + viewer.addViewport( rootnode ); + + unsigned int pos = viewer.registerCameraManipulator(new GliderManipulator()); + + // Open window so camera manipulator's warp pointer request will succeed + viewer.open(); + + viewer.selectCameraManipulator(pos); + + viewer.run(); + + return 0; +} diff --git a/src/Demos/hangglide/hat.cpp b/src/Demos/hangglide/hat.cpp new file mode 100644 index 000000000..0aa57c52f --- /dev/null +++ b/src/Demos/hangglide/hat.cpp @@ -0,0 +1,150 @@ +#ifdef WIN32 +#include +#pragma warning( disable : 4244 ) +#endif + +#include +#include +#include + +#include "terrain_data.h" +#include "hat.h" + +static int inited = 0; + +static float dbcenter[3]; +static float dbradius; + +static void getDatabaseCenterRadius( float dbcenter[3], float *dbradius ) +{ + int i; + double n=0.0; + double center[3] = { 0.0f, 0.0f, 0.0f }; + float cnt; + + cnt = 39 * 38; + for( i = 0; i < cnt; i++ ) + { + center[0] += (double)vertex[i][0]; + center[1] += (double)vertex[i][1]; + center[2] += (double)vertex[i][2]; + + n = n + 1.0; + } + + center[0] /= n; + center[1] /= n; + center[2] /= n; + + float r = 0.0; + + // for( i = 0; i < sizeof( vertex ) / (sizeof( float[3] )); i++ ) + for( i = 0; i < cnt; i++ ) + { + double d = sqrt( + (((double)vertex[i][0] - center[0]) * ((double)vertex[i][0] - center[0])) + + (((double)vertex[i][1] - center[1]) * ((double)vertex[i][1] - center[1])) + + (((double)vertex[i][2] - center[2]) * ((double)vertex[i][2] - center[2])) ); + + if( d > (double)r ) r = (float)d; + + } + + *dbradius = r; + dbcenter[0] = (float)center[0]; + dbcenter[1] = (float)center[1]; + dbcenter[2] = (float)center[2]; + + int index = 19 * 39 + 19; + dbcenter[0] = vertex[index][0] - 0.15; + dbcenter[1] = vertex[index][1]; + dbcenter[2] = vertex[index][2] + 0.35; +} + + +static void init( void ) +{ + getDatabaseCenterRadius( dbcenter, &dbradius ); + inited = 1; +} + + +static void getNormal( float *v1, float *v2, float *v3, float *n ) +{ + float V1[4], V2[4]; + float f; + int i; + + /* Two vectors v2->v1 and v2->v3 */ + + for( i = 0; i < 3; i++ ) + { + V1[i] = v1[i] - v2[i]; + V2[i] = v3[i] - v2[i]; + } + + /* Cross product between V1 and V2 */ + + n[0] = (V1[1] * V2[2]) - (V1[2] * V2[1]); + n[1] = -((V1[0] * V2[2]) - ( V1[2] * V2[0] )); + n[2] = (V1[0] * V2[1] ) - (V1[1] * V2[0] ); + + /* Normalize */ + + f = sqrtf( ( n[0] * n[0] ) + ( n[1] * n[1] ) + ( n[2] * n[2] ) ); + n[0] /= f; + n[1] /= f; + n[2] /= f; +} + + +float Hat( float x, float y, float z ) +{ + int m, n; + int i, j; + float tri[3][3]; + float norm[3]; + float d, pz; + + if( inited == 0 ) init(); + + // m = columns + // n = rows + m = (sizeof( vertex ) /(sizeof( float[3])))/39; + n = 39; + + i = 0; + while( i < ((m-1)*39) && x > (vertex[i+n][0] - dbcenter[0]) ) + i += n; + + j = 0; + + while( j < n-1 && y > (vertex[i+j+1][1] - dbcenter[1]) ) + j++; + + tri[0][0] = vertex[i+0+j+0][0] - dbcenter[0]; + tri[0][1] = vertex[i+0+j+0][1] - dbcenter[1]; + //tri[0][2] = vertex[i+0+j+0][2] - dbcenter[2]; + tri[0][2] = vertex[i+0+j+0][2]; + + tri[1][0] = vertex[i+n+j+0][0] - dbcenter[0]; + tri[1][1] = vertex[i+n+j+0][1] - dbcenter[1]; + //tri[1][2] = vertex[i+n+j+0][2] - dbcenter[2]; + tri[1][2] = vertex[i+n+j+0][2]; + + tri[2][0] = vertex[i+0+j+1][0] - dbcenter[0]; + tri[2][1] = vertex[i+0+j+1][1] - dbcenter[1]; + //tri[2][2] = vertex[i+0+j+1][2] - dbcenter[2]; + tri[2][2] = vertex[i+0+j+1][2]; + + getNormal( tri[0], tri[1], tri[2], norm ); + + d = (tri[0][0] * norm[0]) + + (tri[0][1] * norm[1]) + + (tri[0][2] * norm[2]); + + d *= -1; + pz = (-(norm[0] * x) - (norm[1] * y) - d)/norm[2]; + + return z - pz; +} diff --git a/src/Demos/hangglide/hat.h b/src/Demos/hangglide/hat.h new file mode 100644 index 000000000..1e4a20384 --- /dev/null +++ b/src/Demos/hangglide/hat.h @@ -0,0 +1,4 @@ +#ifndef __HAT_H +#define __HAT_H +extern float Hat( float x, float y, float z ); +#endif diff --git a/src/Demos/hangglide/sky.cpp b/src/Demos/hangglide/sky.cpp new file mode 100644 index 000000000..7e285093e --- /dev/null +++ b/src/Demos/hangglide/sky.cpp @@ -0,0 +1,108 @@ +#include + +#include +#include +#include +#include +#include + +#include + +#ifdef WIN32 +#pragma warning( disable : 4244 ) +#pragma warning( disable : 4305 ) +#endif + +using namespace osg; + +Node *makeSky( void ) +{ + int i, j; + float lev[] = { -5, -1.0, 1.0, 15.0, 30.0, 60.0, 90.0 }; + float cc[][4] = + { + { 0.0, 0.0, 0.15 }, + { 0.0, 0.0, 0.15 }, + { 0.4, 0.4, 0.7 }, + { 0.2, 0.2, 0.6 }, + { 0.1, 0.1, 0.6 }, + { 0.1, 0.1, 0.6 }, + { 0.1, 0.1, 0.6 }, + }; + float x, y, z; + float alpha, theta; + float radius = 20.0f; + int nlev = sizeof( lev )/sizeof(float); + + Vec3 *coords = new Vec3[19*nlev]; + Vec4 *colors = new Vec4[19*nlev]; + Vec2 *tcoords = new Vec2[19*nlev]; + osg::ushort *idx = new osg::ushort[38* nlev]; + int *lengths = new int[nlev]; + + int ci, ii; + ii = ci = 0; + + for( i = 0; i < nlev; i++ ) + { + for( j = 0; j <= 18; j++ ) + { + alpha = lev[i] * M_PI/180.0; + theta = (float)(j*20) * M_PI/180.0; + + x = radius * cosf( alpha ) * cosf( theta ); + y = radius * cosf( alpha ) * -sinf( theta ); + z = radius * sinf( alpha ); + + coords[ci][0] = x; + coords[ci][1] = y; + coords[ci][2] = z; + + colors[ci][0] = cc[i][0]; + colors[ci][1] = cc[i][1]; + colors[ci][2] = cc[i][2]; + colors[ci][3] = 1.0; + + tcoords[ci][0] = (float)j/18.0; + tcoords[ci][0] = (float)i/(float)(nlev-1); + + ci++; + + idx[ii++] = ((i+1)*19+j); + idx[ii++] = ((i+0)*19+j); + } + lengths[i] = 38; + } + + GeoSet *gset = new GeoSet; + + gset->setCoords( coords, idx ); + gset->setTextureCoords( tcoords, idx ); + gset->setTextureBinding( GeoSet::BIND_PERVERTEX ); + + gset->setColors( colors, idx ); + gset->setColorBinding( GeoSet::BIND_PERVERTEX ); + + gset->setPrimType( GeoSet::TRIANGLE_STRIP ); + gset->setNumPrims( nlev - 1 ); + gset->setPrimLengths( lengths ); + + Texture *tex = new Texture; + tex->setImage(osgDB::readImageFile("white.rgb")); + + StateSet *dstate = new StateSet; + + dstate->setAttributeAndModes( tex, StateAttribute::OFF ); + dstate->setAttribute( new TexEnv ); + dstate->setMode( GL_LIGHTING, StateAttribute::OFF ); + dstate->setMode( GL_CULL_FACE, StateAttribute::ON ); + + gset->setStateSet( dstate ); + + Geode *geode = new Geode; + geode->addDrawable( gset ); + + geode->setName( "Sky" ); + + return geode; +} diff --git a/src/Demos/hangglide/tank.cpp b/src/Demos/hangglide/tank.cpp new file mode 100644 index 000000000..fbb4b4e9d --- /dev/null +++ b/src/Demos/hangglide/tank.cpp @@ -0,0 +1,192 @@ +#include + +#include +#include +#include +#include +#include +#include +#include +#include + +#include + +#ifdef WIN32 +#pragma warning( disable : 4244 ) +#pragma warning( disable : 4305 ) +#endif + +using namespace osg; + +extern void getDatabaseCenterRadius( float dbcenter[3], float *dbradius ); + +static float radius = 2.0; +static float dbcenter[3], dbradius; + +static void conv( const Vec3& a, const Matrix& mat, Vec3& b ) +{ + int i; + Vec3 t; + + for( i = 0; i < 3; i++ ) + { + t[i] = (a[0] * mat._mat[0][i]) + + (a[1] * mat._mat[1][i]) + + (a[2] * mat._mat[2][i]) + + mat._mat[3][i]; + } + b[0] = t[0]; + b[1] = t[1]; + b[2] = t[2]; +} + + +Node *makeTank( void ) +{ + + Geode *geode1 = new Geode; + + getDatabaseCenterRadius( dbcenter, &dbradius ); + + ref_ptr mat = new Matrix( + 0.05, 0, 0, 0, + 0, 0.05, 0, 0, + 0, 0, 0.05, 0, + 1.5999 - 0.3, + 3.1474, + dbcenter[2] + 0.6542 - 0.09, + 1 + ); + + Vec3 *vc = new Vec3[42]; + Vec2 *tc = new Vec2[42]; + int *lens = new int[1]; + int i, c; + + c = 0; + for( i = 0; i <= 360; i += 18 ) + { + float x, y, z; + float s, t; + float theta = (float)i * M_PI/180.0; + + s = (float)i/90.0; + t = 1.0; + + x = radius * cosf( theta ); + y = radius * sinf( theta ); + z = 1.0; + + vc[c][0] = x; + vc[c][1] = y; + vc[c][2] = z; + + tc[c][0] = s; + tc[c][1] = t; + + c++; + + t = 0.0; + z = 0.0; + + vc[c][0] = x; + vc[c][1] = y; + vc[c][2] = z; + + tc[c][0] = s; + tc[c][1] = t; + c++; + } + *lens = 42; + + for( i = 0; i < c; i++ ) + conv( vc[i], *mat, vc[i] ); + + GeoSet *gset = new GeoSet; + gset->setCoords( vc ); + + gset->setTextureCoords( tc ); + gset->setTextureBinding( GeoSet::BIND_PERVERTEX ); + + gset->setPrimType( GeoSet::TRIANGLE_STRIP ); + gset->setNumPrims( 1 ); + gset->setPrimLengths( lens ); + + Texture *tex = new Texture; + + tex->setWrap( Texture::WRAP_S, Texture::REPEAT ); + tex->setWrap( Texture::WRAP_T, Texture::REPEAT ); + tex->setImage(osgDB::readImageFile("tank.rgb")); + + StateSet *dstate = new StateSet; + dstate->setAttributeAndModes( tex, StateAttribute::ON ); + dstate->setAttribute( new TexEnv ); + + gset->setStateSet( dstate ); + geode1->addDrawable( gset ); + + lens = new int[1]; + *lens = 22; + + vc = new Vec3[22]; + tc = new Vec2[22]; + + c = 0; + vc[c][0] = 0.0f; + vc[c][1] = 0.0f; + vc[c][2] = 1.0f; + + tc[c][0] = 0.0f; + tc[c][1] = 0.0f; + c++; + + for( i = 0; i <= 360; i += 18 ) + { + float x, y, z; + float s, t; + float theta = (float)i * M_PI/180.0; + + // s = (float)i/360.0; + // t = 1.0; + s = cosf( theta ); + t = sinf( theta ); + + x = radius * cosf( theta ); + y = radius * sinf( theta ); + z = 1.0; + + vc[c][0] = x; + vc[c][1] = y; + vc[c][2] = z; + + tc[c][0] = s; + tc[c][1] = t; + + c++; + } + + for( i = 0; i < c; i++ ) + conv( vc[i], *mat, vc[i] ); + + gset = new GeoSet; + gset->setCoords( vc ); + gset->setTextureCoords( tc ); + gset->setPrimType(GeoSet::TRIANGLE_FAN); + gset->setNumPrims( 1 ); + gset->setPrimLengths( lens ); + + gset->setStateSet( dstate ); + + Geode *geode2 = new Geode; + geode2->addDrawable( gset ); + + + Group *grp = new Group; + grp->addChild( geode1 ); + grp->addChild( geode2 ); + + geode1->setName( "Geode 1" ); + geode2->setName( "Geode 2" ); + + return grp; +} diff --git a/src/Demos/hangglide/terrain.cpp b/src/Demos/hangglide/terrain.cpp new file mode 100644 index 000000000..bb761fbd4 --- /dev/null +++ b/src/Demos/hangglide/terrain.cpp @@ -0,0 +1,136 @@ +// #include + +#include +#include +#include +#include +#include + +#include + +#include "terrain_data.h" + +using namespace osg; + +void getDatabaseCenterRadius( float dbcenter[3], float *dbradius ) +{ + int i; + double n=0.0; + double center[3] = { 0.0f, 0.0f, 0.0f }; + float cnt; + + cnt = 39 * 38; + for( i = 0; i < cnt; i++ ) + { + center[0] += (double)vertex[i][0]; + center[1] += (double)vertex[i][1]; + center[2] += (double)vertex[i][2]; + + n = n + 1.0; + } + + center[0] /= n; + center[1] /= n; + center[2] /= n; + + float r = 0.0; + + // for( i = 0; i < sizeof( vertex ) / (sizeof( float[3] )); i++ ) + for( i = 0; i < cnt; i++ ) + { + double d = sqrt( + (((double)vertex[i][0] - center[0]) * ((double)vertex[i][0] - center[0])) + + (((double)vertex[i][1] - center[1]) * ((double)vertex[i][1] - center[1])) + + (((double)vertex[i][2] - center[2]) * ((double)vertex[i][2] - center[2])) ); + + if( d > (double)r ) r = (float)d; + + } + + *dbradius = r; + dbcenter[0] = (float)center[0]; + dbcenter[1] = (float)center[1]; + dbcenter[2] = (float)center[2]; + + int index = 19 * 39 + 19; + dbcenter[0] = vertex[index][0] - 0.15; + dbcenter[1] = vertex[index][1]; + dbcenter[2] = vertex[index][2] + 0.35; + +} + + +Node *makeTerrain( void ) +{ + int m, n; + int i, j, c; + float dbcenter[3]; + float dbradius; + + getDatabaseCenterRadius( dbcenter, &dbradius ); + + m = (sizeof( vertex ) /(sizeof( float[3])))/39; + n = 39; + + Vec3 *v = new Vec3[m*n]; + Vec2 *t = new Vec2[m*n]; + Vec4 *col = new Vec4[1]; + osg::ushort *cidx = new osg::ushort; + osg::ushort *idx = new osg::ushort[m*n*2]; + int *lens = new int[m]; + + col[0][0] = col[0][1] = col[0][2] = col[0][3] = 1; + *cidx = 0; + + for( i = 0; i < m * n; i++ ) + { + v[i][0] = vertex[i][0] - dbcenter[0]; + v[i][1] = vertex[i][1] - dbcenter[1]; + v[i][2] = vertex[i][2]; + + t[i][0] = texcoord[i][0] + 0.025; + t[i][1] = texcoord[i][1]; + } + + c = 0; + for( i = 0; i < m-2; i++ ) + { + for( j = 0; j < n; j++ ) + { + idx[c++] = (i+0)*n+j; + idx[c++] = (i+1)*n+j; + } + lens[i] = 39*2; + } + + GeoSet *gset = new GeoSet; + + gset->setCoords( v, idx ); + gset->setTextureCoords( t, idx ); + gset->setTextureBinding( GeoSet::BIND_PERVERTEX ); + + gset->setColors( col, cidx ); + gset->setColorBinding( GeoSet::BIND_OVERALL ); + + gset->setPrimType( GeoSet::TRIANGLE_STRIP ); + gset->setNumPrims( m-2 ); + gset->setPrimLengths( lens ); + + Texture *tex = new Texture; + + tex->setImage(osgDB::readImageFile("lz.rgb")); + + StateSet *dstate = new StateSet; + dstate->setMode( GL_LIGHTING, StateAttribute::OFF ); + dstate->setAttributeAndModes( tex, StateAttribute::ON ); + dstate->setAttribute( new TexEnv ); + + gset->setStateSet( dstate ); + + Geode *geode = new Geode; + geode->addDrawable( gset ); + + gset->check(); + + return geode; +} diff --git a/src/Demos/hangglide/terrain_data.h b/src/Demos/hangglide/terrain_data.h new file mode 100644 index 000000000..7869738d6 --- /dev/null +++ b/src/Demos/hangglide/terrain_data.h @@ -0,0 +1,5944 @@ +#ifdef WIN32 +#pragma warning( disable : 4305 ) +#endif + +static float vertex[][3] = { + + { 5998.7998, 41456.1016, 1.7800 }, + { 5998.7998, 41456.3984, 1.8200 }, + { 5998.7998, 41456.6992, 1.8600 }, + { 5998.7998, 41457.0000, 1.8800 }, + { 5998.7998, 41457.3008, 1.9000 }, + { 5998.7998, 41457.6016, 1.9000 }, + { 5998.7998, 41457.8984, 1.8900 }, + { 5998.7998, 41458.1992, 1.8800 }, + { 5998.7998, 41458.5000, 1.8600 }, + { 5998.7998, 41458.8008, 1.8500 }, + { 5998.7998, 41459.1016, 1.8300 }, + { 5998.7998, 41459.3984, 1.8100 }, + { 5998.7998, 41459.6992, 1.7800 }, + { 5998.7998, 41460.0000, 1.7500 }, + { 5998.7998, 41460.3008, 1.7300 }, + { 5998.7998, 41460.6016, 1.7100 }, + { 5998.7998, 41460.8984, 1.7000 }, + { 5998.7998, 41461.1992, 1.6900 }, + { 5998.7998, 41461.5000, 1.7000 }, + { 5998.7998, 41461.8008, 1.7400 }, + { 5998.7998, 41462.1016, 1.7900 }, + { 5998.7998, 41462.3984, 1.8600 }, + { 5998.7998, 41462.6992, 1.9400 }, + { 5998.7998, 41463.0000, 1.9900 }, + { 5998.7998, 41463.3008, 2.0200 }, + { 5998.7998, 41463.6016, 2.0300 }, + { 5998.7998, 41463.8984, 2.0300 }, + { 5998.7998, 41464.1992, 2.0200 }, + { 5998.7998, 41464.5000, 2.0100 }, + { 5998.7998, 41464.8008, 1.9900 }, + { 5998.7998, 41465.1016, 1.9700 }, + { 5998.7998, 41465.3984, 1.9600 }, + { 5998.7998, 41465.6992, 1.9500 }, + { 5998.7998, 41466.0000, 1.9500 }, + { 5998.7998, 41466.3008, 1.9500 }, + { 5998.7998, 41466.6016, 1.9500 }, + { 5998.7998, 41466.8984, 1.9400 }, + { 5998.7998, 41467.1992, 1.9300 }, + { 5998.7998, 41467.5000, 1.9200 }, + + { 5999.1001, 41456.1016, 1.8600 }, + { 5999.1001, 41456.3984, 1.9100 }, + { 5999.1001, 41456.6992, 1.9600 }, + { 5999.1001, 41457.0000, 1.9900 }, + { 5999.1001, 41457.3008, 2.0100 }, + { 5999.1001, 41457.6016, 2.0000 }, + { 5999.1001, 41457.8984, 1.9700 }, + { 5999.1001, 41458.1992, 1.9400 }, + { 5999.1001, 41458.5000, 1.9100 }, + { 5999.1001, 41458.8008, 1.8700 }, + { 5999.1001, 41459.1016, 1.8400 }, + { 5999.1001, 41459.3984, 1.8000 }, + { 5999.1001, 41459.6992, 1.7700 }, + { 5999.1001, 41460.0000, 1.7400 }, + { 5999.1001, 41460.3008, 1.7300 }, + { 5999.1001, 41460.6016, 1.7200 }, + { 5999.1001, 41460.8984, 1.7200 }, + { 5999.1001, 41461.1992, 1.7300 }, + { 5999.1001, 41461.5000, 1.7600 }, + { 5999.1001, 41461.8008, 1.7900 }, + { 5999.1001, 41462.1016, 1.8300 }, + { 5999.1001, 41462.3984, 1.8700 }, + { 5999.1001, 41462.6992, 1.9100 }, + { 5999.1001, 41463.0000, 1.9400 }, + { 5999.1001, 41463.3008, 1.9700 }, + { 5999.1001, 41463.6016, 1.9900 }, + { 5999.1001, 41463.8984, 2.0100 }, + { 5999.1001, 41464.1992, 2.0200 }, + { 5999.1001, 41464.5000, 2.0100 }, + { 5999.1001, 41464.8008, 1.9900 }, + { 5999.1001, 41465.1016, 1.9700 }, + { 5999.1001, 41465.3984, 1.9600 }, + { 5999.1001, 41465.6992, 1.9600 }, + { 5999.1001, 41466.0000, 1.9600 }, + { 5999.1001, 41466.3008, 1.9600 }, + { 5999.1001, 41466.6016, 1.9600 }, + { 5999.1001, 41466.8984, 1.9600 }, + { 5999.1001, 41467.1992, 1.9600 }, + { 5999.1001, 41467.5000, 1.9600 }, + + { 5999.3999, 41456.1016, 1.9200 }, + { 5999.3999, 41456.3984, 1.9800 }, + { 5999.3999, 41456.6992, 2.0300 }, + { 5999.3999, 41457.0000, 2.0600 }, + { 5999.3999, 41457.3008, 2.0700 }, + { 5999.3999, 41457.6016, 2.0500 }, + { 5999.3999, 41457.8984, 2.0100 }, + { 5999.3999, 41458.1992, 1.9700 }, + { 5999.3999, 41458.5000, 1.9200 }, + { 5999.3999, 41458.8008, 1.8700 }, + { 5999.3999, 41459.1016, 1.8300 }, + { 5999.3999, 41459.3984, 1.7900 }, + { 5999.3999, 41459.6992, 1.7500 }, + { 5999.3999, 41460.0000, 1.7300 }, + { 5999.3999, 41460.3008, 1.7200 }, + { 5999.3999, 41460.6016, 1.7200 }, + { 5999.3999, 41460.8984, 1.7400 }, + { 5999.3999, 41461.1992, 1.7700 }, + { 5999.3999, 41461.5000, 1.8100 }, + { 5999.3999, 41461.8008, 1.8400 }, + { 5999.3999, 41462.1016, 1.8700 }, + { 5999.3999, 41462.3984, 1.8900 }, + { 5999.3999, 41462.6992, 1.9100 }, + { 5999.3999, 41463.0000, 1.9200 }, + { 5999.3999, 41463.3008, 1.9400 }, + { 5999.3999, 41463.6016, 1.9700 }, + { 5999.3999, 41463.8984, 2.0000 }, + { 5999.3999, 41464.1992, 2.0100 }, + { 5999.3999, 41464.5000, 2.0100 }, + { 5999.3999, 41464.8008, 2.0000 }, + { 5999.3999, 41465.1016, 1.9800 }, + { 5999.3999, 41465.3984, 1.9700 }, + { 5999.3999, 41465.6992, 1.9700 }, + { 5999.3999, 41466.0000, 1.9700 }, + { 5999.3999, 41466.3008, 1.9800 }, + { 5999.3999, 41466.6016, 1.9800 }, + { 5999.3999, 41466.8984, 1.9900 }, + { 5999.3999, 41467.1992, 1.9900 }, + { 5999.3999, 41467.5000, 2.0100 }, + + { 5999.7002, 41456.1016, 1.9800 }, + { 5999.7002, 41456.3984, 2.0300 }, + { 5999.7002, 41456.6992, 2.0700 }, + { 5999.7002, 41457.0000, 2.0900 }, + { 5999.7002, 41457.3008, 2.0800 }, + { 5999.7002, 41457.6016, 2.0500 }, + { 5999.7002, 41457.8984, 2.0000 }, + { 5999.7002, 41458.1992, 1.9500 }, + { 5999.7002, 41458.5000, 1.9000 }, + { 5999.7002, 41458.8008, 1.8400 }, + { 5999.7002, 41459.1016, 1.8000 }, + { 5999.7002, 41459.3984, 1.7600 }, + { 5999.7002, 41459.6992, 1.7200 }, + { 5999.7002, 41460.0000, 1.7100 }, + { 5999.7002, 41460.3008, 1.7100 }, + { 5999.7002, 41460.6016, 1.7200 }, + { 5999.7002, 41460.8984, 1.7500 }, + { 5999.7002, 41461.1992, 1.8000 }, + { 5999.7002, 41461.5000, 1.8600 }, + { 5999.7002, 41461.8008, 1.9000 }, + { 5999.7002, 41462.1016, 1.9300 }, + { 5999.7002, 41462.3984, 1.9400 }, + { 5999.7002, 41462.6992, 1.9400 }, + { 5999.7002, 41463.0000, 1.9500 }, + { 5999.7002, 41463.3008, 1.9600 }, + { 5999.7002, 41463.6016, 1.9800 }, + { 5999.7002, 41463.8984, 2.0000 }, + { 5999.7002, 41464.1992, 2.0100 }, + { 5999.7002, 41464.5000, 2.0100 }, + { 5999.7002, 41464.8008, 2.0000 }, + { 5999.7002, 41465.1016, 1.9900 }, + { 5999.7002, 41465.3984, 1.9800 }, + { 5999.7002, 41465.6992, 1.9800 }, + { 5999.7002, 41466.0000, 1.9900 }, + { 5999.7002, 41466.3008, 2.0000 }, + { 5999.7002, 41466.6016, 2.0100 }, + { 5999.7002, 41466.8984, 2.0200 }, + { 5999.7002, 41467.1992, 2.0400 }, + { 5999.7002, 41467.5000, 2.0600 }, + + { 6000.0000, 41456.1016, 2.0200 }, + { 6000.0000, 41456.3984, 2.0400 }, + { 6000.0000, 41456.6992, 2.0600 }, + { 6000.0000, 41457.0000, 2.0600 }, + { 6000.0000, 41457.3008, 2.0400 }, + { 6000.0000, 41457.6016, 2.0000 }, + { 6000.0000, 41457.8984, 1.9500 }, + { 6000.0000, 41458.1992, 1.9000 }, + { 6000.0000, 41458.5000, 1.8400 }, + { 6000.0000, 41458.8008, 1.7900 }, + { 6000.0000, 41459.1016, 1.7500 }, + { 6000.0000, 41459.3984, 1.7100 }, + { 6000.0000, 41459.6992, 1.6900 }, + { 6000.0000, 41460.0000, 1.6800 }, + { 6000.0000, 41460.3008, 1.6900 }, + { 6000.0000, 41460.6016, 1.7200 }, + { 6000.0000, 41460.8984, 1.7600 }, + { 6000.0000, 41461.1992, 1.8200 }, + { 6000.0000, 41461.5000, 1.8800 }, + { 6000.0000, 41461.8008, 1.9300 }, + { 6000.0000, 41462.1016, 1.9600 }, + { 6000.0000, 41462.3984, 1.9600 }, + { 6000.0000, 41462.6992, 1.9600 }, + { 6000.0000, 41463.0000, 1.9600 }, + { 6000.0000, 41463.3008, 1.9700 }, + { 6000.0000, 41463.6016, 1.9900 }, + { 6000.0000, 41463.8984, 2.0100 }, + { 6000.0000, 41464.1992, 2.0200 }, + { 6000.0000, 41464.5000, 2.0200 }, + { 6000.0000, 41464.8008, 2.0100 }, + { 6000.0000, 41465.1016, 1.9900 }, + { 6000.0000, 41465.3984, 1.9900 }, + { 6000.0000, 41465.6992, 1.9900 }, + { 6000.0000, 41466.0000, 2.0000 }, + { 6000.0000, 41466.3008, 2.0200 }, + { 6000.0000, 41466.6016, 2.0400 }, + { 6000.0000, 41466.8984, 2.0600 }, + { 6000.0000, 41467.1992, 2.0800 }, + { 6000.0000, 41467.5000, 2.1000 }, + + { 6000.2998, 41456.1016, 2.0600 }, + { 6000.2998, 41456.3984, 2.0700 }, + { 6000.2998, 41456.6992, 2.0700 }, + { 6000.2998, 41457.0000, 2.0500 }, + { 6000.2998, 41457.3008, 2.0200 }, + { 6000.2998, 41457.6016, 1.9700 }, + { 6000.2998, 41457.8984, 1.9000 }, + { 6000.2998, 41458.1992, 1.8400 }, + { 6000.2998, 41458.5000, 1.7800 }, + { 6000.2998, 41458.8008, 1.7400 }, + { 6000.2998, 41459.1016, 1.7000 }, + { 6000.2998, 41459.3984, 1.6800 }, + { 6000.2998, 41459.6992, 1.6700 }, + { 6000.2998, 41460.0000, 1.6700 }, + { 6000.2998, 41460.3008, 1.6800 }, + { 6000.2998, 41460.6016, 1.7100 }, + { 6000.2998, 41460.8984, 1.7400 }, + { 6000.2998, 41461.1992, 1.7800 }, + { 6000.2998, 41461.5000, 1.8300 }, + { 6000.2998, 41461.8008, 1.8700 }, + { 6000.2998, 41462.1016, 1.8900 }, + { 6000.2998, 41462.3984, 1.9000 }, + { 6000.2998, 41462.6992, 1.9000 }, + { 6000.2998, 41463.0000, 1.9100 }, + { 6000.2998, 41463.3008, 1.9300 }, + { 6000.2998, 41463.6016, 1.9500 }, + { 6000.2998, 41463.8984, 1.9800 }, + { 6000.2998, 41464.1992, 2.0000 }, + { 6000.2998, 41464.5000, 2.0100 }, + { 6000.2998, 41464.8008, 2.0100 }, + { 6000.2998, 41465.1016, 2.0000 }, + { 6000.2998, 41465.3984, 2.0000 }, + { 6000.2998, 41465.6992, 2.0000 }, + { 6000.2998, 41466.0000, 2.0200 }, + { 6000.2998, 41466.3008, 2.0400 }, + { 6000.2998, 41466.6016, 2.0600 }, + { 6000.2998, 41466.8984, 2.0800 }, + { 6000.2998, 41467.1992, 2.1100 }, + { 6000.2998, 41467.5000, 2.1300 }, + + { 6000.6001, 41456.1016, 2.1000 }, + { 6000.6001, 41456.3984, 2.1100 }, + { 6000.6001, 41456.6992, 2.1000 }, + { 6000.6001, 41457.0000, 2.0700 }, + { 6000.6001, 41457.3008, 2.0200 }, + { 6000.6001, 41457.6016, 1.9500 }, + { 6000.6001, 41457.8984, 1.8700 }, + { 6000.6001, 41458.1992, 1.8000 }, + { 6000.6001, 41458.5000, 1.7400 }, + { 6000.6001, 41458.8008, 1.7000 }, + { 6000.6001, 41459.1016, 1.6800 }, + { 6000.6001, 41459.3984, 1.6600 }, + { 6000.6001, 41459.6992, 1.6600 }, + { 6000.6001, 41460.0000, 1.6700 }, + { 6000.6001, 41460.3008, 1.6800 }, + { 6000.6001, 41460.6016, 1.7000 }, + { 6000.6001, 41460.8984, 1.7200 }, + { 6000.6001, 41461.1992, 1.7400 }, + { 6000.6001, 41461.5000, 1.7700 }, + { 6000.6001, 41461.8008, 1.7900 }, + { 6000.6001, 41462.1016, 1.8100 }, + { 6000.6001, 41462.3984, 1.8200 }, + { 6000.6001, 41462.6992, 1.8200 }, + { 6000.6001, 41463.0000, 1.8400 }, + { 6000.6001, 41463.3008, 1.8600 }, + { 6000.6001, 41463.6016, 1.9000 }, + { 6000.6001, 41463.8984, 1.9400 }, + { 6000.6001, 41464.1992, 1.9600 }, + { 6000.6001, 41464.5000, 1.9800 }, + { 6000.6001, 41464.8008, 1.9900 }, + { 6000.6001, 41465.1016, 2.0000 }, + { 6000.6001, 41465.3984, 2.0100 }, + { 6000.6001, 41465.6992, 2.0200 }, + { 6000.6001, 41466.0000, 2.0400 }, + { 6000.6001, 41466.3008, 2.0600 }, + { 6000.6001, 41466.6016, 2.0900 }, + { 6000.6001, 41466.8984, 2.1100 }, + { 6000.6001, 41467.1992, 2.1300 }, + { 6000.6001, 41467.5000, 2.1600 }, + + { 6000.8999, 41456.1016, 2.1000 }, + { 6000.8999, 41456.3984, 2.1000 }, + { 6000.8999, 41456.6992, 2.0800 }, + { 6000.8999, 41457.0000, 2.0500 }, + { 6000.8999, 41457.3008, 2.0000 }, + { 6000.8999, 41457.6016, 1.9200 }, + { 6000.8999, 41457.8984, 1.8400 }, + { 6000.8999, 41458.1992, 1.7800 }, + { 6000.8999, 41458.5000, 1.7200 }, + { 6000.8999, 41458.8008, 1.6900 }, + { 6000.8999, 41459.1016, 1.6700 }, + { 6000.8999, 41459.3984, 1.6600 }, + { 6000.8999, 41459.6992, 1.6600 }, + { 6000.8999, 41460.0000, 1.6700 }, + { 6000.8999, 41460.3008, 1.6800 }, + { 6000.8999, 41460.6016, 1.6900 }, + { 6000.8999, 41460.8984, 1.7100 }, + { 6000.8999, 41461.1992, 1.7200 }, + { 6000.8999, 41461.5000, 1.7300 }, + { 6000.8999, 41461.8008, 1.7400 }, + { 6000.8999, 41462.1016, 1.7500 }, + { 6000.8999, 41462.3984, 1.7600 }, + { 6000.8999, 41462.6992, 1.7700 }, + { 6000.8999, 41463.0000, 1.7900 }, + { 6000.8999, 41463.3008, 1.8200 }, + { 6000.8999, 41463.6016, 1.8600 }, + { 6000.8999, 41463.8984, 1.9000 }, + { 6000.8999, 41464.1992, 1.9400 }, + { 6000.8999, 41464.5000, 1.9700 }, + { 6000.8999, 41464.8008, 1.9900 }, + { 6000.8999, 41465.1016, 2.0100 }, + { 6000.8999, 41465.3984, 2.0300 }, + { 6000.8999, 41465.6992, 2.0500 }, + { 6000.8999, 41466.0000, 2.0700 }, + { 6000.8999, 41466.3008, 2.0900 }, + { 6000.8999, 41466.6016, 2.1200 }, + { 6000.8999, 41466.8984, 2.1400 }, + { 6000.8999, 41467.1992, 2.1600 }, + { 6000.8999, 41467.5000, 2.1800 }, + + { 6001.2002, 41456.1016, 2.0600 }, + { 6001.2002, 41456.3984, 2.0400 }, + { 6001.2002, 41456.6992, 2.0200 }, + { 6001.2002, 41457.0000, 1.9800 }, + { 6001.2002, 41457.3008, 1.9400 }, + { 6001.2002, 41457.6016, 1.8800 }, + { 6001.2002, 41457.8984, 1.8100 }, + { 6001.2002, 41458.1992, 1.7600 }, + { 6001.2002, 41458.5000, 1.7200 }, + { 6001.2002, 41458.8008, 1.7000 }, + { 6001.2002, 41459.1016, 1.6800 }, + { 6001.2002, 41459.3984, 1.6700 }, + { 6001.2002, 41459.6992, 1.6700 }, + { 6001.2002, 41460.0000, 1.6800 }, + { 6001.2002, 41460.3008, 1.6900 }, + { 6001.2002, 41460.6016, 1.7000 }, + { 6001.2002, 41460.8984, 1.7100 }, + { 6001.2002, 41461.1992, 1.7100 }, + { 6001.2002, 41461.5000, 1.7200 }, + { 6001.2002, 41461.8008, 1.7200 }, + { 6001.2002, 41462.1016, 1.7300 }, + { 6001.2002, 41462.3984, 1.7400 }, + { 6001.2002, 41462.6992, 1.7500 }, + { 6001.2002, 41463.0000, 1.7700 }, + { 6001.2002, 41463.3008, 1.8100 }, + { 6001.2002, 41463.6016, 1.8700 }, + { 6001.2002, 41463.8984, 1.9300 }, + { 6001.2002, 41464.1992, 1.9800 }, + { 6001.2002, 41464.5000, 2.0200 }, + { 6001.2002, 41464.8008, 2.0400 }, + { 6001.2002, 41465.1016, 2.0500 }, + { 6001.2002, 41465.3984, 2.0600 }, + { 6001.2002, 41465.6992, 2.0800 }, + { 6001.2002, 41466.0000, 2.1000 }, + { 6001.2002, 41466.3008, 2.1200 }, + { 6001.2002, 41466.6016, 2.1500 }, + { 6001.2002, 41466.8984, 2.1700 }, + { 6001.2002, 41467.1992, 2.1900 }, + { 6001.2002, 41467.5000, 2.2200 }, + + { 6001.5000, 41456.1016, 2.0000 }, + { 6001.5000, 41456.3984, 1.9700 }, + { 6001.5000, 41456.6992, 1.9400 }, + { 6001.5000, 41457.0000, 1.9000 }, + { 6001.5000, 41457.3008, 1.8600 }, + { 6001.5000, 41457.6016, 1.8200 }, + { 6001.5000, 41457.8984, 1.7800 }, + { 6001.5000, 41458.1992, 1.7500 }, + { 6001.5000, 41458.5000, 1.7200 }, + { 6001.5000, 41458.8008, 1.7100 }, + { 6001.5000, 41459.1016, 1.7000 }, + { 6001.5000, 41459.3984, 1.6900 }, + { 6001.5000, 41459.6992, 1.6900 }, + { 6001.5000, 41460.0000, 1.7000 }, + { 6001.5000, 41460.3008, 1.7100 }, + { 6001.5000, 41460.6016, 1.7100 }, + { 6001.5000, 41460.8984, 1.7200 }, + { 6001.5000, 41461.1992, 1.7200 }, + { 6001.5000, 41461.5000, 1.7200 }, + { 6001.5000, 41461.8008, 1.7200 }, + { 6001.5000, 41462.1016, 1.7200 }, + { 6001.5000, 41462.3984, 1.7300 }, + { 6001.5000, 41462.6992, 1.7500 }, + { 6001.5000, 41463.0000, 1.7800 }, + { 6001.5000, 41463.3008, 1.8200 }, + { 6001.5000, 41463.6016, 1.8900 }, + { 6001.5000, 41463.8984, 1.9700 }, + { 6001.5000, 41464.1992, 2.0300 }, + { 6001.5000, 41464.5000, 2.0800 }, + { 6001.5000, 41464.8008, 2.0900 }, + { 6001.5000, 41465.1016, 2.0900 }, + { 6001.5000, 41465.3984, 2.0900 }, + { 6001.5000, 41465.6992, 2.1000 }, + { 6001.5000, 41466.0000, 2.1200 }, + { 6001.5000, 41466.3008, 2.1500 }, + { 6001.5000, 41466.6016, 2.1700 }, + { 6001.5000, 41466.8984, 2.2000 }, + { 6001.5000, 41467.1992, 2.2200 }, + { 6001.5000, 41467.5000, 2.2600 }, + + { 6001.7998, 41456.1016, 1.9400 }, + { 6001.7998, 41456.3984, 1.9100 }, + { 6001.7998, 41456.6992, 1.8700 }, + { 6001.7998, 41457.0000, 1.8400 }, + { 6001.7998, 41457.3008, 1.8100 }, + { 6001.7998, 41457.6016, 1.7900 }, + { 6001.7998, 41457.8984, 1.7700 }, + { 6001.7998, 41458.1992, 1.7500 }, + { 6001.7998, 41458.5000, 1.7300 }, + { 6001.7998, 41458.8008, 1.7200 }, + { 6001.7998, 41459.1016, 1.7100 }, + { 6001.7998, 41459.3984, 1.7100 }, + { 6001.7998, 41459.6992, 1.7100 }, + { 6001.7998, 41460.0000, 1.7100 }, + { 6001.7998, 41460.3008, 1.7200 }, + { 6001.7998, 41460.6016, 1.7200 }, + { 6001.7998, 41460.8984, 1.7300 }, + { 6001.7998, 41461.1992, 1.7300 }, + { 6001.7998, 41461.5000, 1.7200 }, + { 6001.7998, 41461.8008, 1.7200 }, + { 6001.7998, 41462.1016, 1.7200 }, + { 6001.7998, 41462.3984, 1.7300 }, + { 6001.7998, 41462.6992, 1.7600 }, + { 6001.7998, 41463.0000, 1.7900 }, + { 6001.7998, 41463.3008, 1.8400 }, + { 6001.7998, 41463.6016, 1.9200 }, + { 6001.7998, 41463.8984, 2.0100 }, + { 6001.7998, 41464.1992, 2.0800 }, + { 6001.7998, 41464.5000, 2.1200 }, + { 6001.7998, 41464.8008, 2.1300 }, + { 6001.7998, 41465.1016, 2.1200 }, + { 6001.7998, 41465.3984, 2.1100 }, + { 6001.7998, 41465.6992, 2.1200 }, + { 6001.7998, 41466.0000, 2.1300 }, + { 6001.7998, 41466.3008, 2.1600 }, + { 6001.7998, 41466.6016, 2.1800 }, + { 6001.7998, 41466.8984, 2.2100 }, + { 6001.7998, 41467.1992, 2.2400 }, + { 6001.7998, 41467.5000, 2.2800 }, + + { 6002.1001, 41456.1016, 1.8900 }, + { 6002.1001, 41456.3984, 1.8500 }, + { 6002.1001, 41456.6992, 1.8200 }, + { 6002.1001, 41457.0000, 1.8000 }, + { 6002.1001, 41457.3008, 1.7800 }, + { 6002.1001, 41457.6016, 1.7600 }, + { 6002.1001, 41457.8984, 1.7500 }, + { 6002.1001, 41458.1992, 1.7400 }, + { 6002.1001, 41458.5000, 1.7400 }, + { 6002.1001, 41458.8008, 1.7300 }, + { 6002.1001, 41459.1016, 1.7300 }, + { 6002.1001, 41459.3984, 1.7200 }, + { 6002.1001, 41459.6992, 1.7200 }, + { 6002.1001, 41460.0000, 1.7200 }, + { 6002.1001, 41460.3008, 1.7300 }, + { 6002.1001, 41460.6016, 1.7300 }, + { 6002.1001, 41460.8984, 1.7400 }, + { 6002.1001, 41461.1992, 1.7300 }, + { 6002.1001, 41461.5000, 1.7200 }, + { 6002.1001, 41461.8008, 1.7200 }, + { 6002.1001, 41462.1016, 1.7300 }, + { 6002.1001, 41462.3984, 1.7500 }, + { 6002.1001, 41462.6992, 1.7800 }, + { 6002.1001, 41463.0000, 1.8200 }, + { 6002.1001, 41463.3008, 1.8800 }, + { 6002.1001, 41463.6016, 1.9600 }, + { 6002.1001, 41463.8984, 2.0600 }, + { 6002.1001, 41464.1992, 2.1300 }, + { 6002.1001, 41464.5000, 2.1700 }, + { 6002.1001, 41464.8008, 2.1700 }, + { 6002.1001, 41465.1016, 2.1500 }, + { 6002.1001, 41465.3984, 2.1400 }, + { 6002.1001, 41465.6992, 2.1300 }, + { 6002.1001, 41466.0000, 2.1400 }, + { 6002.1001, 41466.3008, 2.1600 }, + { 6002.1001, 41466.6016, 2.1800 }, + { 6002.1001, 41466.8984, 2.2100 }, + { 6002.1001, 41467.1992, 2.2400 }, + { 6002.1001, 41467.5000, 2.2900 }, + + { 6002.3999, 41456.1016, 1.8300 }, + { 6002.3999, 41456.3984, 1.8000 }, + { 6002.3999, 41456.6992, 1.7800 }, + { 6002.3999, 41457.0000, 1.7600 }, + { 6002.3999, 41457.3008, 1.7400 }, + { 6002.3999, 41457.6016, 1.7400 }, + { 6002.3999, 41457.8984, 1.7400 }, + { 6002.3999, 41458.1992, 1.7400 }, + { 6002.3999, 41458.5000, 1.7400 }, + { 6002.3999, 41458.8008, 1.7400 }, + { 6002.3999, 41459.1016, 1.7300 }, + { 6002.3999, 41459.3984, 1.7300 }, + { 6002.3999, 41459.6992, 1.7300 }, + { 6002.3999, 41460.0000, 1.7300 }, + { 6002.3999, 41460.3008, 1.7400 }, + { 6002.3999, 41460.6016, 1.7400 }, + { 6002.3999, 41460.8984, 1.7400 }, + { 6002.3999, 41461.1992, 1.7400 }, + { 6002.3999, 41461.5000, 1.7300 }, + { 6002.3999, 41461.8008, 1.7300 }, + { 6002.3999, 41462.1016, 1.7400 }, + { 6002.3999, 41462.3984, 1.7700 }, + { 6002.3999, 41462.6992, 1.8000 }, + { 6002.3999, 41463.0000, 1.8500 }, + { 6002.3999, 41463.3008, 1.9200 }, + { 6002.3999, 41463.6016, 2.0100 }, + { 6002.3999, 41463.8984, 2.1100 }, + { 6002.3999, 41464.1992, 2.1800 }, + { 6002.3999, 41464.5000, 2.2200 }, + { 6002.3999, 41464.8008, 2.2200 }, + { 6002.3999, 41465.1016, 2.1900 }, + { 6002.3999, 41465.3984, 2.1700 }, + { 6002.3999, 41465.6992, 2.1500 }, + { 6002.3999, 41466.0000, 2.1600 }, + { 6002.3999, 41466.3008, 2.1700 }, + { 6002.3999, 41466.6016, 2.1900 }, + { 6002.3999, 41466.8984, 2.2100 }, + { 6002.3999, 41467.1992, 2.2400 }, + { 6002.3999, 41467.5000, 2.2900 }, + + { 6002.7002, 41456.1016, 1.8100 }, + { 6002.7002, 41456.3984, 1.7900 }, + { 6002.7002, 41456.6992, 1.7800 }, + { 6002.7002, 41457.0000, 1.7600 }, + { 6002.7002, 41457.3008, 1.7500 }, + { 6002.7002, 41457.6016, 1.7500 }, + { 6002.7002, 41457.8984, 1.7500 }, + { 6002.7002, 41458.1992, 1.7500 }, + { 6002.7002, 41458.5000, 1.7500 }, + { 6002.7002, 41458.8008, 1.7500 }, + { 6002.7002, 41459.1016, 1.7400 }, + { 6002.7002, 41459.3984, 1.7300 }, + { 6002.7002, 41459.6992, 1.7300 }, + { 6002.7002, 41460.0000, 1.7300 }, + { 6002.7002, 41460.3008, 1.7400 }, + { 6002.7002, 41460.6016, 1.7400 }, + { 6002.7002, 41460.8984, 1.7500 }, + { 6002.7002, 41461.1992, 1.7400 }, + { 6002.7002, 41461.5000, 1.7400 }, + { 6002.7002, 41461.8008, 1.7400 }, + { 6002.7002, 41462.1016, 1.7500 }, + { 6002.7002, 41462.3984, 1.7900 }, + { 6002.7002, 41462.6992, 1.8300 }, + { 6002.7002, 41463.0000, 1.8800 }, + { 6002.7002, 41463.3008, 1.9500 }, + { 6002.7002, 41463.6016, 2.0400 }, + { 6002.7002, 41463.8984, 2.1400 }, + { 6002.7002, 41464.1992, 2.2100 }, + { 6002.7002, 41464.5000, 2.2600 }, + { 6002.7002, 41464.8008, 2.2500 }, + { 6002.7002, 41465.1016, 2.2200 }, + { 6002.7002, 41465.3984, 2.2000 }, + { 6002.7002, 41465.6992, 2.1900 }, + { 6002.7002, 41466.0000, 2.1900 }, + { 6002.7002, 41466.3008, 2.2100 }, + { 6002.7002, 41466.6016, 2.2200 }, + { 6002.7002, 41466.8984, 2.2400 }, + { 6002.7002, 41467.1992, 2.2700 }, + { 6002.7002, 41467.5000, 2.3100 }, + + { 6003.0000, 41456.1016, 1.8400 }, + { 6003.0000, 41456.3984, 1.8300 }, + { 6003.0000, 41456.6992, 1.8200 }, + { 6003.0000, 41457.0000, 1.8100 }, + { 6003.0000, 41457.3008, 1.8000 }, + { 6003.0000, 41457.6016, 1.7900 }, + { 6003.0000, 41457.8984, 1.7800 }, + { 6003.0000, 41458.1992, 1.7700 }, + { 6003.0000, 41458.5000, 1.7600 }, + { 6003.0000, 41458.8008, 1.7600 }, + { 6003.0000, 41459.1016, 1.7500 }, + { 6003.0000, 41459.3984, 1.7400 }, + { 6003.0000, 41459.6992, 1.7400 }, + { 6003.0000, 41460.0000, 1.7400 }, + { 6003.0000, 41460.3008, 1.7500 }, + { 6003.0000, 41460.6016, 1.7500 }, + { 6003.0000, 41460.8984, 1.7500 }, + { 6003.0000, 41461.1992, 1.7500 }, + { 6003.0000, 41461.5000, 1.7500 }, + { 6003.0000, 41461.8008, 1.7500 }, + { 6003.0000, 41462.1016, 1.7700 }, + { 6003.0000, 41462.3984, 1.8000 }, + { 6003.0000, 41462.6992, 1.8500 }, + { 6003.0000, 41463.0000, 1.9100 }, + { 6003.0000, 41463.3008, 1.9800 }, + { 6003.0000, 41463.6016, 2.0600 }, + { 6003.0000, 41463.8984, 2.1500 }, + { 6003.0000, 41464.1992, 2.2200 }, + { 6003.0000, 41464.5000, 2.2700 }, + { 6003.0000, 41464.8008, 2.2700 }, + { 6003.0000, 41465.1016, 2.2400 }, + { 6003.0000, 41465.3984, 2.2300 }, + { 6003.0000, 41465.6992, 2.2200 }, + { 6003.0000, 41466.0000, 2.2300 }, + { 6003.0000, 41466.3008, 2.2600 }, + { 6003.0000, 41466.6016, 2.2800 }, + { 6003.0000, 41466.8984, 2.3000 }, + { 6003.0000, 41467.1992, 2.3300 }, + { 6003.0000, 41467.5000, 2.3700 }, + + { 6003.2998, 41456.1016, 1.8500 }, + { 6003.2998, 41456.3984, 1.8600 }, + { 6003.2998, 41456.6992, 1.8700 }, + { 6003.2998, 41457.0000, 1.8700 }, + { 6003.2998, 41457.3008, 1.8600 }, + { 6003.2998, 41457.6016, 1.8500 }, + { 6003.2998, 41457.8984, 1.8200 }, + { 6003.2998, 41458.1992, 1.8000 }, + { 6003.2998, 41458.5000, 1.7800 }, + { 6003.2998, 41458.8008, 1.7700 }, + { 6003.2998, 41459.1016, 1.7600 }, + { 6003.2998, 41459.3984, 1.7500 }, + { 6003.2998, 41459.6992, 1.7500 }, + { 6003.2998, 41460.0000, 1.7500 }, + { 6003.2998, 41460.3008, 1.7600 }, + { 6003.2998, 41460.6016, 1.7600 }, + { 6003.2998, 41460.8984, 1.7600 }, + { 6003.2998, 41461.1992, 1.7600 }, + { 6003.2998, 41461.5000, 1.7600 }, + { 6003.2998, 41461.8008, 1.7700 }, + { 6003.2998, 41462.1016, 1.7800 }, + { 6003.2998, 41462.3984, 1.8200 }, + { 6003.2998, 41462.6992, 1.8700 }, + { 6003.2998, 41463.0000, 1.9300 }, + { 6003.2998, 41463.3008, 1.9900 }, + { 6003.2998, 41463.6016, 2.0700 }, + { 6003.2998, 41463.8984, 2.1500 }, + { 6003.2998, 41464.1992, 2.2100 }, + { 6003.2998, 41464.5000, 2.2600 }, + { 6003.2998, 41464.8008, 2.2600 }, + { 6003.2998, 41465.1016, 2.2500 }, + { 6003.2998, 41465.3984, 2.2500 }, + { 6003.2998, 41465.6992, 2.2500 }, + { 6003.2998, 41466.0000, 2.2800 }, + { 6003.2998, 41466.3008, 2.3200 }, + { 6003.2998, 41466.6016, 2.3500 }, + { 6003.2998, 41466.8984, 2.3800 }, + { 6003.2998, 41467.1992, 2.4100 }, + { 6003.2998, 41467.5000, 2.4400 }, + + { 6003.6001, 41456.1016, 1.8600 }, + { 6003.6001, 41456.3984, 1.8800 }, + { 6003.6001, 41456.6992, 1.9000 }, + { 6003.6001, 41457.0000, 1.9200 }, + { 6003.6001, 41457.3008, 1.9200 }, + { 6003.6001, 41457.6016, 1.9000 }, + { 6003.6001, 41457.8984, 1.8700 }, + { 6003.6001, 41458.1992, 1.8400 }, + { 6003.6001, 41458.5000, 1.8100 }, + { 6003.6001, 41458.8008, 1.7900 }, + { 6003.6001, 41459.1016, 1.7700 }, + { 6003.6001, 41459.3984, 1.7600 }, + { 6003.6001, 41459.6992, 1.7600 }, + { 6003.6001, 41460.0000, 1.7600 }, + { 6003.6001, 41460.3008, 1.7700 }, + { 6003.6001, 41460.6016, 1.7700 }, + { 6003.6001, 41460.8984, 1.7800 }, + { 6003.6001, 41461.1992, 1.7700 }, + { 6003.6001, 41461.5000, 1.7700 }, + { 6003.6001, 41461.8008, 1.7800 }, + { 6003.6001, 41462.1016, 1.8000 }, + { 6003.6001, 41462.3984, 1.8400 }, + { 6003.6001, 41462.6992, 1.9000 }, + { 6003.6001, 41463.0000, 1.9500 }, + { 6003.6001, 41463.3008, 2.0200 }, + { 6003.6001, 41463.6016, 2.0900 }, + { 6003.6001, 41463.8984, 2.1600 }, + { 6003.6001, 41464.1992, 2.2200 }, + { 6003.6001, 41464.5000, 2.2600 }, + { 6003.6001, 41464.8008, 2.2700 }, + { 6003.6001, 41465.1016, 2.2700 }, + { 6003.6001, 41465.3984, 2.2700 }, + { 6003.6001, 41465.6992, 2.2900 }, + { 6003.6001, 41466.0000, 2.3400 }, + { 6003.6001, 41466.3008, 2.4000 }, + { 6003.6001, 41466.6016, 2.4500 }, + { 6003.6001, 41466.8984, 2.4900 }, + { 6003.6001, 41467.1992, 2.5100 }, + { 6003.6001, 41467.5000, 2.5200 }, + + { 6003.8999, 41456.1016, 1.8800 }, + { 6003.8999, 41456.3984, 1.9000 }, + { 6003.8999, 41456.6992, 1.9300 }, + { 6003.8999, 41457.0000, 1.9600 }, + { 6003.8999, 41457.3008, 1.9600 }, + { 6003.8999, 41457.6016, 1.9400 }, + { 6003.8999, 41457.8984, 1.9000 }, + { 6003.8999, 41458.1992, 1.8700 }, + { 6003.8999, 41458.5000, 1.8400 }, + { 6003.8999, 41458.8008, 1.8100 }, + { 6003.8999, 41459.1016, 1.7800 }, + { 6003.8999, 41459.3984, 1.7700 }, + { 6003.8999, 41459.6992, 1.7600 }, + { 6003.8999, 41460.0000, 1.7700 }, + { 6003.8999, 41460.3008, 1.7800 }, + { 6003.8999, 41460.6016, 1.7900 }, + { 6003.8999, 41460.8984, 1.7900 }, + { 6003.8999, 41461.1992, 1.7900 }, + { 6003.8999, 41461.5000, 1.7900 }, + { 6003.8999, 41461.8008, 1.8000 }, + { 6003.8999, 41462.1016, 1.8200 }, + { 6003.8999, 41462.3984, 1.8700 }, + { 6003.8999, 41462.6992, 1.9300 }, + { 6003.8999, 41463.0000, 2.0000 }, + { 6003.8999, 41463.3008, 2.0600 }, + { 6003.8999, 41463.6016, 2.1400 }, + { 6003.8999, 41463.8984, 2.2100 }, + { 6003.8999, 41464.1992, 2.2800 }, + { 6003.8999, 41464.5000, 2.3200 }, + { 6003.8999, 41464.8008, 2.3200 }, + { 6003.8999, 41465.1016, 2.3200 }, + { 6003.8999, 41465.3984, 2.3300 }, + { 6003.8999, 41465.6992, 2.3500 }, + { 6003.8999, 41466.0000, 2.4100 }, + { 6003.8999, 41466.3008, 2.4900 }, + { 6003.8999, 41466.6016, 2.5500 }, + { 6003.8999, 41466.8984, 2.5900 }, + { 6003.8999, 41467.1992, 2.6000 }, + { 6003.8999, 41467.5000, 2.6000 }, + + { 6004.2002, 41456.1016, 1.9100 }, + { 6004.2002, 41456.3984, 1.9200 }, + { 6004.2002, 41456.6992, 1.9600 }, + { 6004.2002, 41457.0000, 1.9800 }, + { 6004.2002, 41457.3008, 1.9800 }, + { 6004.2002, 41457.6016, 1.9500 }, + { 6004.2002, 41457.8984, 1.9100 }, + { 6004.2002, 41458.1992, 1.8700 }, + { 6004.2002, 41458.5000, 1.8400 }, + { 6004.2002, 41458.8008, 1.8100 }, + { 6004.2002, 41459.1016, 1.7900 }, + { 6004.2002, 41459.3984, 1.7800 }, + { 6004.2002, 41459.6992, 1.7700 }, + { 6004.2002, 41460.0000, 1.7800 }, + { 6004.2002, 41460.3008, 1.7900 }, + { 6004.2002, 41460.6016, 1.8000 }, + { 6004.2002, 41460.8984, 1.8100 }, + { 6004.2002, 41461.1992, 1.8100 }, + { 6004.2002, 41461.5000, 1.8000 }, + { 6004.2002, 41461.8008, 1.8100 }, + { 6004.2002, 41462.1016, 1.8400 }, + { 6004.2002, 41462.3984, 1.9000 }, + { 6004.2002, 41462.6992, 1.9700 }, + { 6004.2002, 41463.0000, 2.0500 }, + { 6004.2002, 41463.3008, 2.1400 }, + { 6004.2002, 41463.6016, 2.2200 }, + { 6004.2002, 41463.8984, 2.3100 }, + { 6004.2002, 41464.1992, 2.3800 }, + { 6004.2002, 41464.5000, 2.4300 }, + { 6004.2002, 41464.8008, 2.4400 }, + { 6004.2002, 41465.1016, 2.4200 }, + { 6004.2002, 41465.3984, 2.4200 }, + { 6004.2002, 41465.6992, 2.4400 }, + { 6004.2002, 41466.0000, 2.5100 }, + { 6004.2002, 41466.3008, 2.5800 }, + { 6004.2002, 41466.6016, 2.6500 }, + { 6004.2002, 41466.8984, 2.6900 }, + { 6004.2002, 41467.1992, 2.6900 }, + { 6004.2002, 41467.5000, 2.6800 }, + + { 6004.5000, 41456.1016, 1.9500 }, + { 6004.5000, 41456.3984, 1.9500 }, + { 6004.5000, 41456.6992, 1.9600 }, + { 6004.5000, 41457.0000, 1.9700 }, + { 6004.5000, 41457.3008, 1.9600 }, + { 6004.5000, 41457.6016, 1.9300 }, + { 6004.5000, 41457.8984, 1.8900 }, + { 6004.5000, 41458.1992, 1.8500 }, + { 6004.5000, 41458.5000, 1.8200 }, + { 6004.5000, 41458.8008, 1.8000 }, + { 6004.5000, 41459.1016, 1.7900 }, + { 6004.5000, 41459.3984, 1.7800 }, + { 6004.5000, 41459.6992, 1.7800 }, + { 6004.5000, 41460.0000, 1.7900 }, + { 6004.5000, 41460.3008, 1.8000 }, + { 6004.5000, 41460.6016, 1.8200 }, + { 6004.5000, 41460.8984, 1.8300 }, + { 6004.5000, 41461.1992, 1.8300 }, + { 6004.5000, 41461.5000, 1.8300 }, + { 6004.5000, 41461.8008, 1.8400 }, + { 6004.5000, 41462.1016, 1.8700 }, + { 6004.5000, 41462.3984, 1.9400 }, + { 6004.5000, 41462.6992, 2.0200 }, + { 6004.5000, 41463.0000, 2.1200 }, + { 6004.5000, 41463.3008, 2.2100 }, + { 6004.5000, 41463.6016, 2.3200 }, + { 6004.5000, 41463.8984, 2.4200 }, + { 6004.5000, 41464.1992, 2.5000 }, + { 6004.5000, 41464.5000, 2.5600 }, + { 6004.5000, 41464.8008, 2.5600 }, + { 6004.5000, 41465.1016, 2.5400 }, + { 6004.5000, 41465.3984, 2.5400 }, + { 6004.5000, 41465.6992, 2.5500 }, + { 6004.5000, 41466.0000, 2.6100 }, + { 6004.5000, 41466.3008, 2.6800 }, + { 6004.5000, 41466.6016, 2.7400 }, + { 6004.5000, 41466.8984, 2.7800 }, + { 6004.5000, 41467.1992, 2.7800 }, + { 6004.5000, 41467.5000, 2.7600 }, + + { 6004.7998, 41456.1016, 1.9800 }, + { 6004.7998, 41456.3984, 1.9600 }, + { 6004.7998, 41456.6992, 1.9400 }, + { 6004.7998, 41457.0000, 1.9100 }, + { 6004.7998, 41457.3008, 1.8900 }, + { 6004.7998, 41457.6016, 1.8600 }, + { 6004.7998, 41457.8984, 1.8300 }, + { 6004.7998, 41458.1992, 1.8100 }, + { 6004.7998, 41458.5000, 1.7900 }, + { 6004.7998, 41458.8008, 1.7900 }, + { 6004.7998, 41459.1016, 1.7900 }, + { 6004.7998, 41459.3984, 1.7900 }, + { 6004.7998, 41459.6992, 1.7900 }, + { 6004.7998, 41460.0000, 1.8000 }, + { 6004.7998, 41460.3008, 1.8200 }, + { 6004.7998, 41460.6016, 1.8400 }, + { 6004.7998, 41460.8984, 1.8500 }, + { 6004.7998, 41461.1992, 1.8600 }, + { 6004.7998, 41461.5000, 1.8700 }, + { 6004.7998, 41461.8008, 1.8900 }, + { 6004.7998, 41462.1016, 1.9200 }, + { 6004.7998, 41462.3984, 1.9900 }, + { 6004.7998, 41462.6992, 2.0800 }, + { 6004.7998, 41463.0000, 2.1700 }, + { 6004.7998, 41463.3008, 2.2700 }, + { 6004.7998, 41463.6016, 2.3900 }, + { 6004.7998, 41463.8984, 2.5100 }, + { 6004.7998, 41464.1992, 2.6100 }, + { 6004.7998, 41464.5000, 2.6700 }, + { 6004.7998, 41464.8008, 2.6800 }, + { 6004.7998, 41465.1016, 2.6600 }, + { 6004.7998, 41465.3984, 2.6500 }, + { 6004.7998, 41465.6992, 2.6600 }, + { 6004.7998, 41466.0000, 2.7100 }, + { 6004.7998, 41466.3008, 2.7700 }, + { 6004.7998, 41466.6016, 2.8300 }, + { 6004.7998, 41466.8984, 2.8700 }, + { 6004.7998, 41467.1992, 2.8700 }, + { 6004.7998, 41467.5000, 2.8500 }, + + { 6005.1001, 41456.1016, 2.0300 }, + { 6005.1001, 41456.3984, 1.9800 }, + { 6005.1001, 41456.6992, 1.9300 }, + { 6005.1001, 41457.0000, 1.8900 }, + { 6005.1001, 41457.3008, 1.8400 }, + { 6005.1001, 41457.6016, 1.8200 }, + { 6005.1001, 41457.8984, 1.8000 }, + { 6005.1001, 41458.1992, 1.8000 }, + { 6005.1001, 41458.5000, 1.8000 }, + { 6005.1001, 41458.8008, 1.8000 }, + { 6005.1001, 41459.1016, 1.7800 }, + { 6005.1001, 41459.3984, 1.7900 }, + { 6005.1001, 41459.6992, 1.8000 }, + { 6005.1001, 41460.0000, 1.8200 }, + { 6005.1001, 41460.3008, 1.8400 }, + { 6005.1001, 41460.6016, 1.8600 }, + { 6005.1001, 41460.8984, 1.8800 }, + { 6005.1001, 41461.1992, 1.9000 }, + { 6005.1001, 41461.5000, 1.9200 }, + { 6005.1001, 41461.8008, 1.9400 }, + { 6005.1001, 41462.1016, 1.9800 }, + { 6005.1001, 41462.3984, 2.0500 }, + { 6005.1001, 41462.6992, 2.1300 }, + { 6005.1001, 41463.0000, 2.2100 }, + { 6005.1001, 41463.3008, 2.3100 }, + { 6005.1001, 41463.6016, 2.4300 }, + { 6005.1001, 41463.8984, 2.5600 }, + { 6005.1001, 41464.1992, 2.6600 }, + { 6005.1001, 41464.5000, 2.7400 }, + { 6005.1001, 41464.8008, 2.7600 }, + { 6005.1001, 41465.1016, 2.7400 }, + { 6005.1001, 41465.3984, 2.7400 }, + { 6005.1001, 41465.6992, 2.7500 }, + { 6005.1001, 41466.0000, 2.7900 }, + { 6005.1001, 41466.3008, 2.8600 }, + { 6005.1001, 41466.6016, 2.9100 }, + { 6005.1001, 41466.8984, 2.9400 }, + { 6005.1001, 41467.1992, 2.9500 }, + { 6005.1001, 41467.5000, 2.9300 }, + + { 6005.3999, 41456.1016, 2.0700 }, + { 6005.3999, 41456.3984, 2.0200 }, + { 6005.3999, 41456.6992, 1.9500 }, + { 6005.3999, 41457.0000, 1.8900 }, + { 6005.3999, 41457.3008, 1.8400 }, + { 6005.3999, 41457.6016, 1.8100 }, + { 6005.3999, 41457.8984, 1.8000 }, + { 6005.3999, 41458.1992, 1.8000 }, + { 6005.3999, 41458.5000, 1.8000 }, + { 6005.3999, 41458.8008, 1.8000 }, + { 6005.3999, 41459.1016, 1.7900 }, + { 6005.3999, 41459.3984, 1.8000 }, + { 6005.3999, 41459.6992, 1.8200 }, + { 6005.3999, 41460.0000, 1.8400 }, + { 6005.3999, 41460.3008, 1.8600 }, + { 6005.3999, 41460.6016, 1.8800 }, + { 6005.3999, 41460.8984, 1.9100 }, + { 6005.3999, 41461.1992, 1.9300 }, + { 6005.3999, 41461.5000, 1.9600 }, + { 6005.3999, 41461.8008, 1.9900 }, + { 6005.3999, 41462.1016, 2.0300 }, + { 6005.3999, 41462.3984, 2.0900 }, + { 6005.3999, 41462.6992, 2.1700 }, + { 6005.3999, 41463.0000, 2.2500 }, + { 6005.3999, 41463.3008, 2.3400 }, + { 6005.3999, 41463.6016, 2.4500 }, + { 6005.3999, 41463.8984, 2.5600 }, + { 6005.3999, 41464.1992, 2.6600 }, + { 6005.3999, 41464.5000, 2.7400 }, + { 6005.3999, 41464.8008, 2.7700 }, + { 6005.3999, 41465.1016, 2.7800 }, + { 6005.3999, 41465.3984, 2.8000 }, + { 6005.3999, 41465.6992, 2.8300 }, + { 6005.3999, 41466.0000, 2.8800 }, + { 6005.3999, 41466.3008, 2.9400 }, + { 6005.3999, 41466.6016, 2.9800 }, + { 6005.3999, 41466.8984, 3.0200 }, + { 6005.3999, 41467.1992, 3.0300 }, + { 6005.3999, 41467.5000, 3.0200 }, + + { 6005.7002, 41456.1016, 2.0900 }, + { 6005.7002, 41456.3984, 2.0300 }, + { 6005.7002, 41456.6992, 1.9600 }, + { 6005.7002, 41457.0000, 1.8900 }, + { 6005.7002, 41457.3008, 1.8300 }, + { 6005.7002, 41457.6016, 1.8000 }, + { 6005.7002, 41457.8984, 1.8000 }, + { 6005.7002, 41458.1992, 1.8000 }, + { 6005.7002, 41458.5000, 1.8000 }, + { 6005.7002, 41458.8008, 1.8000 }, + { 6005.7002, 41459.1016, 1.8100 }, + { 6005.7002, 41459.3984, 1.8200 }, + { 6005.7002, 41459.6992, 1.8300 }, + { 6005.7002, 41460.0000, 1.8500 }, + { 6005.7002, 41460.3008, 1.8800 }, + { 6005.7002, 41460.6016, 1.9000 }, + { 6005.7002, 41460.8984, 1.9200 }, + { 6005.7002, 41461.1992, 1.9500 }, + { 6005.7002, 41461.5000, 1.9800 }, + { 6005.7002, 41461.8008, 2.0200 }, + { 6005.7002, 41462.1016, 2.0600 }, + { 6005.7002, 41462.3984, 2.1200 }, + { 6005.7002, 41462.6992, 2.2000 }, + { 6005.7002, 41463.0000, 2.2800 }, + { 6005.7002, 41463.3008, 2.3700 }, + { 6005.7002, 41463.6016, 2.4600 }, + { 6005.7002, 41463.8984, 2.5500 }, + { 6005.7002, 41464.1992, 2.6400 }, + { 6005.7002, 41464.5000, 2.7200 }, + { 6005.7002, 41464.8008, 2.7700 }, + { 6005.7002, 41465.1016, 2.8100 }, + { 6005.7002, 41465.3984, 2.8600 }, + { 6005.7002, 41465.6992, 2.9100 }, + { 6005.7002, 41466.0000, 2.9600 }, + { 6005.7002, 41466.3008, 3.0100 }, + { 6005.7002, 41466.6016, 3.0500 }, + { 6005.7002, 41466.8984, 3.0900 }, + { 6005.7002, 41467.1992, 3.1000 }, + { 6005.7002, 41467.5000, 3.1000 }, + + { 6006.0000, 41456.1016, 2.0700 }, + { 6006.0000, 41456.3984, 2.0100 }, + { 6006.0000, 41456.6992, 1.9400 }, + { 6006.0000, 41457.0000, 1.8700 }, + { 6006.0000, 41457.3008, 1.8000 }, + { 6006.0000, 41457.6016, 1.8000 }, + { 6006.0000, 41457.8984, 1.8000 }, + { 6006.0000, 41458.1992, 1.8000 }, + { 6006.0000, 41458.5000, 1.8000 }, + { 6006.0000, 41458.8008, 1.8100 }, + { 6006.0000, 41459.1016, 1.8200 }, + { 6006.0000, 41459.3984, 1.8300 }, + { 6006.0000, 41459.6992, 1.8400 }, + { 6006.0000, 41460.0000, 1.8600 }, + { 6006.0000, 41460.3008, 1.8900 }, + { 6006.0000, 41460.6016, 1.9100 }, + { 6006.0000, 41460.8984, 1.9300 }, + { 6006.0000, 41461.1992, 1.9600 }, + { 6006.0000, 41461.5000, 1.9900 }, + { 6006.0000, 41461.8008, 2.0300 }, + { 6006.0000, 41462.1016, 2.0800 }, + { 6006.0000, 41462.3984, 2.1500 }, + { 6006.0000, 41462.6992, 2.2400 }, + { 6006.0000, 41463.0000, 2.3200 }, + { 6006.0000, 41463.3008, 2.4100 }, + { 6006.0000, 41463.6016, 2.5000 }, + { 6006.0000, 41463.8984, 2.6000 }, + { 6006.0000, 41464.1992, 2.6900 }, + { 6006.0000, 41464.5000, 2.7800 }, + { 6006.0000, 41464.8008, 2.8300 }, + { 6006.0000, 41465.1016, 2.8800 }, + { 6006.0000, 41465.3984, 2.9200 }, + { 6006.0000, 41465.6992, 2.9700 }, + { 6006.0000, 41466.0000, 3.0200 }, + { 6006.0000, 41466.3008, 3.0700 }, + { 6006.0000, 41466.6016, 3.1200 }, + { 6006.0000, 41466.8984, 3.1500 }, + { 6006.0000, 41467.1992, 3.1700 }, + { 6006.0000, 41467.5000, 3.1700 }, + + { 6006.2998, 41456.1016, 2.0300 }, + { 6006.2998, 41456.3984, 1.9700 }, + { 6006.2998, 41456.6992, 1.9000 }, + { 6006.2998, 41457.0000, 1.8300 }, + { 6006.2998, 41457.3008, 1.8000 }, + { 6006.2998, 41457.6016, 1.8000 }, + { 6006.2998, 41457.8984, 1.8000 }, + { 6006.2998, 41458.1992, 1.8000 }, + { 6006.2998, 41458.5000, 1.8000 }, + { 6006.2998, 41458.8008, 1.8200 }, + { 6006.2998, 41459.1016, 1.8300 }, + { 6006.2998, 41459.3984, 1.8500 }, + { 6006.2998, 41459.6992, 1.8600 }, + { 6006.2998, 41460.0000, 1.8800 }, + { 6006.2998, 41460.3008, 1.9000 }, + { 6006.2998, 41460.6016, 1.9200 }, + { 6006.2998, 41460.8984, 1.9400 }, + { 6006.2998, 41461.1992, 1.9700 }, + { 6006.2998, 41461.5000, 2.0100 }, + { 6006.2998, 41461.8008, 2.0500 }, + { 6006.2998, 41462.1016, 2.1000 }, + { 6006.2998, 41462.3984, 2.1800 }, + { 6006.2998, 41462.6992, 2.2700 }, + { 6006.2998, 41463.0000, 2.3600 }, + { 6006.2998, 41463.3008, 2.4500 }, + { 6006.2998, 41463.6016, 2.5600 }, + { 6006.2998, 41463.8984, 2.6700 }, + { 6006.2998, 41464.1992, 2.7700 }, + { 6006.2998, 41464.5000, 2.8600 }, + { 6006.2998, 41464.8008, 2.9100 }, + { 6006.2998, 41465.1016, 2.9400 }, + { 6006.2998, 41465.3984, 2.9700 }, + { 6006.2998, 41465.6992, 3.0100 }, + { 6006.2998, 41466.0000, 3.0600 }, + { 6006.2998, 41466.3008, 3.1200 }, + { 6006.2998, 41466.6016, 3.1800 }, + { 6006.2998, 41466.8984, 3.2200 }, + { 6006.2998, 41467.1992, 3.2400 }, + { 6006.2998, 41467.5000, 3.2400 }, + + { 6006.6001, 41456.1016, 1.9600 }, + { 6006.6001, 41456.3984, 1.9100 }, + { 6006.6001, 41456.6992, 1.8500 }, + { 6006.6001, 41457.0000, 1.8000 }, + { 6006.6001, 41457.3008, 1.8000 }, + { 6006.6001, 41457.6016, 1.8000 }, + { 6006.6001, 41457.8984, 1.8000 }, + { 6006.6001, 41458.1992, 1.8000 }, + { 6006.6001, 41458.5000, 1.8000 }, + { 6006.6001, 41458.8008, 1.8200 }, + { 6006.6001, 41459.1016, 1.8400 }, + { 6006.6001, 41459.3984, 1.8600 }, + { 6006.6001, 41459.6992, 1.8800 }, + { 6006.6001, 41460.0000, 1.9000 }, + { 6006.6001, 41460.3008, 1.9100 }, + { 6006.6001, 41460.6016, 1.9300 }, + { 6006.6001, 41460.8984, 1.9500 }, + { 6006.6001, 41461.1992, 1.9800 }, + { 6006.6001, 41461.5000, 2.0200 }, + { 6006.6001, 41461.8008, 2.0700 }, + { 6006.6001, 41462.1016, 2.1200 }, + { 6006.6001, 41462.3984, 2.2000 }, + { 6006.6001, 41462.6992, 2.3000 }, + { 6006.6001, 41463.0000, 2.3900 }, + { 6006.6001, 41463.3008, 2.4900 }, + { 6006.6001, 41463.6016, 2.6100 }, + { 6006.6001, 41463.8984, 2.7300 }, + { 6006.6001, 41464.1992, 2.8400 }, + { 6006.6001, 41464.5000, 2.9300 }, + { 6006.6001, 41464.8008, 2.9700 }, + { 6006.6001, 41465.1016, 2.9800 }, + { 6006.6001, 41465.3984, 3.0000 }, + { 6006.6001, 41465.6992, 3.0300 }, + { 6006.6001, 41466.0000, 3.0900 }, + { 6006.6001, 41466.3008, 3.1700 }, + { 6006.6001, 41466.6016, 3.2400 }, + { 6006.6001, 41466.8984, 3.3000 }, + { 6006.6001, 41467.1992, 3.3200 }, + { 6006.6001, 41467.5000, 3.3200 }, + + { 6006.8999, 41456.1016, 1.8800 }, + { 6006.8999, 41456.3984, 1.8500 }, + { 6006.8999, 41456.6992, 1.8000 }, + { 6006.8999, 41457.0000, 1.8000 }, + { 6006.8999, 41457.3008, 1.8000 }, + { 6006.8999, 41457.6016, 1.8000 }, + { 6006.8999, 41457.8984, 1.8000 }, + { 6006.8999, 41458.1992, 1.8000 }, + { 6006.8999, 41458.5000, 1.8000 }, + { 6006.8999, 41458.8008, 1.8200 }, + { 6006.8999, 41459.1016, 1.8500 }, + { 6006.8999, 41459.3984, 1.8800 }, + { 6006.8999, 41459.6992, 1.9000 }, + { 6006.8999, 41460.0000, 1.9200 }, + { 6006.8999, 41460.3008, 1.9300 }, + { 6006.8999, 41460.6016, 1.9400 }, + { 6006.8999, 41460.8984, 1.9600 }, + { 6006.8999, 41461.1992, 1.9900 }, + { 6006.8999, 41461.5000, 2.0400 }, + { 6006.8999, 41461.8008, 2.0800 }, + { 6006.8999, 41462.1016, 2.1400 }, + { 6006.8999, 41462.3984, 2.2300 }, + { 6006.8999, 41462.6992, 2.3300 }, + { 6006.8999, 41463.0000, 2.4300 }, + { 6006.8999, 41463.3008, 2.5400 }, + { 6006.8999, 41463.6016, 2.6700 }, + { 6006.8999, 41463.8984, 2.7900 }, + { 6006.8999, 41464.1992, 2.9100 }, + { 6006.8999, 41464.5000, 3.0000 }, + { 6006.8999, 41464.8008, 3.0400 }, + { 6006.8999, 41465.1016, 3.0400 }, + { 6006.8999, 41465.3984, 3.0500 }, + { 6006.8999, 41465.6992, 3.0800 }, + { 6006.8999, 41466.0000, 3.1500 }, + { 6006.8999, 41466.3008, 3.2400 }, + { 6006.8999, 41466.6016, 3.3200 }, + { 6006.8999, 41466.8984, 3.3800 }, + { 6006.8999, 41467.1992, 3.4000 }, + { 6006.8999, 41467.5000, 3.4000 }, + + { 6007.2002, 41456.1016, 1.8300 }, + { 6007.2002, 41456.3984, 1.8000 }, + { 6007.2002, 41456.6992, 1.8000 }, + { 6007.2002, 41457.0000, 1.8000 }, + { 6007.2002, 41457.3008, 1.8000 }, + { 6007.2002, 41457.6016, 1.8000 }, + { 6007.2002, 41457.8984, 1.8000 }, + { 6007.2002, 41458.1992, 1.8000 }, + { 6007.2002, 41458.5000, 1.8000 }, + { 6007.2002, 41458.8008, 1.8000 }, + { 6007.2002, 41459.1016, 1.8600 }, + { 6007.2002, 41459.3984, 1.8900 }, + { 6007.2002, 41459.6992, 1.9200 }, + { 6007.2002, 41460.0000, 1.9400 }, + { 6007.2002, 41460.3008, 1.9500 }, + { 6007.2002, 41460.6016, 1.9600 }, + { 6007.2002, 41460.8984, 1.9800 }, + { 6007.2002, 41461.1992, 2.0100 }, + { 6007.2002, 41461.5000, 2.0600 }, + { 6007.2002, 41461.8008, 2.1100 }, + { 6007.2002, 41462.1016, 2.1700 }, + { 6007.2002, 41462.3984, 2.2600 }, + { 6007.2002, 41462.6992, 2.3700 }, + { 6007.2002, 41463.0000, 2.4800 }, + { 6007.2002, 41463.3008, 2.6000 }, + { 6007.2002, 41463.6016, 2.7300 }, + { 6007.2002, 41463.8984, 2.8600 }, + { 6007.2002, 41464.1992, 2.9700 }, + { 6007.2002, 41464.5000, 3.0600 }, + { 6007.2002, 41464.8008, 3.0900 }, + { 6007.2002, 41465.1016, 3.0900 }, + { 6007.2002, 41465.3984, 3.1000 }, + { 6007.2002, 41465.6992, 3.1300 }, + { 6007.2002, 41466.0000, 3.2100 }, + { 6007.2002, 41466.3008, 3.3100 }, + { 6007.2002, 41466.6016, 3.4100 }, + { 6007.2002, 41466.8984, 3.4800 }, + { 6007.2002, 41467.1992, 3.5000 }, + { 6007.2002, 41467.5000, 3.4800 }, + + { 6007.5000, 41456.1016, 1.8000 }, + { 6007.5000, 41456.3984, 1.7800 }, + { 6007.5000, 41456.6992, 1.8000 }, + { 6007.5000, 41457.0000, 1.8000 }, + { 6007.5000, 41457.3008, 1.8000 }, + { 6007.5000, 41457.6016, 1.8000 }, + { 6007.5000, 41457.8984, 1.8000 }, + { 6007.5000, 41458.1992, 1.8000 }, + { 6007.5000, 41458.5000, 1.8000 }, + { 6007.5000, 41458.8008, 1.8400 }, + { 6007.5000, 41459.1016, 1.8800 }, + { 6007.5000, 41459.3984, 1.9100 }, + { 6007.5000, 41459.6992, 1.9400 }, + { 6007.5000, 41460.0000, 1.9600 }, + { 6007.5000, 41460.3008, 1.9700 }, + { 6007.5000, 41460.6016, 1.9900 }, + { 6007.5000, 41460.8984, 2.0100 }, + { 6007.5000, 41461.1992, 2.0500 }, + { 6007.5000, 41461.5000, 2.1000 }, + { 6007.5000, 41461.8008, 2.1600 }, + { 6007.5000, 41462.1016, 2.2300 }, + { 6007.5000, 41462.3984, 2.3200 }, + { 6007.5000, 41462.6992, 2.4400 }, + { 6007.5000, 41463.0000, 2.5600 }, + { 6007.5000, 41463.3008, 2.6800 }, + { 6007.5000, 41463.6016, 2.8000 }, + { 6007.5000, 41463.8984, 2.9200 }, + { 6007.5000, 41464.1992, 3.0200 }, + { 6007.5000, 41464.5000, 3.1100 }, + { 6007.5000, 41464.8008, 3.1300 }, + { 6007.5000, 41465.1016, 3.1200 }, + { 6007.5000, 41465.3984, 3.1200 }, + { 6007.5000, 41465.6992, 3.1500 }, + { 6007.5000, 41466.0000, 3.2400 }, + { 6007.5000, 41466.3008, 3.3700 }, + { 6007.5000, 41466.6016, 3.4800 }, + { 6007.5000, 41466.8984, 3.5700 }, + { 6007.5000, 41467.1992, 3.5800 }, + { 6007.5000, 41467.5000, 3.5600 }, + + { 6007.7998, 41456.1016, 1.8100 }, + { 6007.7998, 41456.3984, 1.7800 }, + { 6007.7998, 41456.6992, 1.8000 }, + { 6007.7998, 41457.0000, 1.8000 }, + { 6007.7998, 41457.3008, 1.8000 }, + { 6007.7998, 41457.6016, 1.8000 }, + { 6007.7998, 41457.8984, 1.8000 }, + { 6007.7998, 41458.1992, 1.8000 }, + { 6007.7998, 41458.5000, 1.8000 }, + { 6007.7998, 41458.8008, 1.8700 }, + { 6007.7998, 41459.1016, 1.9000 }, + { 6007.7998, 41459.3984, 1.9400 }, + { 6007.7998, 41459.6992, 1.9700 }, + { 6007.7998, 41460.0000, 1.9900 }, + { 6007.7998, 41460.3008, 2.0000 }, + { 6007.7998, 41460.6016, 2.0200 }, + { 6007.7998, 41460.8984, 2.0500 }, + { 6007.7998, 41461.1992, 2.1000 }, + { 6007.7998, 41461.5000, 2.1600 }, + { 6007.7998, 41461.8008, 2.2300 }, + { 6007.7998, 41462.1016, 2.3100 }, + { 6007.7998, 41462.3984, 2.4100 }, + { 6007.7998, 41462.6992, 2.5400 }, + { 6007.7998, 41463.0000, 2.6600 }, + { 6007.7998, 41463.3008, 2.7800 }, + { 6007.7998, 41463.6016, 2.8900 }, + { 6007.7998, 41463.8984, 2.9900 }, + { 6007.7998, 41464.1992, 3.0800 }, + { 6007.7998, 41464.5000, 3.1600 }, + { 6007.7998, 41464.8008, 3.1800 }, + { 6007.7998, 41465.1016, 3.1700 }, + { 6007.7998, 41465.3984, 3.1800 }, + { 6007.7998, 41465.6992, 3.2100 }, + { 6007.7998, 41466.0000, 3.3000 }, + { 6007.7998, 41466.3008, 3.4300 }, + { 6007.7998, 41466.6016, 3.5400 }, + { 6007.7998, 41466.8984, 3.6300 }, + { 6007.7998, 41467.1992, 3.6400 }, + { 6007.7998, 41467.5000, 3.6000 }, + + { 6008.1001, 41456.1016, 1.8200 }, + { 6008.1001, 41456.3984, 1.7900 }, + { 6008.1001, 41456.6992, 1.8000 }, + { 6008.1001, 41457.0000, 1.8000 }, + { 6008.1001, 41457.3008, 1.8000 }, + { 6008.1001, 41457.6016, 1.8000 }, + { 6008.1001, 41457.8984, 1.8000 }, + { 6008.1001, 41458.1992, 1.8000 }, + { 6008.1001, 41458.5000, 1.8700 }, + { 6008.1001, 41458.8008, 1.9000 }, + { 6008.1001, 41459.1016, 1.9300 }, + { 6008.1001, 41459.3984, 1.9600 }, + { 6008.1001, 41459.6992, 2.0000 }, + { 6008.1001, 41460.0000, 2.0200 }, + { 6008.1001, 41460.3008, 2.0400 }, + { 6008.1001, 41460.6016, 2.0700 }, + { 6008.1001, 41460.8984, 2.1000 }, + { 6008.1001, 41461.1992, 2.1600 }, + { 6008.1001, 41461.5000, 2.2300 }, + { 6008.1001, 41461.8008, 2.3100 }, + { 6008.1001, 41462.1016, 2.3900 }, + { 6008.1001, 41462.3984, 2.5000 }, + { 6008.1001, 41462.6992, 2.6300 }, + { 6008.1001, 41463.0000, 2.7500 }, + { 6008.1001, 41463.3008, 2.8700 }, + { 6008.1001, 41463.6016, 2.9800 }, + { 6008.1001, 41463.8984, 3.0800 }, + { 6008.1001, 41464.1992, 3.1600 }, + { 6008.1001, 41464.5000, 3.2300 }, + { 6008.1001, 41464.8008, 3.2600 }, + { 6008.1001, 41465.1016, 3.2500 }, + { 6008.1001, 41465.3984, 3.2600 }, + { 6008.1001, 41465.6992, 3.2900 }, + { 6008.1001, 41466.0000, 3.3800 }, + { 6008.1001, 41466.3008, 3.4900 }, + { 6008.1001, 41466.6016, 3.5900 }, + { 6008.1001, 41466.8984, 3.6700 }, + { 6008.1001, 41467.1992, 3.6700 }, + { 6008.1001, 41467.5000, 3.6400 }, + + { 6008.3999, 41456.1016, 1.8100 }, + { 6008.3999, 41456.3984, 1.8000 }, + { 6008.3999, 41456.6992, 1.8000 }, + { 6008.3999, 41457.0000, 1.8000 }, + { 6008.3999, 41457.3008, 1.8000 }, + { 6008.3999, 41457.6016, 1.8000 }, + { 6008.3999, 41457.8984, 1.8000 }, + { 6008.3999, 41458.1992, 1.8000 }, + { 6008.3999, 41458.5000, 1.9100 }, + { 6008.3999, 41458.8008, 1.9400 }, + { 6008.3999, 41459.1016, 1.9600 }, + { 6008.3999, 41459.3984, 1.9900 }, + { 6008.3999, 41459.6992, 2.0200 }, + { 6008.3999, 41460.0000, 2.0500 }, + { 6008.3999, 41460.3008, 2.0800 }, + { 6008.3999, 41460.6016, 2.1200 }, + { 6008.3999, 41460.8984, 2.1600 }, + { 6008.3999, 41461.1992, 2.2200 }, + { 6008.3999, 41461.5000, 2.2900 }, + { 6008.3999, 41461.8008, 2.3600 }, + { 6008.3999, 41462.1016, 2.4400 }, + { 6008.3999, 41462.3984, 2.5600 }, + { 6008.3999, 41462.6992, 2.6900 }, + { 6008.3999, 41463.0000, 2.8100 }, + { 6008.3999, 41463.3008, 2.9400 }, + { 6008.3999, 41463.6016, 3.0600 }, + { 6008.3999, 41463.8984, 3.1700 }, + { 6008.3999, 41464.1992, 3.2700 }, + { 6008.3999, 41464.5000, 3.3500 }, + { 6008.3999, 41464.8008, 3.3700 }, + { 6008.3999, 41465.1016, 3.3600 }, + { 6008.3999, 41465.3984, 3.3600 }, + { 6008.3999, 41465.6992, 3.3800 }, + { 6008.3999, 41466.0000, 3.4500 }, + { 6008.3999, 41466.3008, 3.5500 }, + { 6008.3999, 41466.6016, 3.6400 }, + { 6008.3999, 41466.8984, 3.7100 }, + { 6008.3999, 41467.1992, 3.7100 }, + { 6008.3999, 41467.5000, 3.6900 }, + + { 6008.7002, 41456.1016, 1.7800 }, + { 6008.7002, 41456.3984, 1.7800 }, + { 6008.7002, 41456.6992, 1.8000 }, + { 6008.7002, 41457.0000, 1.8000 }, + { 6008.7002, 41457.3008, 1.8000 }, + { 6008.7002, 41457.6016, 1.8000 }, + { 6008.7002, 41457.8984, 1.8000 }, + { 6008.7002, 41458.1992, 1.9000 }, + { 6008.7002, 41458.5000, 1.9400 }, + { 6008.7002, 41458.8008, 1.9800 }, + { 6008.7002, 41459.1016, 2.0100 }, + { 6008.7002, 41459.3984, 2.0400 }, + { 6008.7002, 41459.6992, 2.0800 }, + { 6008.7002, 41460.0000, 2.1100 }, + { 6008.7002, 41460.3008, 2.1500 }, + { 6008.7002, 41460.6016, 2.1800 }, + { 6008.7002, 41460.8984, 2.2300 }, + { 6008.7002, 41461.1992, 2.2800 }, + { 6008.7002, 41461.5000, 2.3300 }, + { 6008.7002, 41461.8008, 2.3800 }, + { 6008.7002, 41462.1016, 2.4600 }, + { 6008.7002, 41462.3984, 2.5700 }, + { 6008.7002, 41462.6992, 2.7000 }, + { 6008.7002, 41463.0000, 2.8300 }, + { 6008.7002, 41463.3008, 2.9700 }, + { 6008.7002, 41463.6016, 3.1000 }, + { 6008.7002, 41463.8984, 3.2300 }, + { 6008.7002, 41464.1992, 3.3600 }, + { 6008.7002, 41464.5000, 3.4500 }, + { 6008.7002, 41464.8008, 3.4800 }, + { 6008.7002, 41465.1016, 3.4600 }, + { 6008.7002, 41465.3984, 3.4600 }, + { 6008.7002, 41465.6992, 3.4700 }, + { 6008.7002, 41466.0000, 3.5300 }, + { 6008.7002, 41466.3008, 3.6200 }, + { 6008.7002, 41466.6016, 3.7000 }, + { 6008.7002, 41466.8984, 3.7600 }, + { 6008.7002, 41467.1992, 3.7700 }, + { 6008.7002, 41467.5000, 3.7500 }, + + { 6009.0000, 41456.1016, 1.7300 }, + { 6009.0000, 41456.3984, 1.7500 }, + { 6009.0000, 41456.6992, 1.7500 }, + { 6009.0000, 41457.0000, 1.8000 }, + { 6009.0000, 41457.3008, 1.8000 }, + { 6009.0000, 41457.6016, 1.8000 }, + { 6009.0000, 41457.8984, 1.8600 }, + { 6009.0000, 41458.1992, 1.9000 }, + { 6009.0000, 41458.5000, 1.9500 }, + { 6009.0000, 41458.8008, 2.0000 }, + { 6009.0000, 41459.1016, 2.0600 }, + { 6009.0000, 41459.3984, 2.1100 }, + { 6009.0000, 41459.6992, 2.1700 }, + { 6009.0000, 41460.0000, 2.2100 }, + { 6009.0000, 41460.3008, 2.2400 }, + { 6009.0000, 41460.6016, 2.2800 }, + { 6009.0000, 41460.8984, 2.3200 }, + { 6009.0000, 41461.1992, 2.3400 }, + { 6009.0000, 41461.5000, 2.3700 }, + { 6009.0000, 41461.8008, 2.4000 }, + { 6009.0000, 41462.1016, 2.4500 }, + { 6009.0000, 41462.3984, 2.5500 }, + { 6009.0000, 41462.6992, 2.6800 }, + { 6009.0000, 41463.0000, 2.8100 }, + { 6009.0000, 41463.3008, 2.9400 }, + { 6009.0000, 41463.6016, 3.0900 }, + { 6009.0000, 41463.8984, 3.2300 }, + { 6009.0000, 41464.1992, 3.3700 }, + { 6009.0000, 41464.5000, 3.4900 }, + { 6009.0000, 41464.8008, 3.5200 }, + { 6009.0000, 41465.1016, 3.5200 }, + { 6009.0000, 41465.3984, 3.5200 }, + { 6009.0000, 41465.6992, 3.5400 }, + { 6009.0000, 41466.0000, 3.6000 }, + { 6009.0000, 41466.3008, 3.6900 }, + { 6009.0000, 41466.6016, 3.7600 }, + { 6009.0000, 41466.8984, 3.8300 }, + { 6009.0000, 41467.1992, 3.8400 }, + { 6009.0000, 41467.5000, 3.8300 }, + + { 6009.2998, 41456.1016, 1.7000 }, + { 6009.2998, 41456.3984, 1.7100 }, + { 6009.2998, 41456.6992, 1.7200 }, + { 6009.2998, 41457.0000, 1.7400 }, + { 6009.2998, 41457.3008, 1.7600 }, + { 6009.2998, 41457.6016, 1.7900 }, + { 6009.2998, 41457.8984, 1.8400 }, + { 6009.2998, 41458.1992, 1.8900 }, + { 6009.2998, 41458.5000, 1.9400 }, + { 6009.2998, 41458.8008, 2.0000 }, + { 6009.2998, 41459.1016, 2.0800 }, + { 6009.2998, 41459.3984, 2.1500 }, + { 6009.2998, 41459.6992, 2.2300 }, + { 6009.2998, 41460.0000, 2.2800 }, + { 6009.2998, 41460.3008, 2.3300 }, + { 6009.2998, 41460.6016, 2.3800 }, + { 6009.2998, 41460.8984, 2.4200 }, + { 6009.2998, 41461.1992, 2.4300 }, + { 6009.2998, 41461.5000, 2.4300 }, + { 6009.2998, 41461.8008, 2.4300 }, + { 6009.2998, 41462.1016, 2.4500 }, + { 6009.2998, 41462.3984, 2.5400 }, + { 6009.2998, 41462.6992, 2.6500 }, + { 6009.2998, 41463.0000, 2.7700 }, + { 6009.2998, 41463.3008, 2.8900 }, + { 6009.2998, 41463.6016, 3.0300 }, + { 6009.2998, 41463.8984, 3.1800 }, + { 6009.2998, 41464.1992, 3.3200 }, + { 6009.2998, 41464.5000, 3.4500 }, + { 6009.2998, 41464.8008, 3.5000 }, + { 6009.2998, 41465.1016, 3.5200 }, + { 6009.2998, 41465.3984, 3.5400 }, + { 6009.2998, 41465.6992, 3.5800 }, + { 6009.2998, 41466.0000, 3.6500 }, + { 6009.2998, 41466.3008, 3.7500 }, + { 6009.2998, 41466.6016, 3.8400 }, + { 6009.2998, 41466.8984, 3.9100 }, + { 6009.2998, 41467.1992, 3.9400 }, + { 6009.2998, 41467.5000, 3.9300 }, + + { 6009.6001, 41456.3984, 1.6900 }, + { 6009.6001, 41456.6992, 1.7000 }, + { 6009.6001, 41457.0000, 1.7100 }, + { 6009.6001, 41457.3008, 1.7300 }, + { 6009.6001, 41457.6016, 1.7600 }, + { 6009.6001, 41457.8984, 1.8000 }, + { 6009.6001, 41458.1992, 1.8500 }, + { 6009.6001, 41458.5000, 1.9000 }, + { 6009.6001, 41458.8008, 1.9700 }, + { 6009.6001, 41459.1016, 2.0500 }, + { 6009.6001, 41459.3984, 2.1400 }, + { 6009.6001, 41459.6992, 2.2200 }, + { 6009.6001, 41460.0000, 2.3100 }, + { 6009.6001, 41460.3008, 2.3800 }, + { 6009.6001, 41460.6016, 2.4600 }, + { 6009.6001, 41460.8984, 2.5200 }, + { 6009.6001, 41461.1992, 2.5400 }, + { 6009.6001, 41461.5000, 2.5200 }, + { 6009.6001, 41461.8008, 2.5200 }, + { 6009.6001, 41462.1016, 2.5300 }, + { 6009.6001, 41462.3984, 2.5900 }, + { 6009.6001, 41462.6992, 2.6900 }, + { 6009.6001, 41463.0000, 2.7900 }, + { 6009.6001, 41463.3008, 2.8900 }, + { 6009.6001, 41463.6016, 3.0100 }, + { 6009.6001, 41463.8984, 3.1400 }, + { 6009.6001, 41464.1992, 3.2600 }, + { 6009.6001, 41464.5000, 3.3700 }, + { 6009.6001, 41464.8008, 3.4400 }, + { 6009.6001, 41465.1016, 3.4900 }, + { 6009.6001, 41465.3984, 3.5500 }, + { 6009.6001, 41465.6992, 3.6100 }, + { 6009.6001, 41466.0000, 3.7000 }, + { 6009.6001, 41466.3008, 3.8100 }, + { 6009.6001, 41466.6016, 3.9200 }, + { 6009.6001, 41466.8984, 4.0000 }, + { 6009.6001, 41467.1992, 4.0400 }, + { 6009.6001, 41467.5000, 4.0400 }, + { 6009.6001, 41467.8008, 4.0500 }, + + { 6009.8999, 41456.3984, 1.6900 }, + { 6009.8999, 41456.6992, 1.7000 }, + { 6009.8999, 41457.0000, 1.7100 }, + { 6009.8999, 41457.3008, 1.7200 }, + { 6009.8999, 41457.6016, 1.7400 }, + { 6009.8999, 41457.8984, 1.7600 }, + { 6009.8999, 41458.1992, 1.7900 }, + { 6009.8999, 41458.5000, 1.8200 }, + { 6009.8999, 41458.8008, 1.9000 }, + { 6009.8999, 41459.1016, 2.0000 }, + { 6009.8999, 41459.3984, 2.1000 }, + { 6009.8999, 41459.6992, 2.2000 }, + { 6009.8999, 41460.0000, 2.3100 }, + { 6009.8999, 41460.3008, 2.4200 }, + { 6009.8999, 41460.6016, 2.5200 }, + { 6009.8999, 41460.8984, 2.6200 }, + { 6009.8999, 41461.1992, 2.6500 }, + { 6009.8999, 41461.5000, 2.6600 }, + { 6009.8999, 41461.8008, 2.6700 }, + { 6009.8999, 41462.1016, 2.6900 }, + { 6009.8999, 41462.3984, 2.7400 }, + { 6009.8999, 41462.6992, 2.8200 }, + { 6009.8999, 41463.0000, 2.9000 }, + { 6009.8999, 41463.3008, 2.9900 }, + { 6009.8999, 41463.6016, 3.0700 }, + { 6009.8999, 41463.8984, 3.1600 }, + { 6009.8999, 41464.1992, 3.2400 }, + { 6009.8999, 41464.5000, 3.3100 }, + { 6009.8999, 41464.8008, 3.4000 }, + { 6009.8999, 41465.1016, 3.4800 }, + { 6009.8999, 41465.3984, 3.5700 }, + { 6009.8999, 41465.6992, 3.6600 }, + { 6009.8999, 41466.0000, 3.7700 }, + { 6009.8999, 41466.3008, 3.8800 }, + { 6009.8999, 41466.6016, 3.9900 }, + { 6009.8999, 41466.8984, 4.0900 }, + { 6009.8999, 41467.1992, 4.1300 }, + { 6009.8999, 41467.5000, 4.1400 }, + { 6009.8999, 41467.8008, 4.1600 }, + +}; + +static float normal[][3] = { + { -0.2560, -0.1125, 0.9600 }, + { -0.2850, -0.1272, 0.9501 }, + { -0.3146, -0.0941, 0.9440 }, + { -0.3295, -0.0626, 0.9419 }, + { -0.3154, -0.0315, 0.9474 }, + { -0.2560, 0.0162, 0.9644 }, + { -0.1784, 0.0328, 0.9801 }, + { -0.1145, 0.0493, 0.9887 }, + { -0.0488, 0.0494, 0.9908 }, + { 0.0001, 0.0497, 0.9964 }, + { 0.0331, 0.0666, 0.9950 }, + { 0.0825, 0.0828, 0.9918 }, + { 0.0824, 0.0988, 0.9905 }, + { 0.0662, 0.0826, 0.9937 }, + { 0.0166, 0.0663, 0.9975 }, + { -0.0166, 0.0500, 0.9983 }, + { -0.0665, 0.0334, 0.9972 }, + { -0.1157, 0.0000, 0.9926 }, + { -0.1794, -0.0812, 0.9791 }, + { -0.1626, -0.1459, 0.9757 }, + { -0.1135, -0.1954, 0.9734 }, + { -0.0161, -0.2432, 0.9696 }, + { 0.0810, -0.2098, 0.9731 }, + { 0.1469, -0.1302, 0.9799 }, + { 0.1639, -0.0653, 0.9838 }, + { 0.1321, -0.0165, 0.9910 }, + { 0.0665, 0.0166, 0.9975 }, + { 0.0167, 0.0332, 0.9992 }, + { -0.0166, 0.0498, 0.9983 }, + { -0.0166, 0.0663, 0.9975 }, + { -0.0166, 0.0500, 0.9983 }, + { -0.0167, 0.0334, 0.9992 }, + { -0.0333, 0.0166, 0.9992 }, + { -0.0333, 0.0000, 0.9994 }, + { -0.0333, 0.0000, 0.9994 }, + { -0.0499, 0.0168, 0.9983 }, + { -0.0665, 0.0334, 0.9972 }, + { -0.0829, 0.0331, 0.9959 }, + { -0.0992, 0.0000, 0.9940 }, + { -0.2244, -0.1451, 0.9630 }, + { -0.2539, -0.1595, 0.9535 }, + { -0.2693, -0.1266, 0.9531 }, + { -0.2847, -0.0792, 0.9533 }, + { -0.2698, -0.0159, 0.9586 }, + { -0.2396, 0.0647, 0.9650 }, + { -0.1939, 0.0978, 0.9741 }, + { -0.1470, 0.0981, 0.9831 }, + { -0.0981, 0.1147, 0.9862 }, + { -0.0330, 0.1154, 0.9921 }, + { 0.0000, 0.1163, 0.9925 }, + { 0.0331, 0.1163, 0.9925 }, + { 0.0497, 0.0991, 0.9937 }, + { 0.0332, 0.0662, 0.9967 }, + { 0.0167, 0.0332, 0.9992 }, + { -0.0166, 0.0166, 0.9994 }, + { -0.0665, -0.0166, 0.9975 }, + { -0.1318, -0.0657, 0.9886 }, + { -0.1794, -0.0976, 0.9788 }, + { -0.1633, -0.1140, 0.9798 }, + { -0.1310, -0.1315, 0.9826 }, + { -0.0495, -0.1325, 0.9898 }, + { 0.0494, -0.1153, 0.9907 }, + { 0.1148, -0.0985, 0.9873 }, + { 0.1314, -0.0820, 0.9873 }, + { 0.0991, -0.0664, 0.9923 }, + { 0.0498, -0.0502, 0.9972 }, + { 0.0167, 0.0000, 0.9992 }, + { 0.0000, 0.0498, 0.9986 }, + { -0.0166, 0.0663, 0.9975 }, + { -0.0166, 0.0500, 0.9983 }, + { -0.0167, 0.0168, 0.9994 }, + { -0.0333, 0.0000, 0.9994 }, + { -0.0333, 0.0000, 0.9994 }, + { -0.0499, 0.0000, 0.9986 }, + { -0.0499, 0.0000, 0.9986 }, + { -0.0830, 0.0000, 0.9964 }, + { -0.0995, 0.0000, 0.9950 }, + { -0.1481, -0.0328, 0.9877 }, + { -0.1934, -0.1619, 0.9671 }, + { -0.1927, -0.1776, 0.9644 }, + { -0.1781, -0.1294, 0.9738 }, + { -0.1630, -0.0652, 0.9818 }, + { -0.1146, 0.0164, 0.9887 }, + { -0.0818, 0.0993, 0.9877 }, + { -0.0491, 0.1321, 0.9866 }, + { -0.0164, 0.1474, 0.9854 }, + { 0.0163, 0.1638, 0.9851 }, + { 0.0492, 0.1475, 0.9865 }, + { 0.0658, 0.1323, 0.9885 }, + { 0.0658, 0.1323, 0.9885 }, + { 0.0825, 0.0987, 0.9910 }, + { 0.0498, 0.0497, 0.9972 }, + { 0.0333, 0.0166, 0.9992 }, + { 0.0000, -0.0336, 0.9989 }, + { -0.0497, -0.0831, 0.9950 }, + { -0.1150, -0.1148, 0.9864 }, + { -0.1633, -0.1140, 0.9798 }, + { -0.1794, -0.0976, 0.9788 }, + { -0.1635, -0.0821, 0.9825 }, + { -0.1152, -0.0663, 0.9899 }, + { -0.0496, -0.0497, 0.9962 }, + { -0.0164, -0.0496, 0.9951 }, + { 0.0165, -0.0825, 0.9929 }, + { 0.0166, -0.0998, 0.9936 }, + { 0.0166, -0.0669, 0.9969 }, + { 0.0167, -0.0166, 0.9994 }, + { 0.0000, 0.0166, 0.9997 }, + { -0.0166, 0.0498, 0.9983 }, + { -0.0333, 0.0500, 0.9981 }, + { -0.0333, 0.0168, 0.9992 }, + { -0.0333, 0.0000, 0.9994 }, + { -0.0499, -0.0166, 0.9983 }, + { -0.0665, -0.0166, 0.9975 }, + { -0.0830, -0.0168, 0.9961 }, + { -0.0995, -0.0167, 0.9948 }, + { -0.1318, -0.0329, 0.9897 }, + { -0.1638, -0.0817, 0.9830 }, + { -0.1619, -0.1628, 0.9728 }, + { -0.0977, -0.1479, 0.9819 }, + { -0.0491, -0.0986, 0.9900 }, + { 0.0001, -0.0165, 0.9937 }, + { 0.0494, 0.0659, 0.9926 }, + { 0.0815, 0.1318, 0.9840 }, + { 0.0976, 0.1639, 0.9795 }, + { 0.1139, 0.1627, 0.9789 }, + { 0.1293, 0.1779, 0.9733 }, + { 0.1301, 0.1623, 0.9771 }, + { 0.1308, 0.1315, 0.9821 }, + { 0.1308, 0.1315, 0.9821 }, + { 0.0990, 0.0821, 0.9905 }, + { 0.0830, 0.0166, 0.9961 }, + { 0.0499, -0.0166, 0.9983 }, + { 0.0000, -0.0669, 0.9972 }, + { -0.0330, -0.1322, 0.9902 }, + { -0.0816, -0.1792, 0.9802 }, + { -0.1138, -0.1625, 0.9784 }, + { -0.1468, -0.1141, 0.9812 }, + { -0.1474, -0.0657, 0.9852 }, + { -0.1154, -0.0167, 0.9918 }, + { -0.0830, -0.0166, 0.9961 }, + { -0.0663, -0.0331, 0.9967 }, + { -0.0498, -0.0497, 0.9972 }, + { -0.0332, -0.0667, 0.9972 }, + { -0.0166, -0.0502, 0.9983 }, + { -0.0167, -0.0166, 0.9994 }, + { -0.0167, 0.0166, 0.9994 }, + { -0.0167, 0.0332, 0.9992 }, + { -0.0166, 0.0334, 0.9992 }, + { -0.0333, 0.0168, 0.9992 }, + { -0.0333, -0.0166, 0.9992 }, + { -0.0499, -0.0332, 0.9981 }, + { -0.0665, -0.0332, 0.9972 }, + { -0.0994, -0.0333, 0.9945 }, + { -0.1157, -0.0497, 0.9918 }, + { -0.1479, -0.0656, 0.9867 }, + { -0.1477, -0.0819, 0.9854 }, + { -0.1315, -0.0987, 0.9859 }, + { -0.0663, -0.0666, 0.9950 }, + { 0.0000, -0.0332, 0.9983 }, + { 0.0664, 0.0331, 0.9961 }, + { 0.0989, 0.0985, 0.9891 }, + { 0.1306, 0.1476, 0.9797 }, + { 0.1623, 0.1628, 0.9732 }, + { 0.1775, 0.1769, 0.9678 }, + { 0.1931, 0.1764, 0.9651 }, + { 0.1627, 0.1459, 0.9757 }, + { 0.1631, 0.1309, 0.9779 }, + { 0.1313, 0.0990, 0.9853 }, + { 0.0830, 0.0496, 0.9950 }, + { 0.0664, 0.0000, 0.9967 }, + { 0.0498, -0.0661, 0.9959 }, + { 0.0166, -0.1164, 0.9928 }, + { 0.0164, -0.1644, 0.9845 }, + { 0.0322, -0.1946, 0.9755 }, + { 0.0482, -0.1784, 0.9760 }, + { 0.0479, -0.1300, 0.9789 }, + { 0.0638, -0.0489, 0.9821 }, + { 0.0648, 0.0000, 0.9892 }, + { 0.0648, 0.0000, 0.9892 }, + { 0.0656, -0.0165, 0.9926 }, + { 0.0494, -0.0496, 0.9940 }, + { 0.0493, -0.0665, 0.9931 }, + { 0.0331, -0.0501, 0.9958 }, + { 0.0166, -0.0166, 0.9983 }, + { 0.0000, 0.0166, 0.9992 }, + { -0.0166, 0.0498, 0.9983 }, + { -0.0166, 0.0332, 0.9986 }, + { -0.0333, 0.0000, 0.9994 }, + { -0.0333, -0.0166, 0.9992 }, + { -0.0499, -0.0497, 0.9972 }, + { -0.0664, -0.0662, 0.9956 }, + { -0.0829, -0.0665, 0.9942 }, + { -0.0992, -0.0664, 0.9923 }, + { -0.1157, -0.0659, 0.9910 }, + { -0.1155, -0.0822, 0.9896 }, + { -0.1318, -0.0659, 0.9886 }, + { -0.1158, -0.0167, 0.9929 }, + { -0.0663, 0.0331, 0.9962 }, + { -0.0165, 0.0827, 0.9951 }, + { 0.0330, 0.1315, 0.9897 }, + { 0.0814, 0.1961, 0.9765 }, + { 0.1290, 0.2107, 0.9683 }, + { 0.1611, 0.1930, 0.9674 }, + { 0.1619, 0.1615, 0.9725 }, + { 0.1470, 0.1304, 0.9804 }, + { 0.1149, 0.0987, 0.9867 }, + { 0.0829, 0.0500, 0.9950 }, + { 0.0499, 0.0166, 0.9983 }, + { 0.0167, -0.0166, 0.9994 }, + { 0.0166, -0.0662, 0.9970 }, + { 0.0331, -0.0998, 0.9945 }, + { 0.0661, -0.1159, 0.9909 }, + { 0.1307, -0.1466, 0.9804 }, + { 0.1783, -0.1455, 0.9729 }, + { 0.2257, -0.0965, 0.9684 }, + { 0.2421, -0.0485, 0.9688 }, + { 0.2268, -0.0164, 0.9732 }, + { 0.2268, -0.0162, 0.9732 }, + { 0.1955, -0.0488, 0.9788 }, + { 0.1793, -0.0652, 0.9805 }, + { 0.1477, -0.0825, 0.9853 }, + { 0.1154, -0.0829, 0.9896 }, + { 0.0992, -0.0495, 0.9932 }, + { 0.0664, -0.0166, 0.9970 }, + { 0.0332, 0.0166, 0.9986 }, + { -0.0167, 0.0166, 0.9994 }, + { -0.0333, 0.0000, 0.9994 }, + { -0.0498, -0.0331, 0.9975 }, + { -0.0664, -0.0662, 0.9956 }, + { -0.0664, -0.0662, 0.9956 }, + { -0.0828, -0.0665, 0.9942 }, + { -0.0827, -0.0829, 0.9929 }, + { -0.0827, -0.0825, 0.9929 }, + { -0.0991, -0.0824, 0.9915 }, + { -0.0658, -0.0662, 0.9929 }, + { -0.0493, -0.0002, 0.9948 }, + { -0.0164, 0.0660, 0.9937 }, + { 0.0001, 0.1313, 0.9886 }, + { 0.0326, 0.1951, 0.9792 }, + { 0.0805, 0.2426, 0.9665 }, + { 0.0965, 0.2423, 0.9652 }, + { 0.0971, 0.2100, 0.9722 }, + { 0.0979, 0.1629, 0.9807 }, + { 0.0822, 0.0986, 0.9900 }, + { 0.0498, 0.0667, 0.9964 }, + { 0.0332, 0.0336, 0.9978 }, + { 0.0166, -0.0166, 0.9994 }, + { 0.0000, -0.0332, 0.9994 }, + { 0.0000, -0.0498, 0.9986 }, + { 0.0332, -0.0667, 0.9972 }, + { 0.0498, -0.0667, 0.9964 }, + { 0.0989, -0.0823, 0.9910 }, + { 0.1635, -0.0816, 0.9825 }, + { 0.2105, -0.0648, 0.9743 }, + { 0.2265, -0.0487, 0.9721 }, + { 0.2268, -0.0164, 0.9732 }, + { 0.2107, -0.0324, 0.9753 }, + { 0.1953, -0.0650, 0.9781 }, + { 0.1787, -0.0974, 0.9774 }, + { 0.1470, -0.1312, 0.9803 }, + { 0.1314, -0.0991, 0.9858 }, + { 0.0991, -0.0660, 0.9923 }, + { 0.0663, -0.0497, 0.9959 }, + { 0.0332, -0.0332, 0.9983 }, + { -0.0167, -0.0334, 0.9992 }, + { -0.0499, -0.0334, 0.9981 }, + { -0.0829, -0.0496, 0.9950 }, + { -0.0828, -0.0661, 0.9942 }, + { -0.0827, -0.0825, 0.9929 }, + { -0.0991, -0.0828, 0.9915 }, + { -0.0993, -0.0665, 0.9928 }, + { -0.0827, -0.0825, 0.9929 }, + { -0.0827, -0.0825, 0.9929 }, + { 0.0660, -0.0165, 0.9953 }, + { 0.1145, 0.0328, 0.9890 }, + { 0.1308, 0.0819, 0.9857 }, + { 0.1455, 0.1298, 0.9770 }, + { 0.1282, 0.2083, 0.9664 }, + { 0.1119, 0.2570, 0.9598 }, + { 0.0968, 0.2268, 0.9685 }, + { 0.0652, 0.1952, 0.9786 }, + { 0.0329, 0.1473, 0.9868 }, + { 0.0000, 0.0828, 0.9959 }, + { 0.0000, 0.0500, 0.9981 }, + { -0.0166, 0.0168, 0.9994 }, + { -0.0166, -0.0166, 0.9994 }, + { -0.0166, -0.0332, 0.9992 }, + { -0.0166, -0.0332, 0.9992 }, + { 0.0000, -0.0502, 0.9980 }, + { 0.0166, -0.0502, 0.9983 }, + { 0.0499, -0.0332, 0.9981 }, + { 0.0827, -0.0331, 0.9948 }, + { 0.1154, -0.0330, 0.9915 }, + { 0.1313, -0.0331, 0.9886 }, + { 0.1313, -0.0331, 0.9886 }, + { 0.1153, -0.0494, 0.9907 }, + { 0.1151, -0.0821, 0.9886 }, + { 0.0822, -0.1150, 0.9886 }, + { 0.0491, -0.1321, 0.9866 }, + { 0.0163, -0.1318, 0.9845 }, + { -0.0325, -0.1149, 0.9878 }, + { -0.0652, -0.0822, 0.9894 }, + { -0.0819, -0.0659, 0.9911 }, + { -0.0825, -0.0665, 0.9931 }, + { -0.0828, -0.0665, 0.9942 }, + { -0.0993, -0.0660, 0.9929 }, + { -0.0993, -0.0660, 0.9929 }, + { -0.0991, -0.0824, 0.9915 }, + { -0.0991, -0.0828, 0.9915 }, + { -0.0993, -0.0665, 0.9928 }, + { -0.0993, -0.0660, 0.9929 }, + { -0.0989, -0.0823, 0.9910 }, + { 0.1638, 0.0658, 0.9838 }, + { 0.2112, 0.0653, 0.9751 }, + { 0.2257, 0.0965, 0.9684 }, + { 0.2404, 0.1279, 0.9621 }, + { 0.2239, 0.1595, 0.9605 }, + { 0.1605, 0.2097, 0.9638 }, + { 0.0975, 0.1958, 0.9752 }, + { 0.0493, 0.1477, 0.9875 }, + { 0.0000, 0.0991, 0.9945 }, + { -0.0332, 0.0663, 0.9972 }, + { -0.0499, 0.0499, 0.9972 }, + { -0.0499, 0.0168, 0.9983 }, + { -0.0499, -0.0166, 0.9983 }, + { -0.0499, -0.0332, 0.9981 }, + { -0.0499, -0.0332, 0.9981 }, + { -0.0333, -0.0334, 0.9989 }, + { -0.0167, -0.0168, 0.9994 }, + { 0.0000, -0.0166, 0.9992 }, + { 0.0166, -0.0166, 0.9994 }, + { 0.0332, -0.0166, 0.9986 }, + { 0.0499, -0.0334, 0.9981 }, + { 0.0499, -0.0334, 0.9981 }, + { 0.0332, -0.0497, 0.9975 }, + { 0.0165, -0.0990, 0.9932 }, + { 0.0000, -0.1636, 0.9854 }, + { -0.0489, -0.1966, 0.9791 }, + { -0.1139, -0.1798, 0.9768 }, + { -0.1467, -0.1463, 0.9780 }, + { -0.1793, -0.0975, 0.9783 }, + { -0.1642, -0.0491, 0.9851 }, + { -0.1321, -0.0332, 0.9907 }, + { -0.0994, -0.0498, 0.9937 }, + { -0.0828, -0.0661, 0.9942 }, + { -0.0828, -0.0661, 0.9942 }, + { -0.0991, -0.0824, 0.9915 }, + { -0.0827, -0.0829, 0.9929 }, + { -0.0993, -0.0665, 0.9928 }, + { -0.0991, -0.0824, 0.9915 }, + { -0.1315, -0.0984, 0.9864 }, + { 0.1953, 0.0980, 0.9758 }, + { 0.2108, 0.0976, 0.9725 }, + { 0.2410, 0.1121, 0.9638 }, + { 0.2252, 0.1284, 0.9653 }, + { 0.2094, 0.1288, 0.9682 }, + { 0.1466, 0.1311, 0.9793 }, + { 0.0660, 0.1161, 0.9903 }, + { 0.0166, 0.0992, 0.9948 }, + { -0.0166, 0.0662, 0.9970 }, + { -0.0333, 0.0332, 0.9989 }, + { -0.0499, 0.0334, 0.9981 }, + { -0.0665, 0.0168, 0.9975 }, + { -0.0665, -0.0166, 0.9975 }, + { -0.0499, -0.0332, 0.9981 }, + { -0.0499, -0.0166, 0.9983 }, + { -0.0333, -0.0168, 0.9992 }, + { -0.0333, -0.0168, 0.9992 }, + { -0.0333, 0.0000, 0.9994 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0167, -0.0168, 0.9994 }, + { 0.0166, -0.0500, 0.9983 }, + { -0.0166, -0.0828, 0.9962 }, + { -0.0331, -0.1155, 0.9926 }, + { -0.0491, -0.1790, 0.9813 }, + { -0.0806, -0.2426, 0.9665 }, + { -0.1288, -0.2260, 0.9650 }, + { -0.1619, -0.1774, 0.9706 }, + { -0.1631, -0.0972, 0.9791 }, + { -0.1483, -0.0164, 0.9885 }, + { -0.1159, 0.0000, 0.9931 }, + { -0.0830, -0.0166, 0.9961 }, + { -0.0665, -0.0497, 0.9964 }, + { -0.0498, -0.0827, 0.9951 }, + { -0.0662, -0.0826, 0.9937 }, + { -0.0498, -0.0833, 0.9950 }, + { -0.0662, -0.0832, 0.9936 }, + { -0.0826, -0.0987, 0.9910 }, + { -0.0985, -0.1311, 0.9859 }, + { 0.1786, 0.1301, 0.9746 }, + { 0.1948, 0.1140, 0.9741 }, + { 0.1945, 0.1133, 0.9737 }, + { 0.1634, 0.0979, 0.9812 }, + { 0.1315, 0.0820, 0.9872 }, + { 0.0993, 0.0665, 0.9928 }, + { 0.0498, 0.0667, 0.9964 }, + { 0.0166, 0.0663, 0.9975 }, + { -0.0333, 0.0498, 0.9981 }, + { -0.0333, 0.0332, 0.9989 }, + { -0.0499, 0.0166, 0.9983 }, + { -0.0499, 0.0000, 0.9986 }, + { -0.0499, 0.0000, 0.9986 }, + { -0.0333, -0.0166, 0.9992 }, + { -0.0333, -0.0166, 0.9992 }, + { -0.0333, -0.0168, 0.9992 }, + { -0.0333, -0.0168, 0.9992 }, + { -0.0167, 0.0166, 0.9994 }, + { 0.0000, 0.0166, 0.9997 }, + { 0.0000, 0.0000, 1.0000 }, + { -0.0166, -0.0168, 0.9994 }, + { -0.0331, -0.0664, 0.9962 }, + { -0.0496, -0.0991, 0.9937 }, + { -0.0658, -0.1313, 0.9881 }, + { -0.0970, -0.2094, 0.9713 }, + { -0.1114, -0.2718, 0.9556 }, + { -0.1432, -0.2557, 0.9554 }, + { -0.1616, -0.1769, 0.9697 }, + { -0.1476, -0.0816, 0.9843 }, + { -0.1321, 0.0000, 0.9907 }, + { -0.0994, 0.0333, 0.9945 }, + { -0.0829, 0.0002, 0.9959 }, + { -0.0499, -0.0332, 0.9981 }, + { -0.0332, -0.0662, 0.9967 }, + { -0.0166, -0.0828, 0.9962 }, + { -0.0166, -0.0834, 0.9961 }, + { -0.0166, -0.0999, 0.9947 }, + { -0.0331, -0.1154, 0.9921 }, + { -0.0492, -0.1635, 0.9846 }, + { 0.1783, 0.1464, 0.9728 }, + { 0.1790, 0.1145, 0.9769 }, + { 0.1477, 0.0819, 0.9854 }, + { 0.1319, 0.0658, 0.9891 }, + { 0.1156, 0.0659, 0.9910 }, + { 0.0829, 0.0498, 0.9950 }, + { 0.0499, 0.0334, 0.9981 }, + { 0.0166, 0.0166, 0.9994 }, + { -0.0166, 0.0166, 0.9994 }, + { -0.0333, 0.0166, 0.9992 }, + { -0.0332, 0.0168, 0.9986 }, + { -0.0333, 0.0168, 0.9992 }, + { -0.0333, 0.0000, 0.9994 }, + { -0.0333, -0.0166, 0.9992 }, + { -0.0333, -0.0166, 0.9992 }, + { -0.0333, -0.0168, 0.9992 }, + { -0.0166, -0.0002, 0.9992 }, + { -0.0167, 0.0332, 0.9992 }, + { -0.0167, 0.0166, 0.9994 }, + { -0.0167, -0.0166, 0.9994 }, + { -0.0333, -0.0502, 0.9980 }, + { -0.0663, -0.0830, 0.9942 }, + { -0.0661, -0.1153, 0.9910 }, + { -0.0981, -0.1629, 0.9812 }, + { -0.1287, -0.2245, 0.9654 }, + { -0.1420, -0.2852, 0.9472 }, + { -0.1581, -0.2695, 0.9487 }, + { -0.1616, -0.1769, 0.9697 }, + { -0.1637, -0.0650, 0.9822 }, + { -0.1481, 0.0328, 0.9877 }, + { -0.1157, 0.0497, 0.9918 }, + { -0.0994, 0.0333, 0.9945 }, + { -0.0499, 0.0000, 0.9981 }, + { -0.0499, -0.0497, 0.9972 }, + { -0.0166, -0.0663, 0.9975 }, + { -0.0166, -0.0834, 0.9961 }, + { 0.0000, -0.0999, 0.9950 }, + { 0.0000, -0.1316, 0.9908 }, + { -0.0164, -0.1798, 0.9833 }, + { 0.1302, 0.1309, 0.9802 }, + { 0.0985, 0.0829, 0.9894 }, + { 0.0660, 0.0661, 0.9934 }, + { 0.0660, 0.0661, 0.9934 }, + { 0.0494, 0.0330, 0.9942 }, + { 0.0166, 0.0000, 0.9986 }, + { 0.0000, 0.0000, 0.9994 }, + { -0.0166, 0.0000, 0.9997 }, + { -0.0166, 0.0000, 0.9997 }, + { -0.0333, 0.0166, 0.9992 }, + { -0.0166, 0.0166, 0.9994 }, + { -0.0167, 0.0000, 0.9997 }, + { -0.0167, 0.0000, 0.9997 }, + { -0.0167, -0.0166, 0.9994 }, + { -0.0167, -0.0166, 0.9994 }, + { -0.0167, 0.0000, 0.9997 }, + { -0.0166, 0.0000, 0.9997 }, + { -0.0167, 0.0166, 0.9994 }, + { -0.0333, 0.0166, 0.9992 }, + { -0.0333, -0.0166, 0.9992 }, + { -0.0332, -0.0668, 0.9966 }, + { -0.0662, -0.0997, 0.9928 }, + { -0.0822, -0.1312, 0.9873 }, + { -0.0975, -0.1944, 0.9755 }, + { -0.1119, -0.2550, 0.9598 }, + { -0.1259, -0.3004, 0.9448 }, + { -0.1269, -0.2706, 0.9526 }, + { -0.1297, -0.1776, 0.9738 }, + { -0.1476, -0.0652, 0.9846 }, + { -0.1316, 0.0492, 0.9883 }, + { -0.1154, 0.0827, 0.9896 }, + { -0.0993, 0.0665, 0.9928 }, + { -0.0992, 0.0165, 0.9932 }, + { -0.0829, -0.0331, 0.9959 }, + { -0.0826, -0.0496, 0.9940 }, + { -0.0662, -0.0666, 0.9950 }, + { -0.0495, -0.0830, 0.9940 }, + { -0.0492, -0.1313, 0.9884 }, + { -0.0327, -0.1796, 0.9825 }, + { -0.0165, 0.0829, 0.9928 }, + { -0.0494, 0.0500, 0.9939 }, + { -0.0660, 0.0496, 0.9942 }, + { -0.0821, 0.0494, 0.9918 }, + { -0.0989, 0.0165, 0.9926 }, + { -0.0828, 0.0000, 0.9953 }, + { -0.0664, 0.0000, 0.9972 }, + { -0.0499, 0.0000, 0.9986 }, + { -0.0333, 0.0000, 0.9994 }, + { -0.0333, 0.0166, 0.9992 }, + { -0.0333, 0.0334, 0.9989 }, + { -0.0167, 0.0168, 0.9994 }, + { -0.0167, 0.0000, 0.9997 }, + { -0.0167, -0.0166, 0.9994 }, + { -0.0167, -0.0166, 0.9994 }, + { -0.0167, -0.0168, 0.9994 }, + { -0.0166, -0.0002, 0.9992 }, + { -0.0167, 0.0166, 0.9994 }, + { -0.0333, 0.0000, 0.9994 }, + { -0.0333, -0.0166, 0.9992 }, + { -0.0497, -0.0833, 0.9939 }, + { -0.0495, -0.1325, 0.9898 }, + { -0.0821, -0.1474, 0.9854 }, + { -0.0975, -0.1944, 0.9755 }, + { -0.0961, -0.2555, 0.9615 }, + { -0.0791, -0.3020, 0.9498 }, + { -0.0638, -0.2723, 0.9584 }, + { -0.0651, -0.1948, 0.9776 }, + { -0.0821, -0.0651, 0.9884 }, + { -0.0828, 0.0660, 0.9937 }, + { -0.0827, 0.0829, 0.9929 }, + { -0.0993, 0.0500, 0.9937 }, + { -0.1158, 0.0165, 0.9929 }, + { -0.1157, -0.0329, 0.9921 }, + { -0.1481, -0.0492, 0.9875 }, + { -0.1476, -0.0496, 0.9864 }, + { -0.1473, -0.0822, 0.9843 }, + { -0.1468, -0.1141, 0.9812 }, + { -0.1299, -0.1463, 0.9784 }, + { -0.0664, 0.0168, 0.9970 }, + { -0.1158, 0.0332, 0.9926 }, + { -0.1483, 0.0329, 0.9883 }, + { -0.1803, 0.0327, 0.9829 }, + { -0.1803, 0.0327, 0.9829 }, + { -0.1642, 0.0330, 0.9854 }, + { -0.1158, 0.0332, 0.9926 }, + { -0.0830, 0.0331, 0.9959 }, + { -0.0499, 0.0166, 0.9983 }, + { -0.0333, 0.0166, 0.9992 }, + { -0.0333, 0.0334, 0.9989 }, + { -0.0333, 0.0168, 0.9992 }, + { -0.0333, 0.0000, 0.9994 }, + { -0.0333, -0.0166, 0.9992 }, + { -0.0333, -0.0166, 0.9992 }, + { -0.0333, 0.0000, 0.9994 }, + { -0.0167, 0.0000, 0.9997 }, + { -0.0333, 0.0000, 0.9994 }, + { -0.0333, 0.0000, 0.9994 }, + { -0.0499, -0.0331, 0.9975 }, + { -0.0498, -0.0833, 0.9950 }, + { -0.0495, -0.1321, 0.9893 }, + { -0.0655, -0.1794, 0.9815 }, + { -0.0812, -0.2104, 0.9740 }, + { -0.0645, -0.2412, 0.9677 }, + { -0.0480, -0.2732, 0.9605 }, + { -0.0161, -0.2583, 0.9652 }, + { 0.0000, -0.1952, 0.9797 }, + { 0.0000, -0.0819, 0.9927 }, + { -0.0166, 0.0496, 0.9962 }, + { -0.0498, 0.0664, 0.9959 }, + { -0.0830, 0.0333, 0.9959 }, + { -0.0995, 0.0000, 0.9945 }, + { -0.1480, -0.0655, 0.9861 }, + { -0.1797, -0.0814, 0.9801 }, + { -0.2114, -0.0653, 0.9751 }, + { -0.2263, -0.0810, 0.9701 }, + { -0.2256, -0.1125, 0.9671 }, + { -0.2096, -0.1446, 0.9668 }, + { -0.0333, -0.0168, 0.9992 }, + { -0.0830, -0.0333, 0.9959 }, + { -0.1319, -0.0165, 0.9904 }, + { -0.1802, 0.0163, 0.9832 }, + { -0.1960, 0.0326, 0.9801 }, + { -0.1798, 0.0658, 0.9808 }, + { -0.1477, 0.0825, 0.9853 }, + { -0.1156, 0.0659, 0.9910 }, + { -0.0829, 0.0496, 0.9951 }, + { -0.0499, 0.0332, 0.9981 }, + { -0.0333, 0.0334, 0.9989 }, + { -0.0333, 0.0168, 0.9992 }, + { -0.0333, 0.0000, 0.9994 }, + { -0.0333, -0.0166, 0.9992 }, + { -0.0333, -0.0166, 0.9992 }, + { -0.0333, 0.0000, 0.9994 }, + { -0.0499, 0.0000, 0.9986 }, + { -0.0333, 0.0000, 0.9994 }, + { -0.0333, -0.0166, 0.9992 }, + { -0.0499, -0.0332, 0.9981 }, + { -0.0497, -0.0833, 0.9939 }, + { -0.0658, -0.1484, 0.9866 }, + { -0.0816, -0.1792, 0.9802 }, + { -0.0652, -0.1952, 0.9786 }, + { -0.0646, -0.2257, 0.9710 }, + { -0.0482, -0.2583, 0.9647 }, + { -0.0162, -0.2278, 0.9729 }, + { 0.0000, -0.1797, 0.9830 }, + { 0.0166, -0.0820, 0.9930 }, + { 0.0000, 0.0166, 0.9992 }, + { -0.0499, 0.0166, 0.9983 }, + { -0.0665, 0.0000, 0.9978 }, + { -0.1155, -0.0493, 0.9907 }, + { -0.1790, -0.1137, 0.9770 }, + { -0.2254, -0.1125, 0.9671 }, + { -0.2704, -0.0961, 0.9568 }, + { -0.2995, -0.0952, 0.9483 }, + { -0.2856, -0.0951, 0.9531 }, + { -0.2408, -0.1121, 0.9638 }, + { -0.0499, -0.0170, 0.9972 }, + { -0.0664, -0.0666, 0.9956 }, + { -0.0993, -0.0660, 0.9929 }, + { -0.1481, -0.0328, 0.9878 }, + { -0.1639, 0.0327, 0.9849 }, + { -0.1477, 0.0825, 0.9853 }, + { -0.1313, 0.0990, 0.9859 }, + { -0.1152, 0.0986, 0.9883 }, + { -0.0991, 0.0824, 0.9915 }, + { -0.0664, 0.0662, 0.9956 }, + { -0.0333, 0.0500, 0.9981 }, + { -0.0333, 0.0168, 0.9992 }, + { -0.0166, 0.0000, 0.9997 }, + { -0.0333, -0.0166, 0.9992 }, + { -0.0333, -0.0166, 0.9992 }, + { -0.0499, -0.0168, 0.9983 }, + { -0.0499, -0.0002, 0.9981 }, + { -0.0499, 0.0166, 0.9983 }, + { -0.0499, -0.0166, 0.9983 }, + { -0.0499, -0.0497, 0.9972 }, + { -0.0661, -0.0997, 0.9922 }, + { -0.0818, -0.1640, 0.9824 }, + { -0.0979, -0.1789, 0.9788 }, + { -0.1132, -0.1938, 0.9728 }, + { -0.1129, -0.2252, 0.9676 }, + { -0.1125, -0.2264, 0.9663 }, + { -0.0967, -0.2111, 0.9704 }, + { -0.1132, -0.1621, 0.9764 }, + { -0.0977, -0.0817, 0.9858 }, + { -0.0989, -0.0165, 0.9926 }, + { -0.1155, 0.0000, 0.9921 }, + { -0.1312, -0.0328, 0.9881 }, + { -0.1629, -0.1136, 0.9784 }, + { -0.2083, -0.1758, 0.9619 }, + { -0.2683, -0.1732, 0.9474 }, + { -0.3130, -0.1413, 0.9391 }, + { -0.3285, -0.0944, 0.9391 }, + { -0.3014, -0.0475, 0.9521 }, + { -0.2575, -0.0321, 0.9657 }, + { -0.0828, -0.0004, 0.9942 }, + { -0.0663, -0.0830, 0.9942 }, + { -0.0990, -0.0988, 0.9902 }, + { -0.0991, -0.0494, 0.9921 }, + { -0.0992, 0.0330, 0.9934 }, + { -0.0823, 0.0995, 0.9898 }, + { -0.0660, 0.1161, 0.9903 }, + { -0.0495, 0.0990, 0.9926 }, + { -0.0495, 0.0990, 0.9926 }, + { -0.0331, 0.0991, 0.9940 }, + { -0.0332, 0.0664, 0.9967 }, + { -0.0333, 0.0334, 0.9989 }, + { -0.0166, 0.0000, 0.9992 }, + { -0.0333, -0.0332, 0.9989 }, + { -0.0333, -0.0332, 0.9989 }, + { -0.0499, -0.0166, 0.9983 }, + { -0.0499, 0.0000, 0.9986 }, + { -0.0665, 0.0000, 0.9978 }, + { -0.0499, -0.0166, 0.9983 }, + { -0.0499, -0.0497, 0.9972 }, + { -0.0660, -0.1160, 0.9898 }, + { -0.0979, -0.1800, 0.9787 }, + { -0.1132, -0.2098, 0.9709 }, + { -0.1607, -0.2084, 0.9646 }, + { -0.1899, -0.2218, 0.9539 }, + { -0.2049, -0.2378, 0.9482 }, + { -0.2344, -0.2210, 0.9436 }, + { -0.2520, -0.1731, 0.9490 }, + { -0.2690, -0.0633, 0.9559 }, + { -0.2678, 0.0000, 0.9575 }, + { -0.2402, -0.0163, 0.9673 }, + { -0.2414, -0.0485, 0.9680 }, + { -0.2392, -0.1271, 0.9594 }, + { -0.2650, -0.2180, 0.9377 }, + { -0.2803, -0.2173, 0.9345 }, + { -0.3121, -0.1564, 0.9366 }, + { -0.3148, -0.0792, 0.9446 }, + { -0.2872, -0.0159, 0.9576 }, + { -0.2576, 0.0000, 0.9662 }, + { -0.1155, 0.0326, 0.9904 }, + { -0.0826, -0.0825, 0.9918 }, + { -0.0494, -0.0988, 0.9921 }, + { -0.0165, -0.0331, 0.9975 }, + { 0.0001, 0.0495, 0.9953 }, + { 0.0165, 0.1162, 0.9917 }, + { 0.0165, 0.1325, 0.9898 }, + { 0.0331, 0.1154, 0.9921 }, + { 0.0331, 0.0991, 0.9940 }, + { 0.0166, 0.0828, 0.9962 }, + { -0.0166, 0.0500, 0.9983 }, + { -0.0166, 0.0334, 0.9992 }, + { -0.0333, 0.0000, 0.9989 }, + { -0.0333, -0.0332, 0.9989 }, + { -0.0333, -0.0332, 0.9989 }, + { -0.0499, -0.0334, 0.9981 }, + { -0.0665, -0.0168, 0.9975 }, + { -0.0665, 0.0166, 0.9975 }, + { -0.0664, 0.0000, 0.9967 }, + { -0.0662, -0.0661, 0.9945 }, + { -0.0820, -0.1482, 0.9842 }, + { -0.1132, -0.2110, 0.9707 }, + { -0.1439, -0.2393, 0.9600 }, + { -0.1887, -0.2668, 0.9445 }, + { -0.2338, -0.2643, 0.9354 }, + { -0.2768, -0.2628, 0.9237 }, + { -0.3200, -0.2448, 0.9146 }, + { -0.3378, -0.1838, 0.9222 }, + { -0.3686, -0.0917, 0.9226 }, + { -0.3709, 0.0154, 0.9274 }, + { -0.3434, 0.0311, 0.9377 }, + { -0.3290, -0.0313, 0.9422 }, + { -0.3118, -0.1392, 0.9363 }, + { -0.3087, -0.2156, 0.9264 }, + { -0.2946, -0.2166, 0.9306 }, + { -0.2969, -0.1720, 0.9381 }, + { -0.3005, -0.0637, 0.9494 }, + { -0.2872, 0.0159, 0.9576 }, + { -0.2575, 0.0321, 0.9657 }, + { -0.1156, 0.0493, 0.9907 }, + { -0.0664, -0.0166, 0.9970 }, + { 0.0333, -0.0332, 0.9983 }, + { 0.1147, 0.0000, 0.9895 }, + { 0.1466, 0.0653, 0.9832 }, + { 0.1460, 0.1148, 0.9791 }, + { 0.1303, 0.1313, 0.9806 }, + { 0.0987, 0.1149, 0.9878 }, + { 0.0828, 0.0825, 0.9929 }, + { 0.0333, 0.0498, 0.9981 }, + { 0.0000, 0.0334, 0.9994 }, + { -0.0167, 0.0168, 0.9994 }, + { -0.0333, -0.0166, 0.9992 }, + { -0.0333, -0.0332, 0.9989 }, + { -0.0499, -0.0497, 0.9972 }, + { -0.0665, -0.0499, 0.9964 }, + { -0.0665, -0.0168, 0.9975 }, + { -0.0831, 0.0000, 0.9964 }, + { -0.1159, -0.0165, 0.9929 }, + { -0.1317, -0.0656, 0.9880 }, + { -0.1300, -0.1629, 0.9753 }, + { -0.1440, -0.2407, 0.9596 }, + { -0.1730, -0.2819, 0.9431 }, + { -0.1872, -0.2956, 0.9362 }, + { -0.2014, -0.3086, 0.9290 }, + { -0.2576, -0.3198, 0.9106 }, + { -0.3037, -0.2744, 0.9114 }, + { -0.3497, -0.2120, 0.9119 }, + { -0.3680, -0.0910, 0.9204 }, + { -0.3712, 0.0308, 0.9275 }, + { -0.3712, 0.0308, 0.9275 }, + { -0.3579, -0.0155, 0.9334 }, + { -0.3414, -0.1076, 0.9306 }, + { -0.3099, -0.2008, 0.9292 }, + { -0.2957, -0.2017, 0.9335 }, + { -0.2838, -0.1578, 0.9453 }, + { -0.2863, -0.0640, 0.9538 }, + { -0.2872, 0.0318, 0.9568 }, + { -0.2721, 0.0638, 0.9600 }, + { -0.1314, 0.0825, 0.9872 }, + { -0.0498, 0.0667, 0.9964 }, + { 0.0497, 0.0827, 0.9951 }, + { 0.1309, 0.0819, 0.9857 }, + { 0.1951, 0.0812, 0.9768 }, + { 0.1788, 0.0982, 0.9778 }, + { 0.1473, 0.0824, 0.9843 }, + { 0.0826, 0.0660, 0.9932 }, + { 0.0331, 0.0331, 0.9961 }, + { 0.0000, 0.0000, 0.9994 }, + { 0.0166, 0.0000, 0.9997 }, + { -0.0167, 0.0000, 0.9997 }, + { -0.0333, -0.0166, 0.9992 }, + { -0.0498, -0.0497, 0.9972 }, + { -0.0664, -0.0662, 0.9956 }, + { -0.0664, -0.0499, 0.9964 }, + { -0.0829, -0.0333, 0.9959 }, + { -0.1157, -0.0330, 0.9926 }, + { -0.1480, -0.0492, 0.9875 }, + { -0.1638, -0.0817, 0.9830 }, + { -0.1775, -0.1618, 0.9684 }, + { -0.1742, -0.2541, 0.9508 }, + { -0.1729, -0.2823, 0.9435 }, + { -0.1415, -0.2980, 0.9438 }, + { -0.1544, -0.3388, 0.9272 }, + { -0.1672, -0.3670, 0.9139 }, + { -0.2127, -0.3366, 0.9148 }, + { -0.2461, -0.2467, 0.9310 }, + { -0.2832, -0.1096, 0.9476 }, + { -0.3141, 0.0157, 0.9462 }, + { -0.3141, 0.0474, 0.9462 }, + { -0.3156, 0.0002, 0.9479 }, + { -0.3138, -0.0936, 0.9423 }, + { -0.2826, -0.1724, 0.9430 }, + { -0.2822, -0.1877, 0.9408 }, + { -0.2689, -0.1585, 0.9494 }, + { -0.2562, -0.0645, 0.9618 }, + { -0.2722, 0.0319, 0.9611 }, + { -0.2719, 0.0638, 0.9601 }, + { -0.1471, 0.1149, 0.9810 }, + { -0.0980, 0.1642, 0.9810 }, + { -0.0165, 0.1477, 0.9875 }, + { 0.0329, 0.1477, 0.9878 }, + { 0.0815, 0.1144, 0.9855 }, + { 0.0825, 0.0665, 0.9931 }, + { 0.0496, 0.0335, 0.9964 }, + { 0.0166, 0.0000, 0.9997 }, + { -0.0166, 0.0000, 0.9997 }, + { -0.0166, 0.0332, 0.9986 }, + { 0.0000, 0.0163, 0.9981 }, + { -0.0167, -0.0334, 0.9992 }, + { -0.0499, -0.0497, 0.9972 }, + { -0.0664, -0.0662, 0.9956 }, + { -0.0664, -0.0662, 0.9956 }, + { -0.0664, -0.0666, 0.9956 }, + { -0.0993, -0.0665, 0.9928 }, + { -0.1156, -0.0659, 0.9910 }, + { -0.1479, -0.0656, 0.9867 }, + { -0.1635, -0.0978, 0.9812 }, + { -0.1771, -0.1778, 0.9666 }, + { -0.1593, -0.2400, 0.9570 }, + { -0.1434, -0.2544, 0.9563 }, + { -0.1266, -0.2840, 0.9500 }, + { -0.1088, -0.3409, 0.9332 }, + { -0.0917, -0.3840, 0.9181 }, + { -0.0767, -0.3562, 0.9270 }, + { -0.0787, -0.2845, 0.9517 }, + { -0.1116, -0.1597, 0.9697 }, + { -0.1451, 0.0000, 0.9808 }, + { -0.1946, 0.0325, 0.9777 }, + { -0.2416, -0.0161, 0.9690 }, + { -0.2713, -0.0794, 0.9579 }, + { -0.2681, -0.1727, 0.9465 }, + { -0.2675, -0.1882, 0.9444 }, + { -0.2403, -0.1284, 0.9616 }, + { -0.2418, -0.0649, 0.9675 }, + { -0.2573, 0.0160, 0.9650 }, + { -0.2721, 0.0479, 0.9608 }, + { -0.0986, 0.1156, 0.9866 }, + { -0.0811, 0.1955, 0.9756 }, + { -0.0488, 0.2109, 0.9760 }, + { 0.0000, 0.1798, 0.9836 }, + { 0.0165, 0.1316, 0.9905 }, + { 0.0332, 0.0664, 0.9967 }, + { 0.0000, 0.0168, 0.9997 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, 0.0166, 0.9997 }, + { -0.0499, -0.0002, 0.9981 }, + { -0.0498, -0.0499, 0.9972 }, + { -0.0498, -0.0663, 0.9964 }, + { -0.0498, -0.0663, 0.9964 }, + { -0.0664, -0.0662, 0.9956 }, + { -0.0663, -0.0833, 0.9942 }, + { -0.0662, -0.0832, 0.9936 }, + { -0.0827, -0.0825, 0.9929 }, + { -0.0989, -0.0987, 0.9896 }, + { -0.1311, -0.1145, 0.9841 }, + { -0.1301, -0.1635, 0.9768 }, + { -0.1128, -0.2261, 0.9670 }, + { -0.1120, -0.2554, 0.9602 }, + { -0.1115, -0.2701, 0.9561 }, + { -0.0944, -0.3137, 0.9444 }, + { -0.0469, -0.3450, 0.9373 }, + { 0.0157, -0.3314, 0.9431 }, + { 0.0318, -0.2860, 0.9567 }, + { 0.0326, -0.1780, 0.9797 }, + { -0.0166, -0.0662, 0.9970 }, + { -0.1157, -0.0499, 0.9918 }, + { -0.1954, -0.0816, 0.9772 }, + { -0.2554, -0.1273, 0.9579 }, + { -0.2683, -0.1732, 0.9474 }, + { -0.2392, -0.1590, 0.9572 }, + { -0.2253, -0.1293, 0.9657 }, + { -0.2413, -0.0809, 0.9657 }, + { -0.2423, 0.0000, 0.9695 }, + { -0.2723, 0.0320, 0.9615 }, + { 0.0001, 0.1319, 0.9868 }, + { 0.0163, 0.2121, 0.9758 }, + { 0.0162, 0.2264, 0.9727 }, + { 0.0325, 0.2109, 0.9763 }, + { 0.0656, 0.1470, 0.9852 }, + { 0.0166, 0.0496, 0.9973 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, 0.0000, 1.0000 }, + { -0.0167, -0.0166, 0.9994 }, + { -0.0499, -0.0334, 0.9981 }, + { -0.0499, -0.0334, 0.9981 }, + { -0.0333, -0.0498, 0.9981 }, + { -0.0332, -0.0828, 0.9959 }, + { -0.0497, -0.0827, 0.9951 }, + { -0.0498, -0.0667, 0.9964 }, + { -0.0332, -0.0832, 0.9959 }, + { -0.0497, -0.0991, 0.9937 }, + { -0.0496, -0.1154, 0.9918 }, + { -0.0658, -0.1315, 0.9886 }, + { -0.0818, -0.1644, 0.9823 }, + { -0.0969, -0.2265, 0.9687 }, + { -0.1120, -0.2554, 0.9602 }, + { -0.1115, -0.2701, 0.9561 }, + { -0.1110, -0.2849, 0.9520 }, + { -0.0793, -0.2872, 0.9534 }, + { -0.0629, -0.2865, 0.9513 }, + { -0.0472, -0.2699, 0.9552 }, + { -0.0634, -0.2083, 0.9663 }, + { -0.0971, -0.1465, 0.9795 }, + { -0.1616, -0.1467, 0.9736 }, + { -0.1935, -0.1619, 0.9676 }, + { -0.2239, -0.1597, 0.9609 }, + { -0.2239, -0.1597, 0.9609 }, + { -0.2094, -0.1446, 0.9668 }, + { -0.2253, -0.1293, 0.9657 }, + { -0.2107, -0.0815, 0.9728 }, + { -0.2271, -0.0162, 0.9736 }, + { -0.2424, 0.0000, 0.9701 }, + { 0.0982, 0.1479, 0.9823 }, + { 0.0972, 0.2113, 0.9719 }, + { 0.0969, 0.2255, 0.9689 }, + { 0.0969, 0.2255, 0.9689 }, + { 0.0491, 0.1131, 0.9846 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, -0.0166, 0.9997 }, + { -0.0333, -0.0332, 0.9989 }, + { -0.0333, -0.0334, 0.9989 }, + { -0.0499, -0.0334, 0.9981 }, + { -0.0499, -0.0497, 0.9972 }, + { -0.0498, -0.0827, 0.9951 }, + { -0.0332, -0.0828, 0.9959 }, + { -0.0333, -0.0667, 0.9972 }, + { -0.0332, -0.0832, 0.9959 }, + { -0.0332, -0.0992, 0.9945 }, + { -0.0496, -0.1154, 0.9918 }, + { -0.0494, -0.1477, 0.9875 }, + { -0.0652, -0.1963, 0.9778 }, + { -0.0962, -0.2569, 0.9612 }, + { -0.1116, -0.2701, 0.9561 }, + { -0.1273, -0.2696, 0.9544 }, + { -0.1268, -0.2843, 0.9503 }, + { -0.1567, -0.2991, 0.9406 }, + { -0.1871, -0.2975, 0.9356 }, + { -0.2027, -0.2804, 0.9371 }, + { -0.2211, -0.2197, 0.9477 }, + { -0.2241, -0.1597, 0.9609 }, + { -0.2095, -0.1454, 0.9667 }, + { -0.1784, -0.1464, 0.9728 }, + { -0.1621, -0.1617, 0.9729 }, + { -0.1621, -0.1617, 0.9729 }, + { -0.1780, -0.1613, 0.9706 }, + { -0.2099, -0.1293, 0.9685 }, + { -0.2111, -0.0816, 0.9738 }, + { -0.2271, -0.0323, 0.9728 }, + { -0.2274, 0.0000, 0.9738 }, + { 0.1775, 0.1462, 0.9708 }, + { 0.1604, 0.2095, 0.9639 }, + { 0.1445, 0.2243, 0.9636 }, + { 0.1141, 0.1619, 0.9780 }, + { 0.0000, 0.0496, 0.9975 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, -0.0332, 0.9989 }, + { -0.0166, -0.0498, 0.9983 }, + { -0.0333, -0.0502, 0.9980 }, + { -0.0499, -0.0502, 0.9972 }, + { -0.0664, -0.0497, 0.9964 }, + { -0.0664, -0.0662, 0.9956 }, + { -0.0332, -0.0663, 0.9972 }, + { -0.0332, -0.0667, 0.9972 }, + { -0.0332, -0.0832, 0.9959 }, + { -0.0331, -0.1155, 0.9926 }, + { -0.0495, -0.1316, 0.9899 }, + { -0.0658, -0.1476, 0.9867 }, + { -0.0649, -0.2116, 0.9740 }, + { -0.0799, -0.2725, 0.9586 }, + { -0.0954, -0.2854, 0.9537 }, + { -0.1110, -0.2849, 0.9520 }, + { -0.1255, -0.3126, 0.9411 }, + { -0.1695, -0.3404, 0.9247 }, + { -0.2002, -0.3247, 0.9241 }, + { -0.2318, -0.2928, 0.9274 }, + { -0.2361, -0.2190, 0.9446 }, + { -0.2249, -0.1282, 0.9649 }, + { -0.1633, -0.0985, 0.9811 }, + { -0.1311, -0.1151, 0.9840 }, + { -0.0983, -0.1471, 0.9836 }, + { -0.1140, -0.1786, 0.9770 }, + { -0.1613, -0.1931, 0.9678 }, + { -0.1934, -0.1615, 0.9672 }, + { -0.2411, -0.0970, 0.9650 }, + { -0.2421, -0.0322, 0.9690 }, + { -0.2424, 0.0000, 0.9701 }, + { 0.2406, 0.1128, 0.9627 }, + { 0.1930, 0.1775, 0.9649 }, + { 0.1617, 0.1774, 0.9706 }, + { 0.0494, 0.0818, 0.9908 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, -0.0332, 0.9989 }, + { 0.0000, -0.0663, 0.9978 }, + { -0.0332, -0.0667, 0.9972 }, + { -0.0498, -0.0667, 0.9964 }, + { -0.0664, -0.0662, 0.9956 }, + { -0.0664, -0.0497, 0.9964 }, + { -0.0499, -0.0497, 0.9972 }, + { -0.0332, -0.0667, 0.9972 }, + { -0.0332, -0.0832, 0.9959 }, + { -0.0331, -0.1155, 0.9926 }, + { -0.0494, -0.1477, 0.9875 }, + { -0.0492, -0.1638, 0.9851 }, + { -0.0649, -0.2116, 0.9740 }, + { -0.0795, -0.2869, 0.9541 }, + { -0.0949, -0.2997, 0.9492 }, + { -0.1105, -0.2992, 0.9475 }, + { -0.1394, -0.3396, 0.9296 }, + { -0.1676, -0.3673, 0.9147 }, + { -0.1834, -0.3530, 0.9173 }, + { -0.2161, -0.3076, 0.9262 }, + { -0.2217, -0.2041, 0.9504 }, + { -0.2107, -0.0807, 0.9729 }, + { -0.1639, -0.0495, 0.9846 }, + { -0.1315, -0.0825, 0.9872 }, + { -0.1141, -0.1463, 0.9802 }, + { -0.1440, -0.2237, 0.9623 }, + { -0.1902, -0.2373, 0.9520 }, + { -0.2219, -0.2070, 0.9522 }, + { -0.2550, -0.1279, 0.9563 }, + { -0.2574, -0.0321, 0.9653 }, + { -0.2576, 0.0161, 0.9660 }, + { 0.2100, 0.0975, 0.9716 }, + { 0.1786, 0.1301, 0.9746 }, + { 0.0817, 0.0814, 0.9866 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, -0.0332, 0.9989 }, + { 0.0331, -0.0827, 0.9953 }, + { -0.0331, -0.0998, 0.9945 }, + { -0.0497, -0.0833, 0.9950 }, + { -0.0664, -0.0662, 0.9956 }, + { -0.0664, -0.0497, 0.9964 }, + { -0.0665, -0.0332, 0.9972 }, + { -0.0498, -0.0502, 0.9972 }, + { -0.0497, -0.0831, 0.9950 }, + { -0.0494, -0.1314, 0.9894 }, + { -0.0658, -0.1476, 0.9867 }, + { -0.0654, -0.1633, 0.9833 }, + { -0.0804, -0.2421, 0.9656 }, + { -0.0949, -0.3014, 0.9487 }, + { -0.1100, -0.3135, 0.9431 }, + { -0.1401, -0.3262, 0.9346 }, + { -0.1677, -0.3648, 0.9153 }, + { -0.1814, -0.3793, 0.9072 }, + { -0.1970, -0.3653, 0.9097 }, + { -0.2002, -0.3219, 0.9242 }, + { -0.2065, -0.2048, 0.9535 }, + { -0.1950, -0.0646, 0.9760 }, + { -0.1802, -0.0166, 0.9832 }, + { -0.1639, -0.0656, 0.9838 }, + { -0.1619, -0.1608, 0.9715 }, + { -0.1897, -0.2520, 0.9485 }, + { -0.2190, -0.2653, 0.9389 }, + { -0.2657, -0.2194, 0.9382 }, + { -0.2840, -0.1268, 0.9478 }, + { -0.2866, -0.0318, 0.9565 }, + { -0.2576, 0.0161, 0.9660 }, + { 0.1313, 0.0990, 0.9859 }, + { 0.1151, 0.0499, 0.9896 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, 0.0000, 1.0000 }, + { -0.0326, -0.0973, 0.9850 }, + { -0.0493, -0.1479, 0.9865 }, + { -0.0497, -0.0998, 0.9936 }, + { -0.0663, -0.0826, 0.9942 }, + { -0.0664, -0.0497, 0.9964 }, + { -0.0665, -0.0332, 0.9972 }, + { -0.0829, -0.0500, 0.9950 }, + { -0.0827, -0.0829, 0.9928 }, + { -0.0984, -0.1309, 0.9854 }, + { -0.0980, -0.1631, 0.9812 }, + { -0.1298, -0.1782, 0.9747 }, + { -0.1433, -0.2401, 0.9577 }, + { -0.1404, -0.3133, 0.9377 }, + { -0.1692, -0.3382, 0.9246 }, + { -0.1977, -0.3496, 0.9146 }, + { -0.2103, -0.3749, 0.9023 }, + { -0.1948, -0.3912, 0.8993 }, + { -0.1969, -0.3650, 0.9093 }, + { -0.1712, -0.3104, 0.9345 }, + { -0.1761, -0.1900, 0.9611 }, + { -0.1479, -0.0491, 0.9864 }, + { -0.1319, -0.0167, 0.9904 }, + { -0.1151, -0.0659, 0.9894 }, + { -0.1132, -0.1768, 0.9733 }, + { -0.1417, -0.2831, 0.9469 }, + { -0.2013, -0.3090, 0.9294 }, + { -0.2479, -0.2639, 0.9307 }, + { -0.2978, -0.1413, 0.9407 }, + { -0.2863, 0.0000, 0.9555 }, + { -0.2571, 0.0641, 0.9643 }, + { 0.0329, 0.0992, 0.9918 }, + { 0.0332, 0.0004, 0.9967 }, + { 0.0000, -0.0332, 0.9989 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, -0.0659, 0.9956 }, + { -0.1149, -0.1309, 0.9846 }, + { -0.0661, -0.1159, 0.9909 }, + { -0.0827, -0.0995, 0.9915 }, + { -0.0828, -0.0825, 0.9929 }, + { -0.0830, -0.0496, 0.9950 }, + { -0.0830, -0.0496, 0.9950 }, + { -0.0993, -0.0665, 0.9928 }, + { -0.1153, -0.0988, 0.9877 }, + { -0.1468, -0.1463, 0.9780 }, + { -0.1616, -0.1773, 0.9701 }, + { -0.1917, -0.2071, 0.9587 }, + { -0.2196, -0.2520, 0.9414 }, + { -0.2289, -0.3213, 0.9169 }, + { -0.2539, -0.3581, 0.8975 }, + { -0.2682, -0.3568, 0.8944 }, + { -0.2682, -0.3568, 0.8944 }, + { -0.2401, -0.3616, 0.9004 }, + { -0.1992, -0.3382, 0.9191 }, + { -0.1722, -0.2965, 0.9391 }, + { -0.1610, -0.1743, 0.9651 }, + { -0.1482, -0.0164, 0.9875 }, + { -0.1320, 0.0165, 0.9904 }, + { -0.1311, -0.0491, 0.9868 }, + { -0.1284, -0.1910, 0.9664 }, + { -0.1390, -0.3380, 0.9279 }, + { -0.1827, -0.3639, 0.9129 }, + { -0.2013, -0.3103, 0.9286 }, + { -0.2369, -0.1570, 0.9493 }, + { -0.2267, 0.0161, 0.9721 }, + { -0.1944, 0.0810, 0.9754 }, + { -0.0331, 0.0998, 0.9945 }, + { -0.0166, 0.0171, 0.9961 }, + { 0.0000, -0.0332, 0.9989 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, 0.0000, 1.0000 }, + { -0.1121, -0.1119, 0.9744 }, + { -0.0980, -0.1622, 0.9798 }, + { -0.0824, -0.1160, 0.9895 }, + { -0.0824, -0.1160, 0.9895 }, + { -0.0991, -0.0824, 0.9915 }, + { -0.0994, -0.0495, 0.9937 }, + { -0.1156, -0.0494, 0.9918 }, + { -0.1314, -0.0827, 0.9872 }, + { -0.1469, -0.1308, 0.9798 }, + { -0.1774, -0.1769, 0.9679 }, + { -0.2070, -0.2065, 0.9560 }, + { -0.2356, -0.2350, 0.9428 }, + { -0.2472, -0.2792, 0.9273 }, + { -0.2694, -0.3448, 0.8983 }, + { -0.2805, -0.3682, 0.8862 }, + { -0.2821, -0.3555, 0.8910 }, + { -0.2835, -0.3423, 0.8956 }, + { -0.2723, -0.3188, 0.9078 }, + { -0.2459, -0.2935, 0.9232 }, + { -0.2187, -0.2651, 0.9385 }, + { -0.1924, -0.1586, 0.9632 }, + { -0.2107, -0.0162, 0.9751 }, + { -0.2109, -0.0002, 0.9758 }, + { -0.2262, -0.0647, 0.9709 }, + { -0.2218, -0.1881, 0.9517 }, + { -0.2135, -0.3337, 0.9159 }, + { -0.1826, -0.3639, 0.9129 }, + { -0.1712, -0.3121, 0.9340 }, + { -0.1607, -0.1596, 0.9650 }, + { -0.1472, 0.0487, 0.9833 }, + { -0.1313, 0.1145, 0.9846 }, + { 0.0000, 0.0668, 0.9966 }, + { -0.0332, 0.0336, 0.9966 }, + { 0.0000, -0.0166, 0.9997 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, -0.1133, 0.9870 }, + { -0.1770, -0.1602, 0.9678 }, + { -0.1153, -0.0986, 0.9883 }, + { -0.0990, -0.0994, 0.9901 }, + { -0.0824, -0.1158, 0.9896 }, + { -0.0825, -0.0987, 0.9910 }, + { -0.0993, -0.0660, 0.9929 }, + { -0.1317, -0.0821, 0.9878 }, + { -0.1636, -0.0985, 0.9816 }, + { -0.1781, -0.1457, 0.9719 }, + { -0.1918, -0.2072, 0.9592 }, + { -0.2056, -0.2367, 0.9493 }, + { -0.2042, -0.2513, 0.9450 }, + { -0.2013, -0.2958, 0.9315 }, + { -0.2252, -0.3622, 0.9031 }, + { -0.2242, -0.3735, 0.8990 }, + { -0.2255, -0.3607, 0.9040 }, + { -0.2413, -0.3463, 0.9060 }, + { -0.2581, -0.3201, 0.9114 }, + { -0.2759, -0.2770, 0.9199 }, + { -0.2928, -0.2310, 0.9267 }, + { -0.2951, -0.1553, 0.9378 }, + { -0.3002, -0.0315, 0.9502 }, + { -0.3008, -0.0002, 0.9521 }, + { -0.2862, -0.0636, 0.9550 }, + { -0.2665, -0.1861, 0.9411 }, + { -0.2306, -0.3065, 0.9229 }, + { -0.1855, -0.3238, 0.9277 }, + { -0.1575, -0.2843, 0.9453 }, + { -0.1299, -0.1290, 0.9744 }, + { -0.1155, 0.0493, 0.9907 }, + { -0.1476, 0.0981, 0.9840 }, + { 0.0663, -0.0163, 0.9959 }, + { 0.0166, 0.0168, 0.9983 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, 0.0000, 1.0000 }, + { -0.1536, -0.1678, 0.9461 }, + { -0.1121, -0.2200, 0.9609 }, + { -0.1317, -0.0821, 0.9878 }, + { -0.1314, -0.0827, 0.9872 }, + { -0.1313, -0.0990, 0.9859 }, + { -0.1306, -0.0982, 0.9844 }, + { -0.1470, -0.0981, 0.9831 }, + { -0.1785, -0.1135, 0.9761 }, + { -0.1787, -0.1305, 0.9751 }, + { -0.2088, -0.1609, 0.9640 }, + { -0.1918, -0.2072, 0.9592 }, + { -0.1600, -0.2236, 0.9609 }, + { -0.1121, -0.2401, 0.9629 }, + { -0.1094, -0.3137, 0.9400 }, + { -0.1061, -0.3824, 0.9146 }, + { -0.1062, -0.3804, 0.9155 }, + { -0.1215, -0.3801, 0.9148 }, + { -0.1513, -0.3785, 0.9110 }, + { -0.1825, -0.3523, 0.9159 }, + { -0.2288, -0.3223, 0.9173 }, + { -0.3037, -0.2726, 0.9120 }, + { -0.3383, -0.1522, 0.9237 }, + { -0.3438, -0.0156, 0.9378 }, + { -0.3301, 0.0157, 0.9436 }, + { -0.3159, -0.0315, 0.9478 }, + { -0.2836, -0.1406, 0.9454 }, + { -0.2336, -0.2636, 0.9347 }, + { -0.2022, -0.2948, 0.9337 }, + { -0.1742, -0.2541, 0.9508 }, + { -0.1463, -0.1135, 0.9759 }, + { -0.1639, 0.0327, 0.9849 }, + { -0.1796, 0.0814, 0.9801 }, + { 0.1316, -0.0492, 0.9883 }, + { 0.0829, -0.0331, 0.9953 }, + { 0.0822, -0.0329, 0.9921 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, 0.0000, 1.0000 }, + { 0.0000, 0.0000, 1.0000 }, + { -0.0957, -0.1564, 0.9654 }, + { -0.1537, -0.2183, 0.9466 }, + { -0.0658, -0.1315, 0.9886 }, + { -0.0986, -0.1149, 0.9878 }, + { -0.1636, -0.0985, 0.9816 }, + { -0.1945, -0.1139, 0.9736 }, + { -0.2402, -0.1120, 0.9630 }, + { -0.2546, -0.1115, 0.9585 }, + { -0.2556, -0.1116, 0.9597 }, + { -0.2539, -0.1281, 0.9562 }, + { -0.2540, -0.1595, 0.9535 }, + { -0.1935, -0.1609, 0.9678 }, + { -0.1304, -0.1626, 0.9780 }, + { -0.0649, -0.2101, 0.9744 }, + { -0.0158, -0.3019, 0.9509 }, + { 0.0154, -0.3716, 0.9267 }, + { 0.0153, -0.3963, 0.9169 }, + { 0.0000, -0.4086, 0.9106 }, + { 0.0001, -0.4077, 0.9085 }, + { -0.0453, -0.3974, 0.9134 }, + { -0.0901, -0.3957, 0.9095 }, + { -0.1509, -0.3353, 0.9202 }, + { -0.2192, -0.1875, 0.9485 }, + { -0.2373, -0.0159, 0.9619 }, + { -0.2558, 0.0320, 0.9637 }, + { -0.2560, -0.0160, 0.9644 }, + { -0.2548, -0.1106, 0.9569 }, + { -0.2354, -0.2344, 0.9420 }, + { -0.2190, -0.2653, 0.9389 }, + { -0.1910, -0.2234, 0.9554 }, + { -0.1939, -0.1134, 0.9705 }, + { -0.2114, 0.0162, 0.9759 }, + { -0.2264, 0.0646, 0.9714 }, + { 0.1316, -0.0825, 0.9872 }, + { 0.1158, -0.0334, 0.9920 }, + { 0.1312, -0.0812, 0.9841 }, + { 0.0975, -0.0812, 0.9837 }, + { 0.0661, 0.0000, 0.9956 }, + { 0.0165, -0.0990, 0.9898 }, + { -0.0640, -0.1632, 0.9753 }, + { 0.0165, -0.1479, 0.9886 }, + { 0.0000, -0.1639, 0.9859 }, + { -0.0327, -0.1796, 0.9825 }, + { -0.1137, -0.1795, 0.9759 }, + { -0.1769, -0.1778, 0.9667 }, + { -0.2387, -0.1588, 0.9564 }, + { -0.2702, -0.1111, 0.9551 }, + { -0.2857, -0.1107, 0.9518 }, + { -0.3139, -0.1260, 0.9411 }, + { -0.3004, -0.0953, 0.9484 }, + { -0.2411, -0.0803, 0.9659 }, + { -0.1635, -0.0979, 0.9812 }, + { -0.0823, -0.1312, 0.9873 }, + { 0.0161, -0.2415, 0.9668 }, + { 0.0466, -0.3575, 0.9317 }, + { 0.0763, -0.3955, 0.9152 }, + { 0.0913, -0.3949, 0.9137 }, + { 0.1199, -0.4183, 0.8995 }, + { 0.1036, -0.4329, 0.8924 }, + { 0.0747, -0.4219, 0.9005 }, + { 0.0603, -0.3939, 0.9122 }, + { 0.0000, -0.2331, 0.9541 }, + { -0.0328, -0.0494, 0.9921 }, + { -0.0981, 0.0000, 0.9903 }, + { -0.1313, -0.0328, 0.9881 }, + { -0.1779, -0.1288, 0.9723 }, + { -0.1902, -0.2366, 0.9512 }, + { -0.2049, -0.2512, 0.9454 }, + { -0.2214, -0.2223, 0.9490 }, + { -0.2395, -0.1276, 0.9575 }, + { -0.2718, 0.0000, 0.9607 }, + { -0.2870, 0.0318, 0.9569 }, + { 0.0988, -0.0661, 0.9921 }, + { 0.0994, -0.0333, 0.9939 }, + { 0.0911, -0.0496, 0.9944 }, + { 0.1475, -0.0655, 0.9857 }, + { 0.1072, -0.0823, 0.9903 }, + { 0.0653, -0.1322, 0.9877 }, + { 0.0985, -0.1641, 0.9810 }, + { 0.0816, -0.1632, 0.9820 }, + { 0.0572, -0.1794, 0.9816 }, + { 0.0322, -0.2260, 0.9723 }, + { -0.0090, -0.2429, 0.9683 }, + { -0.0554, -0.2422, 0.9657 }, + { -0.1204, -0.2084, 0.9662 }, + { -0.1933, -0.1608, 0.9674 }, + { -0.2691, -0.1579, 0.9500 }, + { -0.3063, -0.1416, 0.9411 }, + { -0.3069, -0.0797, 0.9466 }, + { -0.2798, -0.0160, 0.9597 }, + { -0.2417, 0.0000, 0.9692 }, + { -0.1929, -0.0325, 0.9752 }, + { -0.1321, -0.1761, 0.9566 }, + { -0.0613, -0.3148, 0.9419 }, + { 0.0077, -0.3557, 0.9305 }, + { 0.0615, -0.3692, 0.9253 }, + { 0.0907, -0.3938, 0.9120 }, + { 0.1393, -0.4319, 0.8901 }, + { 0.1710, -0.4299, 0.8860 }, + { 0.2001, -0.4005, 0.8926 }, + { 0.2097, -0.2705, 0.9252 }, + { 0.1062, -0.1142, 0.9852 }, + { -0.0168, -0.0668, 0.9975 }, + { -0.0985, -0.0990, 0.9889 }, + { -0.1688, -0.1767, 0.9671 }, + { -0.1958, -0.2657, 0.9415 }, + { -0.2095, -0.2943, 0.9320 }, + { -0.2501, -0.2499, 0.9347 }, + { -0.2527, -0.1594, 0.9511 }, + { -0.3003, -0.0320, 0.9501 }, + { -0.3434, -0.0002, 0.9380 }, + { 0.0331, -0.0334, 0.9983 }, + { 0.0332, -0.0332, 0.9983 }, + { 0.0414, -0.0497, 0.9968 }, + { 0.0743, -0.0825, 0.9928 }, + { 0.0909, -0.1158, 0.9886 }, + { 0.1221, -0.1476, 0.9813 }, + { 0.1620, -0.1617, 0.9729 }, + { 0.2068, -0.1908, 0.9577 }, + { 0.1823, -0.2376, 0.9531 }, + { 0.1357, -0.2709, 0.9525 }, + { 0.1027, -0.2720, 0.9563 }, + { 0.0560, -0.2714, 0.9606 }, + { -0.0001, -0.2566, 0.9658 }, + { -0.1045, -0.2405, 0.9645 }, + { -0.1904, -0.2234, 0.9552 }, + { -0.3126, -0.1261, 0.9383 }, + { -0.3562, -0.0007, 0.9314 }, + { -0.3690, 0.0306, 0.9264 }, + { -0.3598, -0.0155, 0.9280 }, + { -0.3370, -0.1083, 0.9200 }, + { -0.3128, -0.2418, 0.9067 }, + { -0.2683, -0.3017, 0.9074 }, + { -0.2271, -0.3055, 0.9188 }, + { -0.1652, -0.3350, 0.9169 }, + { -0.0818, -0.3826, 0.9146 }, + { -0.0090, -0.3853, 0.9210 }, + { 0.0851, -0.3556, 0.9303 }, + { 0.1563, -0.2810, 0.9435 }, + { 0.1760, -0.1919, 0.9636 }, + { 0.1210, -0.1789, 0.9721 }, + { 0.0155, -0.1962, 0.9771 }, + { -0.0720, -0.2394, 0.9625 }, + { -0.1398, -0.3110, 0.9362 }, + { -0.1843, -0.3374, 0.9226 }, + { -0.2234, -0.2943, 0.9277 }, + { -0.2956, -0.1877, 0.9334 }, + { -0.3137, -0.0632, 0.9439 }, + { -0.3089, -0.0158, 0.9507 }, + { -0.3368, -0.0469, 0.9402 }, + { -0.0166, -0.0334, 0.9992 }, + { -0.0166, -0.0332, 0.9992 }, + { -0.0166, -0.0332, 0.9992 }, + { -0.0165, -0.0497, 0.9972 }, + { 0.0332, -0.0667, 0.9967 }, + { 0.0825, -0.0828, 0.9918 }, + { 0.1634, -0.0979, 0.9812 }, + { 0.2072, -0.1741, 0.9583 }, + { 0.1878, -0.2810, 0.9401 }, + { 0.1408, -0.3142, 0.9387 }, + { 0.1099, -0.3154, 0.9424 }, + { 0.0471, -0.3291, 0.9429 }, + { -0.0156, -0.3434, 0.9389 }, + { -0.1094, -0.3275, 0.9383 }, + { -0.1863, -0.3118, 0.9317 }, + { -0.2794, -0.2010, 0.9322 }, + { -0.3434, -0.0622, 0.9366 }, + { -0.4100, -0.0303, 0.9115 }, + { -0.4467, -0.0445, 0.8935 }, + { -0.4787, -0.1021, 0.8708 }, + { -0.4502, -0.1890, 0.8716 }, + { -0.3862, -0.2371, 0.8914 }, + { -0.3190, -0.2576, 0.9118 }, + { -0.2622, -0.2621, 0.9275 }, + { -0.1888, -0.2687, 0.9444 }, + { -0.1111, -0.2716, 0.9547 }, + { -0.0474, -0.2401, 0.9630 }, + { 0.0001, -0.2520, 0.9485 }, + { -0.0154, -0.2690, 0.9522 }, + { -0.0783, -0.2711, 0.9528 }, + { -0.1408, -0.2846, 0.9450 }, + { -0.1861, -0.3094, 0.9316 }, + { -0.2140, -0.3355, 0.9174 }, + { -0.1993, -0.3365, 0.9202 }, + { -0.2002, -0.3246, 0.9242 }, + { -0.2194, -0.2197, 0.9439 }, + { -0.2562, -0.0797, 0.9616 }, + { -0.3014, -0.0475, 0.9521 }, + { -0.3435, -0.0623, 0.9371 }, +}; + +static float texcoord[][2] = { +#ifdef _ORIGINAL_ /* [ */ + { 0.1121, 0.0171 }, + { 0.1094, 0.0411 }, + { 0.1066, 0.0654 }, + { 0.1038, 0.0898 }, + { 0.1010, 0.1141 }, + { 0.0982, 0.1384 }, + { 0.0954, 0.1624 }, + { 0.0926, 0.1868 }, + { 0.0898, 0.2111 }, + { 0.0870, 0.2354 }, + { 0.0842, 0.2598 }, + { 0.0815, 0.2838 }, + { 0.0787, 0.3081 }, + { 0.0759, 0.3325 }, + { 0.0731, 0.3568 }, + { 0.0703, 0.3811 }, + { 0.0675, 0.4052 }, + { 0.0647, 0.4295 }, + { 0.0619, 0.4538 }, + { 0.0591, 0.4782 }, + { 0.0564, 0.5025 }, + { 0.0536, 0.5265 }, + { 0.0508, 0.5508 }, + { 0.0480, 0.5752 }, + { 0.0452, 0.5995 }, + { 0.0424, 0.6239 }, + { 0.0397, 0.6479 }, + { 0.0369, 0.6722 }, + { 0.0341, 0.6965 }, + { 0.0313, 0.7209 }, + { 0.0285, 0.7452 }, + { 0.0257, 0.7692 }, + { 0.0229, 0.7936 }, + { 0.0201, 0.8179 }, + { 0.0173, 0.8422 }, + { 0.0145, 0.8666 }, + { 0.0118, 0.8906 }, + { 0.0090, 0.9149 }, + { 0.0062, 0.9393 }, + { 0.1364, 0.0199 }, + { 0.1336, 0.0439 }, + { 0.1309, 0.0682 }, + { 0.1281, 0.0925 }, + { 0.1253, 0.1169 }, + { 0.1225, 0.1412 }, + { 0.1197, 0.1652 }, + { 0.1169, 0.1896 }, + { 0.1141, 0.2139 }, + { 0.1113, 0.2382 }, + { 0.1085, 0.2626 }, + { 0.1058, 0.2866 }, + { 0.1030, 0.3109 }, + { 0.1002, 0.3353 }, + { 0.0974, 0.3596 }, + { 0.0946, 0.3839 }, + { 0.0918, 0.4079 }, + { 0.0890, 0.4323 }, + { 0.0862, 0.4566 }, + { 0.0834, 0.4810 }, + { 0.0806, 0.5053 }, + { 0.0779, 0.5293 }, + { 0.0751, 0.5536 }, + { 0.0723, 0.5780 }, + { 0.0695, 0.6023 }, + { 0.0667, 0.6266 }, + { 0.0640, 0.6507 }, + { 0.0612, 0.6750 }, + { 0.0584, 0.6993 }, + { 0.0556, 0.7237 }, + { 0.0528, 0.7480 }, + { 0.0500, 0.7720 }, + { 0.0472, 0.7964 }, + { 0.0444, 0.8207 }, + { 0.0416, 0.8450 }, + { 0.0388, 0.8694 }, + { 0.0361, 0.8934 }, + { 0.0333, 0.9177 }, + { 0.0305, 0.9420 }, + { 0.1607, 0.0226 }, + { 0.1579, 0.0467 }, + { 0.1551, 0.0710 }, + { 0.1523, 0.0953 }, + { 0.1495, 0.1197 }, + { 0.1467, 0.1440 }, + { 0.1440, 0.1680 }, + { 0.1412, 0.1924 }, + { 0.1384, 0.2167 }, + { 0.1356, 0.2410 }, + { 0.1328, 0.2654 }, + { 0.1300, 0.2894 }, + { 0.1272, 0.3137 }, + { 0.1244, 0.3380 }, + { 0.1216, 0.3624 }, + { 0.1188, 0.3867 }, + { 0.1161, 0.4107 }, + { 0.1133, 0.4351 }, + { 0.1105, 0.4594 }, + { 0.1077, 0.4837 }, + { 0.1049, 0.5081 }, + { 0.1021, 0.5321 }, + { 0.0994, 0.5564 }, + { 0.0966, 0.5808 }, + { 0.0938, 0.6051 }, + { 0.0910, 0.6294 }, + { 0.0882, 0.6534 }, + { 0.0854, 0.6778 }, + { 0.0826, 0.7021 }, + { 0.0798, 0.7265 }, + { 0.0770, 0.7508 }, + { 0.0743, 0.7748 }, + { 0.0715, 0.7991 }, + { 0.0687, 0.8235 }, + { 0.0659, 0.8478 }, + { 0.0631, 0.8721 }, + { 0.0603, 0.8962 }, + { 0.0575, 0.9205 }, + { 0.0547, 0.9448 }, + { 0.1850, 0.0254 }, + { 0.1822, 0.0495 }, + { 0.1794, 0.0738 }, + { 0.1766, 0.0981 }, + { 0.1738, 0.1225 }, + { 0.1710, 0.1468 }, + { 0.1683, 0.1708 }, + { 0.1655, 0.1951 }, + { 0.1627, 0.2195 }, + { 0.1599, 0.2438 }, + { 0.1571, 0.2681 }, + { 0.1543, 0.2922 }, + { 0.1515, 0.3165 }, + { 0.1487, 0.3408 }, + { 0.1459, 0.3652 }, + { 0.1431, 0.3895 }, + { 0.1404, 0.4135 }, + { 0.1376, 0.4379 }, + { 0.1348, 0.4622 }, + { 0.1320, 0.4865 }, + { 0.1292, 0.5109 }, + { 0.1264, 0.5349 }, + { 0.1236, 0.5592 }, + { 0.1209, 0.5835 }, + { 0.1181, 0.6079 }, + { 0.1153, 0.6322 }, + { 0.1125, 0.6562 }, + { 0.1097, 0.6806 }, + { 0.1069, 0.7049 }, + { 0.1041, 0.7292 }, + { 0.1013, 0.7536 }, + { 0.0986, 0.7776 }, + { 0.0958, 0.8019 }, + { 0.0930, 0.8263 }, + { 0.0902, 0.8506 }, + { 0.0874, 0.8749 }, + { 0.0846, 0.8990 }, + { 0.0818, 0.9233 }, + { 0.0790, 0.9476 }, + { 0.2092, 0.0282 }, + { 0.2065, 0.0522 }, + { 0.2037, 0.0766 }, + { 0.2009, 0.1009 }, + { 0.1981, 0.1252 }, + { 0.1953, 0.1496 }, + { 0.1925, 0.1736 }, + { 0.1897, 0.1979 }, + { 0.1869, 0.2223 }, + { 0.1841, 0.2466 }, + { 0.1813, 0.2709 }, + { 0.1786, 0.2950 }, + { 0.1758, 0.3193 }, + { 0.1730, 0.3436 }, + { 0.1702, 0.3680 }, + { 0.1674, 0.3923 }, + { 0.1646, 0.4163 }, + { 0.1618, 0.4406 }, + { 0.1590, 0.4650 }, + { 0.1563, 0.4893 }, + { 0.1535, 0.5136 }, + { 0.1507, 0.5377 }, + { 0.1479, 0.5620 }, + { 0.1451, 0.5863 }, + { 0.1423, 0.6107 }, + { 0.1395, 0.6350 }, + { 0.1368, 0.6590 }, + { 0.1340, 0.6834 }, + { 0.1312, 0.7077 }, + { 0.1284, 0.7320 }, + { 0.1256, 0.7564 }, + { 0.1228, 0.7804 }, + { 0.1200, 0.8047 }, + { 0.1172, 0.8290 }, + { 0.1144, 0.8534 }, + { 0.1116, 0.8777 }, + { 0.1089, 0.9017 }, + { 0.1061, 0.9261 }, + { 0.1033, 0.9504 }, + { 0.2335, 0.0310 }, + { 0.2307, 0.0550 }, + { 0.2279, 0.0794 }, + { 0.2251, 0.1037 }, + { 0.2223, 0.1280 }, + { 0.2195, 0.1524 }, + { 0.2168, 0.1764 }, + { 0.2140, 0.2007 }, + { 0.2112, 0.2251 }, + { 0.2084, 0.2494 }, + { 0.2056, 0.2737 }, + { 0.2028, 0.2977 }, + { 0.2000, 0.3221 }, + { 0.1972, 0.3464 }, + { 0.1944, 0.3707 }, + { 0.1916, 0.3951 }, + { 0.1889, 0.4191 }, + { 0.1861, 0.4434 }, + { 0.1833, 0.4678 }, + { 0.1805, 0.4921 }, + { 0.1777, 0.5164 }, + { 0.1750, 0.5405 }, + { 0.1722, 0.5648 }, + { 0.1694, 0.5891 }, + { 0.1666, 0.6135 }, + { 0.1638, 0.6378 }, + { 0.1610, 0.6618 }, + { 0.1582, 0.6861 }, + { 0.1554, 0.7105 }, + { 0.1526, 0.7348 }, + { 0.1498, 0.7591 }, + { 0.1471, 0.7832 }, + { 0.1443, 0.8075 }, + { 0.1415, 0.8318 }, + { 0.1387, 0.8562 }, + { 0.1359, 0.8805 }, + { 0.1331, 0.9045 }, + { 0.1303, 0.9289 }, + { 0.1275, 0.9532 }, + { 0.2578, 0.0338 }, + { 0.2550, 0.0578 }, + { 0.2522, 0.0822 }, + { 0.2494, 0.1065 }, + { 0.2466, 0.1308 }, + { 0.2438, 0.1552 }, + { 0.2411, 0.1792 }, + { 0.2383, 0.2035 }, + { 0.2355, 0.2278 }, + { 0.2327, 0.2522 }, + { 0.2299, 0.2765 }, + { 0.2271, 0.3005 }, + { 0.2243, 0.3249 }, + { 0.2215, 0.3492 }, + { 0.2187, 0.3735 }, + { 0.2159, 0.3979 }, + { 0.2132, 0.4219 }, + { 0.2104, 0.4462 }, + { 0.2076, 0.4706 }, + { 0.2048, 0.4949 }, + { 0.2020, 0.5192 }, + { 0.1992, 0.5432 }, + { 0.1965, 0.5676 }, + { 0.1937, 0.5919 }, + { 0.1909, 0.6162 }, + { 0.1881, 0.6406 }, + { 0.1853, 0.6646 }, + { 0.1825, 0.6889 }, + { 0.1797, 0.7133 }, + { 0.1769, 0.7376 }, + { 0.1741, 0.7619 }, + { 0.1714, 0.7860 }, + { 0.1686, 0.8103 }, + { 0.1658, 0.8346 }, + { 0.1630, 0.8590 }, + { 0.1602, 0.8833 }, + { 0.1574, 0.9073 }, + { 0.1546, 0.9316 }, + { 0.1518, 0.9560 }, + { 0.2820, 0.0366 }, + { 0.2793, 0.0606 }, + { 0.2765, 0.0849 }, + { 0.2737, 0.1093 }, + { 0.2709, 0.1336 }, + { 0.2681, 0.1579 }, + { 0.2653, 0.1820 }, + { 0.2625, 0.2063 }, + { 0.2597, 0.2306 }, + { 0.2569, 0.2550 }, + { 0.2541, 0.2793 }, + { 0.2514, 0.3033 }, + { 0.2486, 0.3277 }, + { 0.2458, 0.3520 }, + { 0.2430, 0.3763 }, + { 0.2402, 0.4007 }, + { 0.2374, 0.4247 }, + { 0.2346, 0.4490 }, + { 0.2319, 0.4733 }, + { 0.2291, 0.4977 }, + { 0.2263, 0.5220 }, + { 0.2235, 0.5460 }, + { 0.2207, 0.5704 }, + { 0.2179, 0.5947 }, + { 0.2151, 0.6190 }, + { 0.2123, 0.6434 }, + { 0.2096, 0.6674 }, + { 0.2068, 0.6917 }, + { 0.2040, 0.7161 }, + { 0.2012, 0.7404 }, + { 0.1984, 0.7647 }, + { 0.1956, 0.7887 }, + { 0.1928, 0.8131 }, + { 0.1900, 0.8374 }, + { 0.1872, 0.8617 }, + { 0.1844, 0.8861 }, + { 0.1817, 0.9101 }, + { 0.1789, 0.9344 }, + { 0.1761, 0.9588 }, + { 0.3063, 0.0394 }, + { 0.3036, 0.0634 }, + { 0.3008, 0.0877 }, + { 0.2980, 0.1121 }, + { 0.2952, 0.1364 }, + { 0.2924, 0.1607 }, + { 0.2896, 0.1848 }, + { 0.2868, 0.2091 }, + { 0.2840, 0.2334 }, + { 0.2812, 0.2578 }, + { 0.2784, 0.2821 }, + { 0.2757, 0.3061 }, + { 0.2729, 0.3304 }, + { 0.2701, 0.3548 }, + { 0.2673, 0.3791 }, + { 0.2645, 0.4034 }, + { 0.2617, 0.4275 }, + { 0.2589, 0.4518 }, + { 0.2561, 0.4761 }, + { 0.2534, 0.5005 }, + { 0.2506, 0.5248 }, + { 0.2478, 0.5488 }, + { 0.2450, 0.5732 }, + { 0.2422, 0.5975 }, + { 0.2394, 0.6218 }, + { 0.2366, 0.6462 }, + { 0.2339, 0.6702 }, + { 0.2311, 0.6945 }, + { 0.2283, 0.7188 }, + { 0.2255, 0.7432 }, + { 0.2227, 0.7675 }, + { 0.2199, 0.7915 }, + { 0.2171, 0.8159 }, + { 0.2143, 0.8402 }, + { 0.2115, 0.8645 }, + { 0.2087, 0.8889 }, + { 0.2060, 0.9129 }, + { 0.2032, 0.9372 }, + { 0.2004, 0.9616 }, + { 0.3306, 0.0422 }, + { 0.3278, 0.0662 }, + { 0.3250, 0.0905 }, + { 0.3222, 0.1148 }, + { 0.3194, 0.1392 }, + { 0.3166, 0.1635 }, + { 0.3139, 0.1875 }, + { 0.3111, 0.2119 }, + { 0.3083, 0.2362 }, + { 0.3055, 0.2605 }, + { 0.3027, 0.2849 }, + { 0.2999, 0.3089 }, + { 0.2971, 0.3332 }, + { 0.2943, 0.3576 }, + { 0.2915, 0.3819 }, + { 0.2888, 0.4062 }, + { 0.2860, 0.4302 }, + { 0.2832, 0.4546 }, + { 0.2804, 0.4789 }, + { 0.2776, 0.5033 }, + { 0.2748, 0.5276 }, + { 0.2721, 0.5516 }, + { 0.2693, 0.5759 }, + { 0.2665, 0.6003 }, + { 0.2637, 0.6246 }, + { 0.2609, 0.6489 }, + { 0.2581, 0.6730 }, + { 0.2553, 0.6973 }, + { 0.2525, 0.7216 }, + { 0.2497, 0.7460 }, + { 0.2469, 0.7703 }, + { 0.2442, 0.7943 }, + { 0.2414, 0.8187 }, + { 0.2386, 0.8430 }, + { 0.2358, 0.8673 }, + { 0.2330, 0.8917 }, + { 0.2302, 0.9157 }, + { 0.2274, 0.9400 }, + { 0.2246, 0.9643 }, + { 0.3548, 0.0449 }, + { 0.3521, 0.0690 }, + { 0.3493, 0.0933 }, + { 0.3465, 0.1176 }, + { 0.3437, 0.1420 }, + { 0.3409, 0.1663 }, + { 0.3381, 0.1903 }, + { 0.3353, 0.2147 }, + { 0.3325, 0.2390 }, + { 0.3297, 0.2633 }, + { 0.3269, 0.2877 }, + { 0.3242, 0.3117 }, + { 0.3214, 0.3360 }, + { 0.3186, 0.3603 }, + { 0.3158, 0.3847 }, + { 0.3130, 0.4090 }, + { 0.3102, 0.4330 }, + { 0.3075, 0.4574 }, + { 0.3047, 0.4817 }, + { 0.3019, 0.5060 }, + { 0.2991, 0.5304 }, + { 0.2963, 0.5544 }, + { 0.2935, 0.5787 }, + { 0.2907, 0.6031 }, + { 0.2879, 0.6274 }, + { 0.2851, 0.6517 }, + { 0.2824, 0.6757 }, + { 0.2796, 0.7001 }, + { 0.2768, 0.7244 }, + { 0.2740, 0.7488 }, + { 0.2712, 0.7731 }, + { 0.2684, 0.7971 }, + { 0.2656, 0.8214 }, + { 0.2628, 0.8458 }, + { 0.2600, 0.8701 }, + { 0.2573, 0.8944 }, + { 0.2545, 0.9185 }, + { 0.2517, 0.9428 }, + { 0.2489, 0.9671 }, + { 0.3791, 0.0477 }, + { 0.3764, 0.0718 }, + { 0.3736, 0.0961 }, + { 0.3708, 0.1204 }, + { 0.3680, 0.1448 }, + { 0.3652, 0.1691 }, + { 0.3624, 0.1931 }, + { 0.3596, 0.2174 }, + { 0.3568, 0.2418 }, + { 0.3540, 0.2661 }, + { 0.3512, 0.2905 }, + { 0.3485, 0.3145 }, + { 0.3457, 0.3388 }, + { 0.3429, 0.3631 }, + { 0.3401, 0.3875 }, + { 0.3373, 0.4118 }, + { 0.3345, 0.4358 }, + { 0.3317, 0.4602 }, + { 0.3290, 0.4845 }, + { 0.3262, 0.5088 }, + { 0.3234, 0.5332 }, + { 0.3206, 0.5572 }, + { 0.3178, 0.5815 }, + { 0.3150, 0.6059 }, + { 0.3122, 0.6302 }, + { 0.3094, 0.6545 }, + { 0.3067, 0.6785 }, + { 0.3039, 0.7029 }, + { 0.3011, 0.7272 }, + { 0.2983, 0.7515 }, + { 0.2955, 0.7759 }, + { 0.2927, 0.7999 }, + { 0.2899, 0.8242 }, + { 0.2871, 0.8486 }, + { 0.2843, 0.8729 }, + { 0.2815, 0.8972 }, + { 0.2788, 0.9213 }, + { 0.2760, 0.9456 }, + { 0.2732, 0.9699 }, + { 0.4034, 0.0505 }, + { 0.4006, 0.0745 }, + { 0.3978, 0.0989 }, + { 0.3950, 0.1232 }, + { 0.3922, 0.1475 }, + { 0.3894, 0.1719 }, + { 0.3867, 0.1959 }, + { 0.3839, 0.2202 }, + { 0.3811, 0.2446 }, + { 0.3783, 0.2689 }, + { 0.3755, 0.2932 }, + { 0.3727, 0.3173 }, + { 0.3699, 0.3416 }, + { 0.3671, 0.3659 }, + { 0.3644, 0.3903 }, + { 0.3616, 0.4146 }, + { 0.3588, 0.4386 }, + { 0.3560, 0.4629 }, + { 0.3532, 0.4873 }, + { 0.3504, 0.5116 }, + { 0.3476, 0.5359 }, + { 0.3449, 0.5600 }, + { 0.3421, 0.5843 }, + { 0.3393, 0.6086 }, + { 0.3365, 0.6330 }, + { 0.3337, 0.6573 }, + { 0.3309, 0.6813 }, + { 0.3281, 0.7057 }, + { 0.3253, 0.7300 }, + { 0.3225, 0.7543 }, + { 0.3197, 0.7787 }, + { 0.3170, 0.8027 }, + { 0.3142, 0.8270 }, + { 0.3114, 0.8513 }, + { 0.3086, 0.8757 }, + { 0.3058, 0.9000 }, + { 0.3030, 0.9240 }, + { 0.3002, 0.9484 }, + { 0.2975, 0.9727 }, + { 0.4277, 0.0533 }, + { 0.4249, 0.0773 }, + { 0.4221, 0.1017 }, + { 0.4193, 0.1260 }, + { 0.4165, 0.1503 }, + { 0.4137, 0.1747 }, + { 0.4110, 0.1987 }, + { 0.4082, 0.2230 }, + { 0.4054, 0.2474 }, + { 0.4026, 0.2717 }, + { 0.3998, 0.2960 }, + { 0.3970, 0.3200 }, + { 0.3942, 0.3444 }, + { 0.3914, 0.3687 }, + { 0.3886, 0.3930 }, + { 0.3859, 0.4174 }, + { 0.3831, 0.4414 }, + { 0.3803, 0.4657 }, + { 0.3775, 0.4901 }, + { 0.3747, 0.5144 }, + { 0.3719, 0.5387 }, + { 0.3692, 0.5628 }, + { 0.3664, 0.5871 }, + { 0.3636, 0.6114 }, + { 0.3608, 0.6358 }, + { 0.3580, 0.6601 }, + { 0.3552, 0.6841 }, + { 0.3524, 0.7084 }, + { 0.3496, 0.7328 }, + { 0.3468, 0.7571 }, + { 0.3440, 0.7815 }, + { 0.3413, 0.8055 }, + { 0.3385, 0.8298 }, + { 0.3357, 0.8541 }, + { 0.3329, 0.8785 }, + { 0.3301, 0.9028 }, + { 0.3273, 0.9268 }, + { 0.3245, 0.9512 }, + { 0.3217, 0.9755 }, + { 0.4519, 0.0561 }, + { 0.4492, 0.0801 }, + { 0.4464, 0.1045 }, + { 0.4436, 0.1288 }, + { 0.4408, 0.1531 }, + { 0.4380, 0.1775 }, + { 0.4352, 0.2015 }, + { 0.4324, 0.2258 }, + { 0.4296, 0.2501 }, + { 0.4268, 0.2745 }, + { 0.4240, 0.2988 }, + { 0.4213, 0.3228 }, + { 0.4185, 0.3472 }, + { 0.4157, 0.3715 }, + { 0.4129, 0.3958 }, + { 0.4101, 0.4202 }, + { 0.4073, 0.4442 }, + { 0.4046, 0.4685 }, + { 0.4018, 0.4929 }, + { 0.3990, 0.5172 }, + { 0.3962, 0.5415 }, + { 0.3934, 0.5655 }, + { 0.3906, 0.5899 }, + { 0.3878, 0.6142 }, + { 0.3850, 0.6385 }, + { 0.3822, 0.6629 }, + { 0.3795, 0.6869 }, + { 0.3767, 0.7112 }, + { 0.3739, 0.7356 }, + { 0.3711, 0.7599 }, + { 0.3683, 0.7842 }, + { 0.3655, 0.8083 }, + { 0.3627, 0.8326 }, + { 0.3599, 0.8569 }, + { 0.3571, 0.8813 }, + { 0.3544, 0.9056 }, + { 0.3516, 0.9296 }, + { 0.3488, 0.9539 }, + { 0.3460, 0.9783 }, + { 0.4762, 0.0589 }, + { 0.4734, 0.0829 }, + { 0.4706, 0.1072 }, + { 0.4678, 0.1316 }, + { 0.4650, 0.1559 }, + { 0.4622, 0.1802 }, + { 0.4595, 0.2043 }, + { 0.4567, 0.2286 }, + { 0.4539, 0.2529 }, + { 0.4511, 0.2773 }, + { 0.4483, 0.3016 }, + { 0.4455, 0.3256 }, + { 0.4427, 0.3500 }, + { 0.4400, 0.3743 }, + { 0.4372, 0.3986 }, + { 0.4344, 0.4230 }, + { 0.4316, 0.4470 }, + { 0.4288, 0.4713 }, + { 0.4260, 0.4956 }, + { 0.4232, 0.5200 }, + { 0.4204, 0.5443 }, + { 0.4177, 0.5683 }, + { 0.4149, 0.5927 }, + { 0.4121, 0.6170 }, + { 0.4093, 0.6413 }, + { 0.4065, 0.6657 }, + { 0.4037, 0.6897 }, + { 0.4009, 0.7140 }, + { 0.3981, 0.7384 }, + { 0.3953, 0.7627 }, + { 0.3925, 0.7870 }, + { 0.3898, 0.8110 }, + { 0.3870, 0.8354 }, + { 0.3842, 0.8597 }, + { 0.3814, 0.8840 }, + { 0.3786, 0.9084 }, + { 0.3758, 0.9324 }, + { 0.3731, 0.9567 }, + { 0.3703, 0.9811 }, + { 0.5005, 0.0617 }, + { 0.4977, 0.0857 }, + { 0.4949, 0.1100 }, + { 0.4921, 0.1344 }, + { 0.4893, 0.1587 }, + { 0.4865, 0.1830 }, + { 0.4838, 0.2071 }, + { 0.4810, 0.2314 }, + { 0.4782, 0.2557 }, + { 0.4754, 0.2801 }, + { 0.4726, 0.3044 }, + { 0.4698, 0.3284 }, + { 0.4670, 0.3527 }, + { 0.4642, 0.3771 }, + { 0.4615, 0.4014 }, + { 0.4587, 0.4257 }, + { 0.4559, 0.4498 }, + { 0.4531, 0.4741 }, + { 0.4503, 0.4984 }, + { 0.4475, 0.5228 }, + { 0.4447, 0.5471 }, + { 0.4420, 0.5711 }, + { 0.4392, 0.5955 }, + { 0.4364, 0.6198 }, + { 0.4336, 0.6441 }, + { 0.4308, 0.6685 }, + { 0.4280, 0.6925 }, + { 0.4252, 0.7168 }, + { 0.4224, 0.7411 }, + { 0.4196, 0.7655 }, + { 0.4168, 0.7898 }, + { 0.4141, 0.8138 }, + { 0.4113, 0.8382 }, + { 0.4085, 0.8625 }, + { 0.4057, 0.8868 }, + { 0.4029, 0.9112 }, + { 0.4001, 0.9352 }, + { 0.3973, 0.9595 }, + { 0.3946, 0.9839 }, + { 0.5247, 0.0645 }, + { 0.5220, 0.0885 }, + { 0.5192, 0.1128 }, + { 0.5164, 0.1371 }, + { 0.5136, 0.1615 }, + { 0.5108, 0.1858 }, + { 0.5080, 0.2098 }, + { 0.5052, 0.2342 }, + { 0.5024, 0.2585 }, + { 0.4996, 0.2828 }, + { 0.4969, 0.3072 }, + { 0.4941, 0.3312 }, + { 0.4913, 0.3555 }, + { 0.4885, 0.3799 }, + { 0.4857, 0.4042 }, + { 0.4829, 0.4285 }, + { 0.4802, 0.4526 }, + { 0.4774, 0.4769 }, + { 0.4746, 0.5012 }, + { 0.4718, 0.5256 }, + { 0.4690, 0.5499 }, + { 0.4662, 0.5739 }, + { 0.4634, 0.5982 }, + { 0.4606, 0.6226 }, + { 0.4578, 0.6469 }, + { 0.4550, 0.6712 }, + { 0.4523, 0.6953 }, + { 0.4495, 0.7196 }, + { 0.4467, 0.7439 }, + { 0.4439, 0.7683 }, + { 0.4411, 0.7926 }, + { 0.4383, 0.8166 }, + { 0.4355, 0.8410 }, + { 0.4327, 0.8653 }, + { 0.4300, 0.8896 }, + { 0.4272, 0.9140 }, + { 0.4244, 0.9380 }, + { 0.4216, 0.9623 }, + { 0.4188, 0.9866 }, + { 0.5490, 0.0673 }, + { 0.5463, 0.0913 }, + { 0.5435, 0.1156 }, + { 0.5407, 0.1399 }, + { 0.5379, 0.1643 }, + { 0.5351, 0.1886 }, + { 0.5323, 0.2126 }, + { 0.5295, 0.2370 }, + { 0.5267, 0.2613 }, + { 0.5239, 0.2856 }, + { 0.5211, 0.3100 }, + { 0.5184, 0.3340 }, + { 0.5156, 0.3583 }, + { 0.5128, 0.3827 }, + { 0.5100, 0.4070 }, + { 0.5072, 0.4313 }, + { 0.5044, 0.4553 }, + { 0.5017, 0.4797 }, + { 0.4989, 0.5040 }, + { 0.4961, 0.5283 }, + { 0.4933, 0.5527 }, + { 0.4905, 0.5767 }, + { 0.4877, 0.6010 }, + { 0.4849, 0.6254 }, + { 0.4821, 0.6497 }, + { 0.4793, 0.6740 }, + { 0.4766, 0.6981 }, + { 0.4738, 0.7224 }, + { 0.4710, 0.7467 }, + { 0.4682, 0.7711 }, + { 0.4654, 0.7954 }, + { 0.4626, 0.8194 }, + { 0.4598, 0.8437 }, + { 0.4570, 0.8681 }, + { 0.4542, 0.8924 }, + { 0.4515, 0.9167 }, + { 0.4487, 0.9408 }, + { 0.4459, 0.9651 }, + { 0.4431, 0.9894 }, + { 0.5733, 0.0700 }, + { 0.5705, 0.0941 }, + { 0.5677, 0.1184 }, + { 0.5649, 0.1427 }, + { 0.5621, 0.1671 }, + { 0.5593, 0.1914 }, + { 0.5566, 0.2154 }, + { 0.5538, 0.2397 }, + { 0.5510, 0.2641 }, + { 0.5482, 0.2884 }, + { 0.5454, 0.3128 }, + { 0.5426, 0.3368 }, + { 0.5398, 0.3611 }, + { 0.5371, 0.3854 }, + { 0.5343, 0.4098 }, + { 0.5315, 0.4341 }, + { 0.5287, 0.4581 }, + { 0.5259, 0.4825 }, + { 0.5231, 0.5068 }, + { 0.5203, 0.5311 }, + { 0.5175, 0.5555 }, + { 0.5148, 0.5795 }, + { 0.5120, 0.6038 }, + { 0.5092, 0.6282 }, + { 0.5064, 0.6525 }, + { 0.5036, 0.6768 }, + { 0.5008, 0.7008 }, + { 0.4980, 0.7252 }, + { 0.4952, 0.7495 }, + { 0.4924, 0.7738 }, + { 0.4896, 0.7982 }, + { 0.4869, 0.8222 }, + { 0.4841, 0.8465 }, + { 0.4813, 0.8709 }, + { 0.4785, 0.8952 }, + { 0.4757, 0.9195 }, + { 0.4729, 0.9436 }, + { 0.4702, 0.9679 }, + { 0.4674, 0.9922 }, + { 0.5975, 0.0728 }, + { 0.5948, 0.0968 }, + { 0.5920, 0.1212 }, + { 0.5892, 0.1455 }, + { 0.5864, 0.1698 }, + { 0.5836, 0.1942 }, + { 0.5808, 0.2182 }, + { 0.5780, 0.2425 }, + { 0.5752, 0.2669 }, + { 0.5725, 0.2912 }, + { 0.5697, 0.3155 }, + { 0.5669, 0.3396 }, + { 0.5641, 0.3639 }, + { 0.5613, 0.3882 }, + { 0.5585, 0.4126 }, + { 0.5557, 0.4369 }, + { 0.5530, 0.4609 }, + { 0.5502, 0.4852 }, + { 0.5474, 0.5096 }, + { 0.5446, 0.5339 }, + { 0.5418, 0.5583 }, + { 0.5390, 0.5823 }, + { 0.5362, 0.6066 }, + { 0.5334, 0.6309 }, + { 0.5306, 0.6553 }, + { 0.5278, 0.6796 }, + { 0.5251, 0.7036 }, + { 0.5223, 0.7280 }, + { 0.5195, 0.7523 }, + { 0.5167, 0.7766 }, + { 0.5139, 0.8010 }, + { 0.5111, 0.8250 }, + { 0.5083, 0.8493 }, + { 0.5056, 0.8737 }, + { 0.5028, 0.8980 }, + { 0.5000, 0.9223 }, + { 0.4972, 0.9463 }, + { 0.4944, 0.9707 }, + { 0.4916, 0.9950 }, + { 0.6218, 0.0756 }, + { 0.6191, 0.0996 }, + { 0.6163, 0.1240 }, + { 0.6135, 0.1483 }, + { 0.6107, 0.1726 }, + { 0.6079, 0.1970 }, + { 0.6051, 0.2210 }, + { 0.6023, 0.2453 }, + { 0.5995, 0.2697 }, + { 0.5967, 0.2940 }, + { 0.5940, 0.3183 }, + { 0.5912, 0.3423 }, + { 0.5884, 0.3667 }, + { 0.5856, 0.3910 }, + { 0.5828, 0.4153 }, + { 0.5800, 0.4397 }, + { 0.5773, 0.4637 }, + { 0.5745, 0.4880 }, + { 0.5717, 0.5124 }, + { 0.5689, 0.5367 }, + { 0.5661, 0.5610 }, + { 0.5633, 0.5851 }, + { 0.5605, 0.6094 }, + { 0.5577, 0.6337 }, + { 0.5549, 0.6581 }, + { 0.5521, 0.6824 }, + { 0.5494, 0.7064 }, + { 0.5466, 0.7308 }, + { 0.5438, 0.7551 }, + { 0.5410, 0.7794 }, + { 0.5382, 0.8038 }, + { 0.5354, 0.8278 }, + { 0.5326, 0.8521 }, + { 0.5298, 0.8764 }, + { 0.5271, 0.9008 }, + { 0.5243, 0.9251 }, + { 0.5215, 0.9491 }, + { 0.5187, 0.9735 }, + { 0.5159, 0.9978 }, + { 0.6461, 0.0784 }, + { 0.6433, 0.1024 }, + { 0.6405, 0.1268 }, + { 0.6377, 0.1511 }, + { 0.6349, 0.1754 }, + { 0.6321, 0.1998 }, + { 0.6294, 0.2238 }, + { 0.6266, 0.2481 }, + { 0.6238, 0.2724 }, + { 0.6210, 0.2968 }, + { 0.6182, 0.3211 }, + { 0.6154, 0.3451 }, + { 0.6127, 0.3695 }, + { 0.6099, 0.3938 }, + { 0.6071, 0.4181 }, + { 0.6043, 0.4425 }, + { 0.6015, 0.4665 }, + { 0.5987, 0.4908 }, + { 0.5959, 0.5152 }, + { 0.5931, 0.5395 }, + { 0.5903, 0.5638 }, + { 0.5876, 0.5878 }, + { 0.5848, 0.6122 }, + { 0.5820, 0.6365 }, + { 0.5792, 0.6608 }, + { 0.5764, 0.6852 }, + { 0.5736, 0.7092 }, + { 0.5708, 0.7335 }, + { 0.5680, 0.7579 }, + { 0.5652, 0.7822 }, + { 0.5625, 0.8065 }, + { 0.5597, 0.8306 }, + { 0.5569, 0.8549 }, + { 0.5541, 0.8792 }, + { 0.5513, 0.9036 }, + { 0.5485, 0.9279 }, + { 0.5458, 0.9519 }, + { 0.5430, 0.9762 }, + { 0.5402, 1.0006 }, + { 0.6704, 0.0812 }, + { 0.6676, 0.1052 }, + { 0.6648, 0.1295 }, + { 0.6620, 0.1539 }, + { 0.6592, 0.1782 }, + { 0.6564, 0.2025 }, + { 0.6537, 0.2266 }, + { 0.6509, 0.2509 }, + { 0.6481, 0.2752 }, + { 0.6453, 0.2996 }, + { 0.6425, 0.3239 }, + { 0.6397, 0.3479 }, + { 0.6369, 0.3723 }, + { 0.6342, 0.3966 }, + { 0.6314, 0.4209 }, + { 0.6286, 0.4453 }, + { 0.6258, 0.4693 }, + { 0.6230, 0.4936 }, + { 0.6202, 0.5179 }, + { 0.6174, 0.5423 }, + { 0.6146, 0.5666 }, + { 0.6119, 0.5906 }, + { 0.6091, 0.6150 }, + { 0.6063, 0.6393 }, + { 0.6035, 0.6636 }, + { 0.6007, 0.6880 }, + { 0.5979, 0.7120 }, + { 0.5951, 0.7363 }, + { 0.5923, 0.7607 }, + { 0.5895, 0.7850 }, + { 0.5867, 0.8093 }, + { 0.5840, 0.8333 }, + { 0.5812, 0.8577 }, + { 0.5784, 0.8820 }, + { 0.5756, 0.9064 }, + { 0.5728, 0.9307 }, + { 0.5701, 0.9547 }, + { 0.5673, 0.9790 }, + { 0.5645, 1.0034 }, + { 0.6946, 0.0840 }, + { 0.6919, 0.1080 }, + { 0.6891, 0.1323 }, + { 0.6863, 0.1567 }, + { 0.6835, 0.1810 }, + { 0.6807, 0.2053 }, + { 0.6779, 0.2294 }, + { 0.6751, 0.2537 }, + { 0.6723, 0.2780 }, + { 0.6696, 0.3024 }, + { 0.6668, 0.3267 }, + { 0.6640, 0.3507 }, + { 0.6612, 0.3750 }, + { 0.6584, 0.3994 }, + { 0.6556, 0.4237 }, + { 0.6528, 0.4480 }, + { 0.6501, 0.4721 }, + { 0.6473, 0.4964 }, + { 0.6445, 0.5207 }, + { 0.6417, 0.5451 }, + { 0.6389, 0.5694 }, + { 0.6361, 0.5934 }, + { 0.6333, 0.6178 }, + { 0.6305, 0.6421 }, + { 0.6277, 0.6664 }, + { 0.6249, 0.6908 }, + { 0.6222, 0.7148 }, + { 0.6194, 0.7391 }, + { 0.6166, 0.7634 }, + { 0.6138, 0.7878 }, + { 0.6110, 0.8121 }, + { 0.6082, 0.8361 }, + { 0.6055, 0.8605 }, + { 0.6027, 0.8848 }, + { 0.5999, 0.9091 }, + { 0.5971, 0.9335 }, + { 0.5943, 0.9575 }, + { 0.5915, 0.9818 }, + { 0.5887, 1.0062 }, + { 0.7189, 0.0868 }, + { 0.7161, 0.1108 }, + { 0.7133, 0.1351 }, + { 0.7105, 0.1595 }, + { 0.7077, 0.1838 }, + { 0.7050, 0.2081 }, + { 0.7022, 0.2321 }, + { 0.6994, 0.2565 }, + { 0.6966, 0.2808 }, + { 0.6938, 0.3051 }, + { 0.6910, 0.3295 }, + { 0.6883, 0.3535 }, + { 0.6855, 0.3778 }, + { 0.6827, 0.4022 }, + { 0.6799, 0.4265 }, + { 0.6771, 0.4508 }, + { 0.6743, 0.4749 }, + { 0.6715, 0.4992 }, + { 0.6687, 0.5235 }, + { 0.6659, 0.5479 }, + { 0.6631, 0.5722 }, + { 0.6604, 0.5962 }, + { 0.6576, 0.6205 }, + { 0.6548, 0.6449 }, + { 0.6520, 0.6692 }, + { 0.6492, 0.6935 }, + { 0.6464, 0.7176 }, + { 0.6436, 0.7419 }, + { 0.6408, 0.7662 }, + { 0.6381, 0.7906 }, + { 0.6353, 0.8149 }, + { 0.6325, 0.8389 }, + { 0.6297, 0.8633 }, + { 0.6269, 0.8876 }, + { 0.6241, 0.9119 }, + { 0.6213, 0.9363 }, + { 0.6186, 0.9603 }, + { 0.6158, 0.9846 }, + { 0.6130, 1.0089 }, + { 0.7432, 0.0896 }, + { 0.7404, 0.1136 }, + { 0.7376, 0.1379 }, + { 0.7348, 0.1622 }, + { 0.7320, 0.1866 }, + { 0.7292, 0.2109 }, + { 0.7265, 0.2349 }, + { 0.7237, 0.2593 }, + { 0.7209, 0.2836 }, + { 0.7181, 0.3079 }, + { 0.7153, 0.3323 }, + { 0.7126, 0.3563 }, + { 0.7098, 0.3806 }, + { 0.7070, 0.4050 }, + { 0.7042, 0.4293 }, + { 0.7014, 0.4536 }, + { 0.6986, 0.4776 }, + { 0.6958, 0.5020 }, + { 0.6930, 0.5263 }, + { 0.6902, 0.5506 }, + { 0.6874, 0.5750 }, + { 0.6847, 0.5990 }, + { 0.6819, 0.6233 }, + { 0.6791, 0.6477 }, + { 0.6763, 0.6720 }, + { 0.6735, 0.6963 }, + { 0.6707, 0.7204 }, + { 0.6679, 0.7447 }, + { 0.6651, 0.7690 }, + { 0.6623, 0.7934 }, + { 0.6596, 0.8177 }, + { 0.6568, 0.8417 }, + { 0.6540, 0.8660 }, + { 0.6512, 0.8904 }, + { 0.6484, 0.9147 }, + { 0.6456, 0.9390 }, + { 0.6429, 0.9631 }, + { 0.6401, 0.9874 }, + { 0.6373, 1.0117 }, + { 0.7674, 0.0923 }, + { 0.7647, 0.1164 }, + { 0.7619, 0.1407 }, + { 0.7591, 0.1650 }, + { 0.7563, 0.1894 }, + { 0.7535, 0.2137 }, + { 0.7507, 0.2377 }, + { 0.7479, 0.2620 }, + { 0.7452, 0.2864 }, + { 0.7424, 0.3107 }, + { 0.7396, 0.3351 }, + { 0.7368, 0.3591 }, + { 0.7340, 0.3834 }, + { 0.7312, 0.4077 }, + { 0.7284, 0.4321 }, + { 0.7256, 0.4564 }, + { 0.7229, 0.4804 }, + { 0.7201, 0.5048 }, + { 0.7173, 0.5291 }, + { 0.7145, 0.5534 }, + { 0.7117, 0.5778 }, + { 0.7089, 0.6018 }, + { 0.7061, 0.6261 }, + { 0.7033, 0.6505 }, + { 0.7005, 0.6748 }, + { 0.6977, 0.6991 }, + { 0.6950, 0.7231 }, + { 0.6922, 0.7475 }, + { 0.6894, 0.7718 }, + { 0.6866, 0.7961 }, + { 0.6838, 0.8205 }, + { 0.6811, 0.8445 }, + { 0.6783, 0.8688 }, + { 0.6755, 0.8932 }, + { 0.6727, 0.9175 }, + { 0.6699, 0.9418 }, + { 0.6671, 0.9659 }, + { 0.6643, 0.9902 }, + { 0.6615, 1.0145 }, + { 0.7917, 0.0951 }, + { 0.7890, 0.1191 }, + { 0.7862, 0.1435 }, + { 0.7834, 0.1678 }, + { 0.7806, 0.1922 }, + { 0.7778, 0.2165 }, + { 0.7750, 0.2405 }, + { 0.7722, 0.2648 }, + { 0.7694, 0.2892 }, + { 0.7667, 0.3135 }, + { 0.7639, 0.3378 }, + { 0.7611, 0.3619 }, + { 0.7583, 0.3862 }, + { 0.7555, 0.4105 }, + { 0.7527, 0.4349 }, + { 0.7499, 0.4592 }, + { 0.7472, 0.4832 }, + { 0.7444, 0.5076 }, + { 0.7416, 0.5319 }, + { 0.7388, 0.5562 }, + { 0.7360, 0.5806 }, + { 0.7332, 0.6046 }, + { 0.7304, 0.6289 }, + { 0.7276, 0.6532 }, + { 0.7248, 0.6776 }, + { 0.7220, 0.7019 }, + { 0.7193, 0.7259 }, + { 0.7165, 0.7503 }, + { 0.7137, 0.7746 }, + { 0.7109, 0.7989 }, + { 0.7081, 0.8233 }, + { 0.7053, 0.8473 }, + { 0.7026, 0.8716 }, + { 0.6998, 0.8960 }, + { 0.6970, 0.9203 }, + { 0.6942, 0.9446 }, + { 0.6914, 0.9686 }, + { 0.6886, 0.9930 }, + { 0.6858, 1.0173 }, + { 0.8160, 0.0979 }, + { 0.8132, 0.1219 }, + { 0.8104, 0.1463 }, + { 0.8076, 0.1706 }, + { 0.8048, 0.1949 }, + { 0.8021, 0.2193 }, + { 0.7993, 0.2433 }, + { 0.7965, 0.2676 }, + { 0.7937, 0.2920 }, + { 0.7909, 0.3163 }, + { 0.7881, 0.3406 }, + { 0.7854, 0.3646 }, + { 0.7826, 0.3890 }, + { 0.7798, 0.4133 }, + { 0.7770, 0.4377 }, + { 0.7742, 0.4620 }, + { 0.7714, 0.4860 }, + { 0.7686, 0.5103 }, + { 0.7658, 0.5347 }, + { 0.7630, 0.5590 }, + { 0.7602, 0.5833 }, + { 0.7575, 0.6074 }, + { 0.7547, 0.6317 }, + { 0.7519, 0.6560 }, + { 0.7491, 0.6804 }, + { 0.7463, 0.7047 }, + { 0.7435, 0.7287 }, + { 0.7407, 0.7531 }, + { 0.7380, 0.7774 }, + { 0.7352, 0.8017 }, + { 0.7324, 0.8261 }, + { 0.7296, 0.8501 }, + { 0.7268, 0.8744 }, + { 0.7240, 0.8987 }, + { 0.7212, 0.9231 }, + { 0.7184, 0.9474 }, + { 0.7157, 0.9714 }, + { 0.7129, 0.9958 }, + { 0.7101, 1.0201 }, + { 0.8402, 0.1007 }, + { 0.8375, 0.1247 }, + { 0.8347, 0.1491 }, + { 0.8319, 0.1734 }, + { 0.8291, 0.1977 }, + { 0.8263, 0.2221 }, + { 0.8236, 0.2461 }, + { 0.8208, 0.2704 }, + { 0.8180, 0.2947 }, + { 0.8152, 0.3191 }, + { 0.8124, 0.3434 }, + { 0.8096, 0.3674 }, + { 0.8068, 0.3918 }, + { 0.8040, 0.4161 }, + { 0.8012, 0.4404 }, + { 0.7984, 0.4648 }, + { 0.7957, 0.4888 }, + { 0.7929, 0.5131 }, + { 0.7901, 0.5375 }, + { 0.7873, 0.5618 }, + { 0.7845, 0.5861 }, + { 0.7817, 0.6101 }, + { 0.7789, 0.6345 }, + { 0.7761, 0.6588 }, + { 0.7733, 0.6831 }, + { 0.7706, 0.7075 }, + { 0.7678, 0.7315 }, + { 0.7650, 0.7558 }, + { 0.7622, 0.7802 }, + { 0.7594, 0.8045 }, + { 0.7566, 0.8288 }, + { 0.7539, 0.8529 }, + { 0.7511, 0.8772 }, + { 0.7483, 0.9015 }, + { 0.7455, 0.9259 }, + { 0.7427, 0.9502 }, + { 0.7399, 0.9742 }, + { 0.7371, 0.9986 }, + { 0.7343, 1.0229 }, + { 0.8645, 0.1035 }, + { 0.8618, 0.1275 }, + { 0.8590, 0.1518 }, + { 0.8562, 0.1762 }, + { 0.8534, 0.2005 }, + { 0.8506, 0.2248 }, + { 0.8478, 0.2489 }, + { 0.8451, 0.2732 }, + { 0.8423, 0.2975 }, + { 0.8395, 0.3219 }, + { 0.8367, 0.3462 }, + { 0.8339, 0.3702 }, + { 0.8311, 0.3946 }, + { 0.8283, 0.4189 }, + { 0.8255, 0.4432 }, + { 0.8227, 0.4676 }, + { 0.8200, 0.4916 }, + { 0.8172, 0.5159 }, + { 0.8144, 0.5402 }, + { 0.8116, 0.5646 }, + { 0.8088, 0.5889 }, + { 0.8060, 0.6129 }, + { 0.8032, 0.6373 }, + { 0.8004, 0.6616 }, + { 0.7976, 0.6859 }, + { 0.7948, 0.7103 }, + { 0.7921, 0.7343 }, + { 0.7893, 0.7586 }, + { 0.7865, 0.7830 }, + { 0.7837, 0.8073 }, + { 0.7809, 0.8316 }, + { 0.7782, 0.8556 }, + { 0.7754, 0.8800 }, + { 0.7726, 0.9043 }, + { 0.7698, 0.9287 }, + { 0.7670, 0.9530 }, + { 0.7642, 0.9770 }, + { 0.7614, 1.0013 }, + { 0.7586, 1.0257 }, + { 0.8888, 0.1063 }, + { 0.8860, 0.1303 }, + { 0.8832, 0.1546 }, + { 0.8805, 0.1790 }, + { 0.8777, 0.2033 }, + { 0.8749, 0.2276 }, + { 0.8721, 0.2517 }, + { 0.8693, 0.2760 }, + { 0.8665, 0.3003 }, + { 0.8637, 0.3247 }, + { 0.8609, 0.3490 }, + { 0.8582, 0.3730 }, + { 0.8554, 0.3973 }, + { 0.8526, 0.4217 }, + { 0.8498, 0.4460 }, + { 0.8470, 0.4703 }, + { 0.8442, 0.4944 }, + { 0.8414, 0.5187 }, + { 0.8386, 0.5430 }, + { 0.8358, 0.5674 }, + { 0.8330, 0.5917 }, + { 0.8303, 0.6157 }, + { 0.8275, 0.6401 }, + { 0.8247, 0.6644 }, + { 0.8219, 0.6887 }, + { 0.8191, 0.7131 }, + { 0.8163, 0.7371 }, + { 0.8136, 0.7614 }, + { 0.8108, 0.7857 }, + { 0.8080, 0.8101 }, + { 0.8052, 0.8344 }, + { 0.8024, 0.8584 }, + { 0.7996, 0.8828 }, + { 0.7968, 0.9071 }, + { 0.7940, 0.9314 }, + { 0.7912, 0.9558 }, + { 0.7885, 0.9798 }, + { 0.7857, 1.0041 }, + { 0.7829, 1.0285 }, + { 0.9131, 0.1091 }, + { 0.9103, 0.1331 }, + { 0.9075, 0.1574 }, + { 0.9047, 0.1818 }, + { 0.9020, 0.2061 }, + { 0.8992, 0.2304 }, + { 0.8964, 0.2544 }, + { 0.8936, 0.2788 }, + { 0.8908, 0.3031 }, + { 0.8880, 0.3274 }, + { 0.8852, 0.3518 }, + { 0.8825, 0.3758 }, + { 0.8797, 0.4001 }, + { 0.8769, 0.4245 }, + { 0.8741, 0.4488 }, + { 0.8713, 0.4731 }, + { 0.8685, 0.4972 }, + { 0.8657, 0.5215 }, + { 0.8629, 0.5458 }, + { 0.8601, 0.5702 }, + { 0.8573, 0.5945 }, + { 0.8546, 0.6185 }, + { 0.8518, 0.6428 }, + { 0.8490, 0.6672 }, + { 0.8462, 0.6915 }, + { 0.8434, 0.7159 }, + { 0.8406, 0.7399 }, + { 0.8378, 0.7642 }, + { 0.8351, 0.7885 }, + { 0.8323, 0.8129 }, + { 0.8295, 0.8372 }, + { 0.8267, 0.8612 }, + { 0.8239, 0.8856 }, + { 0.8211, 0.9099 }, + { 0.8183, 0.9342 }, + { 0.8155, 0.9586 }, + { 0.8128, 0.9826 }, + { 0.8100, 1.0069 }, + { 0.8072, 1.0313 }, + { 0.9373, 0.1119 }, + { 0.9346, 0.1359 }, + { 0.9318, 0.1602 }, + { 0.9290, 0.1845 }, + { 0.9262, 0.2089 }, + { 0.9234, 0.2332 }, + { 0.9207, 0.2572 }, + { 0.9179, 0.2816 }, + { 0.9151, 0.3059 }, + { 0.9123, 0.3302 }, + { 0.9095, 0.3546 }, + { 0.9067, 0.3786 }, + { 0.9039, 0.4029 }, + { 0.9011, 0.4273 }, + { 0.8983, 0.4516 }, + { 0.8955, 0.4759 }, + { 0.8928, 0.4999 }, + { 0.8900, 0.5243 }, + { 0.8872, 0.5486 }, + { 0.8844, 0.5729 }, + { 0.8816, 0.5973 }, + { 0.8788, 0.6213 }, + { 0.8760, 0.6456 }, + { 0.8732, 0.6700 }, + { 0.8705, 0.6943 }, + { 0.8677, 0.7186 }, + { 0.8649, 0.7427 }, + { 0.8621, 0.7670 }, + { 0.8593, 0.7913 }, + { 0.8565, 0.8157 }, + { 0.8537, 0.8400 }, + { 0.8510, 0.8640 }, + { 0.8482, 0.8883 }, + { 0.8454, 0.9127 }, + { 0.8426, 0.9370 }, + { 0.8398, 0.9614 }, + { 0.8370, 0.9854 }, + { 0.8342, 1.0097 }, + { 0.8314, 1.0340 }, + { 0.9616, 0.1146 }, + { 0.9588, 0.1387 }, + { 0.9561, 0.1630 }, + { 0.9533, 0.1873 }, + { 0.9505, 0.2117 }, + { 0.9477, 0.2360 }, + { 0.9449, 0.2600 }, + { 0.9421, 0.2844 }, + { 0.9393, 0.3087 }, + { 0.9365, 0.3330 }, + { 0.9337, 0.3574 }, + { 0.9310, 0.3814 }, + { 0.9282, 0.4057 }, + { 0.9254, 0.4300 }, + { 0.9226, 0.4544 }, + { 0.9198, 0.4787 }, + { 0.9170, 0.5027 }, + { 0.9142, 0.5271 }, + { 0.9114, 0.5514 }, + { 0.9086, 0.5757 }, + { 0.9058, 0.6001 }, + { 0.9031, 0.6241 }, + { 0.9003, 0.6484 }, + { 0.8975, 0.6728 }, + { 0.8947, 0.6971 }, + { 0.8919, 0.7214 }, + { 0.8892, 0.7454 }, + { 0.8864, 0.7698 }, + { 0.8836, 0.7941 }, + { 0.8808, 0.8184 }, + { 0.8780, 0.8428 }, + { 0.8752, 0.8668 }, + { 0.8724, 0.8911 }, + { 0.8696, 0.9155 }, + { 0.8668, 0.9398 }, + { 0.8640, 0.9641 }, + { 0.8613, 0.9882 }, + { 0.8585, 1.0125 }, + { 0.8557, 1.0368 }, + { 0.9831, 0.1414 }, + { 0.9803, 0.1658 }, + { 0.9776, 0.1901 }, + { 0.9748, 0.2145 }, + { 0.9720, 0.2388 }, + { 0.9692, 0.2628 }, + { 0.9664, 0.2871 }, + { 0.9636, 0.3115 }, + { 0.9608, 0.3358 }, + { 0.9580, 0.3601 }, + { 0.9553, 0.3842 }, + { 0.9525, 0.4085 }, + { 0.9497, 0.4328 }, + { 0.9469, 0.4572 }, + { 0.9441, 0.4815 }, + { 0.9413, 0.5055 }, + { 0.9385, 0.5299 }, + { 0.9357, 0.5542 }, + { 0.9329, 0.5785 }, + { 0.9301, 0.6029 }, + { 0.9274, 0.6269 }, + { 0.9246, 0.6512 }, + { 0.9218, 0.6755 }, + { 0.9190, 0.6999 }, + { 0.9162, 0.7242 }, + { 0.9134, 0.7482 }, + { 0.9107, 0.7726 }, + { 0.9079, 0.7969 }, + { 0.9051, 0.8212 }, + { 0.9023, 0.8456 }, + { 0.8995, 0.8696 }, + { 0.8967, 0.8939 }, + { 0.8939, 0.9183 }, + { 0.8911, 0.9426 }, + { 0.8883, 0.9669 }, + { 0.8856, 0.9909 }, + { 0.8828, 1.0153 }, + { 0.8800, 1.0396 }, + { 0.8772, 1.0639 }, + { 1.0074, 0.1442 }, + { 1.0046, 0.1686 }, + { 1.0018, 0.1929 }, + { 0.9990, 0.2172 }, + { 0.9962, 0.2416 }, + { 0.9935, 0.2656 }, + { 0.9907, 0.2899 }, + { 0.9879, 0.3143 }, + { 0.9851, 0.3386 }, + { 0.9823, 0.3629 }, + { 0.9795, 0.3869 }, + { 0.9767, 0.4113 }, + { 0.9739, 0.4356 }, + { 0.9711, 0.4600 }, + { 0.9683, 0.4843 }, + { 0.9656, 0.5083 }, + { 0.9628, 0.5326 }, + { 0.9600, 0.5570 }, + { 0.9572, 0.5813 }, + { 0.9544, 0.6056 }, + { 0.9516, 0.6297 }, + { 0.9488, 0.6540 }, + { 0.9461, 0.6783 }, + { 0.9433, 0.7027 }, + { 0.9405, 0.7270 }, + { 0.9377, 0.7510 }, + { 0.9349, 0.7754 }, + { 0.9321, 0.7997 }, + { 0.9293, 0.8240 }, + { 0.9265, 0.8484 }, + { 0.9238, 0.8724 }, + { 0.9210, 0.8967 }, + { 0.9182, 0.9210 }, + { 0.9154, 0.9454 }, + { 0.9126, 0.9697 }, + { 0.9098, 0.9937 }, + { 0.9070, 1.0181 }, + { 0.9042, 1.0424 }, + { 0.9014, 1.0667 }, +#endif /* ] */ + + { 0.0871, 0.0171 }, + { 0.0844, 0.0411 }, + { 0.0816, 0.0654 }, + { 0.0788, 0.0898 }, + { 0.0760, 0.1141 }, + { 0.0732, 0.1384 }, + { 0.0704, 0.1624 }, + { 0.0676, 0.1868 }, + { 0.0648, 0.2111 }, + { 0.0620, 0.2354 }, + { 0.0592, 0.2598 }, + { 0.0565, 0.2838 }, + { 0.0537, 0.3081 }, + { 0.0509, 0.3325 }, + { 0.0481, 0.3568 }, + { 0.0453, 0.3811 }, + { 0.0425, 0.4052 }, + { 0.0397, 0.4295 }, + { 0.0369, 0.4538 }, + { 0.0341, 0.4782 }, + { 0.0314, 0.5025 }, + { 0.0286, 0.5265 }, + { 0.0258, 0.5508 }, + { 0.0230, 0.5752 }, + { 0.0202, 0.5995 }, + { 0.0174, 0.6239 }, + { 0.0147, 0.6479 }, + { 0.0119, 0.6722 }, + { 0.0091, 0.6965 }, + { 0.0063, 0.7209 }, + { 0.0035, 0.7452 }, + { 0.0007, 0.7692 }, + { -0.0021, 0.7936 }, + { -0.0049, 0.8179 }, + { -0.0077, 0.8422 }, + { -0.0105, 0.8666 }, + { -0.0132, 0.8906 }, + { -0.0160, 0.9149 }, + { -0.0188, 0.9393 }, + { 0.1114, 0.0199 }, + { 0.1086, 0.0439 }, + { 0.1059, 0.0682 }, + { 0.1031, 0.0925 }, + { 0.1003, 0.1169 }, + { 0.0975, 0.1412 }, + { 0.0947, 0.1652 }, + { 0.0919, 0.1896 }, + { 0.0891, 0.2139 }, + { 0.0863, 0.2382 }, + { 0.0835, 0.2626 }, + { 0.0808, 0.2866 }, + { 0.0780, 0.3109 }, + { 0.0752, 0.3353 }, + { 0.0724, 0.3596 }, + { 0.0696, 0.3839 }, + { 0.0668, 0.4079 }, + { 0.0640, 0.4323 }, + { 0.0612, 0.4566 }, + { 0.0584, 0.4810 }, + { 0.0556, 0.5053 }, + { 0.0529, 0.5293 }, + { 0.0501, 0.5536 }, + { 0.0473, 0.5780 }, + { 0.0445, 0.6023 }, + { 0.0417, 0.6266 }, + { 0.0390, 0.6507 }, + { 0.0362, 0.6750 }, + { 0.0334, 0.6993 }, + { 0.0306, 0.7237 }, + { 0.0278, 0.7480 }, + { 0.0250, 0.7720 }, + { 0.0222, 0.7964 }, + { 0.0194, 0.8207 }, + { 0.0166, 0.8450 }, + { 0.0138, 0.8694 }, + { 0.0111, 0.8934 }, + { 0.0083, 0.9177 }, + { 0.0055, 0.9420 }, + { 0.1357, 0.0226 }, + { 0.1329, 0.0467 }, + { 0.1301, 0.0710 }, + { 0.1273, 0.0953 }, + { 0.1245, 0.1197 }, + { 0.1217, 0.1440 }, + { 0.1190, 0.1680 }, + { 0.1162, 0.1924 }, + { 0.1134, 0.2167 }, + { 0.1106, 0.2410 }, + { 0.1078, 0.2654 }, + { 0.1050, 0.2894 }, + { 0.1022, 0.3137 }, + { 0.0994, 0.3380 }, + { 0.0966, 0.3624 }, + { 0.0938, 0.3867 }, + { 0.0911, 0.4107 }, + { 0.0883, 0.4351 }, + { 0.0855, 0.4594 }, + { 0.0827, 0.4837 }, + { 0.0799, 0.5081 }, + { 0.0771, 0.5321 }, + { 0.0744, 0.5564 }, + { 0.0716, 0.5808 }, + { 0.0688, 0.6051 }, + { 0.0660, 0.6294 }, + { 0.0632, 0.6534 }, + { 0.0604, 0.6778 }, + { 0.0576, 0.7021 }, + { 0.0548, 0.7265 }, + { 0.0520, 0.7508 }, + { 0.0493, 0.7748 }, + { 0.0465, 0.7991 }, + { 0.0437, 0.8235 }, + { 0.0409, 0.8478 }, + { 0.0381, 0.8721 }, + { 0.0353, 0.8962 }, + { 0.0325, 0.9205 }, + { 0.0297, 0.9448 }, + { 0.1600, 0.0254 }, + { 0.1572, 0.0495 }, + { 0.1544, 0.0738 }, + { 0.1516, 0.0981 }, + { 0.1488, 0.1225 }, + { 0.1460, 0.1468 }, + { 0.1433, 0.1708 }, + { 0.1405, 0.1951 }, + { 0.1377, 0.2195 }, + { 0.1349, 0.2438 }, + { 0.1321, 0.2681 }, + { 0.1293, 0.2922 }, + { 0.1265, 0.3165 }, + { 0.1237, 0.3408 }, + { 0.1209, 0.3652 }, + { 0.1181, 0.3895 }, + { 0.1154, 0.4135 }, + { 0.1126, 0.4379 }, + { 0.1098, 0.4622 }, + { 0.1070, 0.4865 }, + { 0.1042, 0.5109 }, + { 0.1014, 0.5349 }, + { 0.0986, 0.5592 }, + { 0.0959, 0.5835 }, + { 0.0931, 0.6079 }, + { 0.0903, 0.6322 }, + { 0.0875, 0.6562 }, + { 0.0847, 0.6806 }, + { 0.0819, 0.7049 }, + { 0.0791, 0.7292 }, + { 0.0763, 0.7536 }, + { 0.0736, 0.7776 }, + { 0.0708, 0.8019 }, + { 0.0680, 0.8263 }, + { 0.0652, 0.8506 }, + { 0.0624, 0.8749 }, + { 0.0596, 0.8990 }, + { 0.0568, 0.9233 }, + { 0.0540, 0.9476 }, + { 0.1842, 0.0282 }, + { 0.1815, 0.0522 }, + { 0.1787, 0.0766 }, + { 0.1759, 0.1009 }, + { 0.1731, 0.1252 }, + { 0.1703, 0.1496 }, + { 0.1675, 0.1736 }, + { 0.1647, 0.1979 }, + { 0.1619, 0.2223 }, + { 0.1591, 0.2466 }, + { 0.1563, 0.2709 }, + { 0.1536, 0.2950 }, + { 0.1508, 0.3193 }, + { 0.1480, 0.3436 }, + { 0.1452, 0.3680 }, + { 0.1424, 0.3923 }, + { 0.1396, 0.4163 }, + { 0.1368, 0.4406 }, + { 0.1340, 0.4650 }, + { 0.1313, 0.4893 }, + { 0.1285, 0.5136 }, + { 0.1257, 0.5377 }, + { 0.1229, 0.5620 }, + { 0.1201, 0.5863 }, + { 0.1173, 0.6107 }, + { 0.1145, 0.6350 }, + { 0.1118, 0.6590 }, + { 0.1090, 0.6834 }, + { 0.1062, 0.7077 }, + { 0.1034, 0.7320 }, + { 0.1006, 0.7564 }, + { 0.0978, 0.7804 }, + { 0.0950, 0.8047 }, + { 0.0922, 0.8290 }, + { 0.0894, 0.8534 }, + { 0.0866, 0.8777 }, + { 0.0839, 0.9017 }, + { 0.0811, 0.9261 }, + { 0.0783, 0.9504 }, + { 0.2085, 0.0310 }, + { 0.2057, 0.0550 }, + { 0.2029, 0.0794 }, + { 0.2001, 0.1037 }, + { 0.1973, 0.1280 }, + { 0.1945, 0.1524 }, + { 0.1918, 0.1764 }, + { 0.1890, 0.2007 }, + { 0.1862, 0.2251 }, + { 0.1834, 0.2494 }, + { 0.1806, 0.2737 }, + { 0.1778, 0.2977 }, + { 0.1750, 0.3221 }, + { 0.1722, 0.3464 }, + { 0.1694, 0.3707 }, + { 0.1666, 0.3951 }, + { 0.1639, 0.4191 }, + { 0.1611, 0.4434 }, + { 0.1583, 0.4678 }, + { 0.1555, 0.4921 }, + { 0.1527, 0.5164 }, + { 0.1500, 0.5405 }, + { 0.1472, 0.5648 }, + { 0.1444, 0.5891 }, + { 0.1416, 0.6135 }, + { 0.1388, 0.6378 }, + { 0.1360, 0.6618 }, + { 0.1332, 0.6861 }, + { 0.1304, 0.7105 }, + { 0.1276, 0.7348 }, + { 0.1248, 0.7591 }, + { 0.1221, 0.7832 }, + { 0.1193, 0.8075 }, + { 0.1165, 0.8318 }, + { 0.1137, 0.8562 }, + { 0.1109, 0.8805 }, + { 0.1081, 0.9045 }, + { 0.1053, 0.9289 }, + { 0.1025, 0.9532 }, + { 0.2328, 0.0338 }, + { 0.2300, 0.0578 }, + { 0.2272, 0.0822 }, + { 0.2244, 0.1065 }, + { 0.2216, 0.1308 }, + { 0.2188, 0.1552 }, + { 0.2161, 0.1792 }, + { 0.2133, 0.2035 }, + { 0.2105, 0.2278 }, + { 0.2077, 0.2522 }, + { 0.2049, 0.2765 }, + { 0.2021, 0.3005 }, + { 0.1993, 0.3249 }, + { 0.1965, 0.3492 }, + { 0.1937, 0.3735 }, + { 0.1909, 0.3979 }, + { 0.1882, 0.4219 }, + { 0.1854, 0.4462 }, + { 0.1826, 0.4706 }, + { 0.1798, 0.4949 }, + { 0.1770, 0.5192 }, + { 0.1742, 0.5432 }, + { 0.1715, 0.5676 }, + { 0.1687, 0.5919 }, + { 0.1659, 0.6162 }, + { 0.1631, 0.6406 }, + { 0.1603, 0.6646 }, + { 0.1575, 0.6889 }, + { 0.1547, 0.7133 }, + { 0.1519, 0.7376 }, + { 0.1491, 0.7619 }, + { 0.1464, 0.7860 }, + { 0.1436, 0.8103 }, + { 0.1408, 0.8346 }, + { 0.1380, 0.8590 }, + { 0.1352, 0.8833 }, + { 0.1324, 0.9073 }, + { 0.1296, 0.9316 }, + { 0.1268, 0.9560 }, + { 0.2570, 0.0366 }, + { 0.2543, 0.0606 }, + { 0.2515, 0.0849 }, + { 0.2487, 0.1093 }, + { 0.2459, 0.1336 }, + { 0.2431, 0.1579 }, + { 0.2403, 0.1820 }, + { 0.2375, 0.2063 }, + { 0.2347, 0.2306 }, + { 0.2319, 0.2550 }, + { 0.2291, 0.2793 }, + { 0.2264, 0.3033 }, + { 0.2236, 0.3277 }, + { 0.2208, 0.3520 }, + { 0.2180, 0.3763 }, + { 0.2152, 0.4007 }, + { 0.2124, 0.4247 }, + { 0.2096, 0.4490 }, + { 0.2069, 0.4733 }, + { 0.2041, 0.4977 }, + { 0.2013, 0.5220 }, + { 0.1985, 0.5460 }, + { 0.1957, 0.5704 }, + { 0.1929, 0.5947 }, + { 0.1901, 0.6190 }, + { 0.1873, 0.6434 }, + { 0.1846, 0.6674 }, + { 0.1818, 0.6917 }, + { 0.1790, 0.7161 }, + { 0.1762, 0.7404 }, + { 0.1734, 0.7647 }, + { 0.1706, 0.7887 }, + { 0.1678, 0.8131 }, + { 0.1650, 0.8374 }, + { 0.1622, 0.8617 }, + { 0.1594, 0.8861 }, + { 0.1567, 0.9101 }, + { 0.1539, 0.9344 }, + { 0.1511, 0.9588 }, + { 0.2813, 0.0394 }, + { 0.2786, 0.0634 }, + { 0.2758, 0.0877 }, + { 0.2730, 0.1121 }, + { 0.2702, 0.1364 }, + { 0.2674, 0.1607 }, + { 0.2646, 0.1848 }, + { 0.2618, 0.2091 }, + { 0.2590, 0.2334 }, + { 0.2562, 0.2578 }, + { 0.2534, 0.2821 }, + { 0.2507, 0.3061 }, + { 0.2479, 0.3304 }, + { 0.2451, 0.3548 }, + { 0.2423, 0.3791 }, + { 0.2395, 0.4034 }, + { 0.2367, 0.4275 }, + { 0.2339, 0.4518 }, + { 0.2311, 0.4761 }, + { 0.2284, 0.5005 }, + { 0.2256, 0.5248 }, + { 0.2228, 0.5488 }, + { 0.2200, 0.5732 }, + { 0.2172, 0.5975 }, + { 0.2144, 0.6218 }, + { 0.2116, 0.6462 }, + { 0.2089, 0.6702 }, + { 0.2061, 0.6945 }, + { 0.2033, 0.7188 }, + { 0.2005, 0.7432 }, + { 0.1977, 0.7675 }, + { 0.1949, 0.7915 }, + { 0.1921, 0.8159 }, + { 0.1893, 0.8402 }, + { 0.1865, 0.8645 }, + { 0.1837, 0.8889 }, + { 0.1810, 0.9129 }, + { 0.1782, 0.9372 }, + { 0.1754, 0.9616 }, + { 0.3056, 0.0422 }, + { 0.3028, 0.0662 }, + { 0.3000, 0.0905 }, + { 0.2972, 0.1148 }, + { 0.2944, 0.1392 }, + { 0.2916, 0.1635 }, + { 0.2889, 0.1875 }, + { 0.2861, 0.2119 }, + { 0.2833, 0.2362 }, + { 0.2805, 0.2605 }, + { 0.2777, 0.2849 }, + { 0.2749, 0.3089 }, + { 0.2721, 0.3332 }, + { 0.2693, 0.3576 }, + { 0.2665, 0.3819 }, + { 0.2638, 0.4062 }, + { 0.2610, 0.4302 }, + { 0.2582, 0.4546 }, + { 0.2554, 0.4789 }, + { 0.2526, 0.5033 }, + { 0.2498, 0.5276 }, + { 0.2471, 0.5516 }, + { 0.2443, 0.5759 }, + { 0.2415, 0.6003 }, + { 0.2387, 0.6246 }, + { 0.2359, 0.6489 }, + { 0.2331, 0.6730 }, + { 0.2303, 0.6973 }, + { 0.2275, 0.7216 }, + { 0.2247, 0.7460 }, + { 0.2219, 0.7703 }, + { 0.2192, 0.7943 }, + { 0.2164, 0.8187 }, + { 0.2136, 0.8430 }, + { 0.2108, 0.8673 }, + { 0.2080, 0.8917 }, + { 0.2052, 0.9157 }, + { 0.2024, 0.9400 }, + { 0.1996, 0.9643 }, + { 0.3298, 0.0449 }, + { 0.3271, 0.0690 }, + { 0.3243, 0.0933 }, + { 0.3215, 0.1176 }, + { 0.3187, 0.1420 }, + { 0.3159, 0.1663 }, + { 0.3131, 0.1903 }, + { 0.3103, 0.2147 }, + { 0.3075, 0.2390 }, + { 0.3047, 0.2633 }, + { 0.3019, 0.2877 }, + { 0.2992, 0.3117 }, + { 0.2964, 0.3360 }, + { 0.2936, 0.3603 }, + { 0.2908, 0.3847 }, + { 0.2880, 0.4090 }, + { 0.2852, 0.4330 }, + { 0.2825, 0.4574 }, + { 0.2797, 0.4817 }, + { 0.2769, 0.5060 }, + { 0.2741, 0.5304 }, + { 0.2713, 0.5544 }, + { 0.2685, 0.5787 }, + { 0.2657, 0.6031 }, + { 0.2629, 0.6274 }, + { 0.2601, 0.6517 }, + { 0.2574, 0.6757 }, + { 0.2546, 0.7001 }, + { 0.2518, 0.7244 }, + { 0.2490, 0.7488 }, + { 0.2462, 0.7731 }, + { 0.2434, 0.7971 }, + { 0.2406, 0.8214 }, + { 0.2378, 0.8458 }, + { 0.2350, 0.8701 }, + { 0.2323, 0.8944 }, + { 0.2295, 0.9185 }, + { 0.2267, 0.9428 }, + { 0.2239, 0.9671 }, + { 0.3541, 0.0477 }, + { 0.3514, 0.0718 }, + { 0.3486, 0.0961 }, + { 0.3458, 0.1204 }, + { 0.3430, 0.1448 }, + { 0.3402, 0.1691 }, + { 0.3374, 0.1931 }, + { 0.3346, 0.2174 }, + { 0.3318, 0.2418 }, + { 0.3290, 0.2661 }, + { 0.3262, 0.2905 }, + { 0.3235, 0.3145 }, + { 0.3207, 0.3388 }, + { 0.3179, 0.3631 }, + { 0.3151, 0.3875 }, + { 0.3123, 0.4118 }, + { 0.3095, 0.4358 }, + { 0.3067, 0.4602 }, + { 0.3040, 0.4845 }, + { 0.3012, 0.5088 }, + { 0.2984, 0.5332 }, + { 0.2956, 0.5572 }, + { 0.2928, 0.5815 }, + { 0.2900, 0.6059 }, + { 0.2872, 0.6302 }, + { 0.2844, 0.6545 }, + { 0.2817, 0.6785 }, + { 0.2789, 0.7029 }, + { 0.2761, 0.7272 }, + { 0.2733, 0.7515 }, + { 0.2705, 0.7759 }, + { 0.2677, 0.7999 }, + { 0.2649, 0.8242 }, + { 0.2621, 0.8486 }, + { 0.2593, 0.8729 }, + { 0.2565, 0.8972 }, + { 0.2538, 0.9213 }, + { 0.2510, 0.9456 }, + { 0.2482, 0.9699 }, + { 0.3784, 0.0505 }, + { 0.3756, 0.0745 }, + { 0.3728, 0.0989 }, + { 0.3700, 0.1232 }, + { 0.3672, 0.1475 }, + { 0.3644, 0.1719 }, + { 0.3617, 0.1959 }, + { 0.3589, 0.2202 }, + { 0.3561, 0.2446 }, + { 0.3533, 0.2689 }, + { 0.3505, 0.2932 }, + { 0.3477, 0.3173 }, + { 0.3449, 0.3416 }, + { 0.3421, 0.3659 }, + { 0.3394, 0.3903 }, + { 0.3366, 0.4146 }, + { 0.3338, 0.4386 }, + { 0.3310, 0.4629 }, + { 0.3282, 0.4873 }, + { 0.3254, 0.5116 }, + { 0.3226, 0.5359 }, + { 0.3199, 0.5600 }, + { 0.3171, 0.5843 }, + { 0.3143, 0.6086 }, + { 0.3115, 0.6330 }, + { 0.3087, 0.6573 }, + { 0.3059, 0.6813 }, + { 0.3031, 0.7057 }, + { 0.3003, 0.7300 }, + { 0.2975, 0.7543 }, + { 0.2947, 0.7787 }, + { 0.2920, 0.8027 }, + { 0.2892, 0.8270 }, + { 0.2864, 0.8513 }, + { 0.2836, 0.8757 }, + { 0.2808, 0.9000 }, + { 0.2780, 0.9240 }, + { 0.2752, 0.9484 }, + { 0.2725, 0.9727 }, + { 0.4027, 0.0533 }, + { 0.3999, 0.0773 }, + { 0.3971, 0.1017 }, + { 0.3943, 0.1260 }, + { 0.3915, 0.1503 }, + { 0.3887, 0.1747 }, + { 0.3860, 0.1987 }, + { 0.3832, 0.2230 }, + { 0.3804, 0.2474 }, + { 0.3776, 0.2717 }, + { 0.3748, 0.2960 }, + { 0.3720, 0.3200 }, + { 0.3692, 0.3444 }, + { 0.3664, 0.3687 }, + { 0.3636, 0.3930 }, + { 0.3609, 0.4174 }, + { 0.3581, 0.4414 }, + { 0.3553, 0.4657 }, + { 0.3525, 0.4901 }, + { 0.3497, 0.5144 }, + { 0.3469, 0.5387 }, + { 0.3442, 0.5628 }, + { 0.3414, 0.5871 }, + { 0.3386, 0.6114 }, + { 0.3358, 0.6358 }, + { 0.3330, 0.6601 }, + { 0.3302, 0.6841 }, + { 0.3274, 0.7084 }, + { 0.3246, 0.7328 }, + { 0.3218, 0.7571 }, + { 0.3190, 0.7815 }, + { 0.3163, 0.8055 }, + { 0.3135, 0.8298 }, + { 0.3107, 0.8541 }, + { 0.3079, 0.8785 }, + { 0.3051, 0.9028 }, + { 0.3023, 0.9268 }, + { 0.2995, 0.9512 }, + { 0.2967, 0.9755 }, + { 0.4269, 0.0561 }, + { 0.4242, 0.0801 }, + { 0.4214, 0.1045 }, + { 0.4186, 0.1288 }, + { 0.4158, 0.1531 }, + { 0.4130, 0.1775 }, + { 0.4102, 0.2015 }, + { 0.4074, 0.2258 }, + { 0.4046, 0.2501 }, + { 0.4018, 0.2745 }, + { 0.3990, 0.2988 }, + { 0.3963, 0.3228 }, + { 0.3935, 0.3472 }, + { 0.3907, 0.3715 }, + { 0.3879, 0.3958 }, + { 0.3851, 0.4202 }, + { 0.3823, 0.4442 }, + { 0.3796, 0.4685 }, + { 0.3768, 0.4929 }, + { 0.3740, 0.5172 }, + { 0.3712, 0.5415 }, + { 0.3684, 0.5655 }, + { 0.3656, 0.5899 }, + { 0.3628, 0.6142 }, + { 0.3600, 0.6385 }, + { 0.3572, 0.6629 }, + { 0.3545, 0.6869 }, + { 0.3517, 0.7112 }, + { 0.3489, 0.7356 }, + { 0.3461, 0.7599 }, + { 0.3433, 0.7842 }, + { 0.3405, 0.8083 }, + { 0.3377, 0.8326 }, + { 0.3349, 0.8569 }, + { 0.3321, 0.8813 }, + { 0.3294, 0.9056 }, + { 0.3266, 0.9296 }, + { 0.3238, 0.9539 }, + { 0.3210, 0.9783 }, + { 0.4512, 0.0589 }, + { 0.4484, 0.0829 }, + { 0.4456, 0.1072 }, + { 0.4428, 0.1316 }, + { 0.4400, 0.1559 }, + { 0.4372, 0.1802 }, + { 0.4345, 0.2043 }, + { 0.4317, 0.2286 }, + { 0.4289, 0.2529 }, + { 0.4261, 0.2773 }, + { 0.4233, 0.3016 }, + { 0.4205, 0.3256 }, + { 0.4177, 0.3500 }, + { 0.4150, 0.3743 }, + { 0.4122, 0.3986 }, + { 0.4094, 0.4230 }, + { 0.4066, 0.4470 }, + { 0.4038, 0.4713 }, + { 0.4010, 0.4956 }, + { 0.3982, 0.5200 }, + { 0.3954, 0.5443 }, + { 0.3927, 0.5683 }, + { 0.3899, 0.5927 }, + { 0.3871, 0.6170 }, + { 0.3843, 0.6413 }, + { 0.3815, 0.6657 }, + { 0.3787, 0.6897 }, + { 0.3759, 0.7140 }, + { 0.3731, 0.7384 }, + { 0.3703, 0.7627 }, + { 0.3675, 0.7870 }, + { 0.3648, 0.8110 }, + { 0.3620, 0.8354 }, + { 0.3592, 0.8597 }, + { 0.3564, 0.8840 }, + { 0.3536, 0.9084 }, + { 0.3508, 0.9324 }, + { 0.3481, 0.9567 }, + { 0.3453, 0.9811 }, + { 0.4755, 0.0617 }, + { 0.4727, 0.0857 }, + { 0.4699, 0.1100 }, + { 0.4671, 0.1344 }, + { 0.4643, 0.1587 }, + { 0.4615, 0.1830 }, + { 0.4588, 0.2071 }, + { 0.4560, 0.2314 }, + { 0.4532, 0.2557 }, + { 0.4504, 0.2801 }, + { 0.4476, 0.3044 }, + { 0.4448, 0.3284 }, + { 0.4420, 0.3527 }, + { 0.4392, 0.3771 }, + { 0.4365, 0.4014 }, + { 0.4337, 0.4257 }, + { 0.4309, 0.4498 }, + { 0.4281, 0.4741 }, + { 0.4253, 0.4984 }, + { 0.4225, 0.5228 }, + { 0.4197, 0.5471 }, + { 0.4170, 0.5711 }, + { 0.4142, 0.5955 }, + { 0.4114, 0.6198 }, + { 0.4086, 0.6441 }, + { 0.4058, 0.6685 }, + { 0.4030, 0.6925 }, + { 0.4002, 0.7168 }, + { 0.3974, 0.7411 }, + { 0.3946, 0.7655 }, + { 0.3918, 0.7898 }, + { 0.3891, 0.8138 }, + { 0.3863, 0.8382 }, + { 0.3835, 0.8625 }, + { 0.3807, 0.8868 }, + { 0.3779, 0.9112 }, + { 0.3751, 0.9352 }, + { 0.3723, 0.9595 }, + { 0.3696, 0.9839 }, + { 0.4997, 0.0645 }, + { 0.4970, 0.0885 }, + { 0.4942, 0.1128 }, + { 0.4914, 0.1371 }, + { 0.4886, 0.1615 }, + { 0.4858, 0.1858 }, + { 0.4830, 0.2098 }, + { 0.4802, 0.2342 }, + { 0.4774, 0.2585 }, + { 0.4746, 0.2828 }, + { 0.4719, 0.3072 }, + { 0.4691, 0.3312 }, + { 0.4663, 0.3555 }, + { 0.4635, 0.3799 }, + { 0.4607, 0.4042 }, + { 0.4579, 0.4285 }, + { 0.4552, 0.4526 }, + { 0.4524, 0.4769 }, + { 0.4496, 0.5012 }, + { 0.4468, 0.5256 }, + { 0.4440, 0.5499 }, + { 0.4412, 0.5739 }, + { 0.4384, 0.5982 }, + { 0.4356, 0.6226 }, + { 0.4328, 0.6469 }, + { 0.4300, 0.6712 }, + { 0.4273, 0.6953 }, + { 0.4245, 0.7196 }, + { 0.4217, 0.7439 }, + { 0.4189, 0.7683 }, + { 0.4161, 0.7926 }, + { 0.4133, 0.8166 }, + { 0.4105, 0.8410 }, + { 0.4077, 0.8653 }, + { 0.4050, 0.8896 }, + { 0.4022, 0.9140 }, + { 0.3994, 0.9380 }, + { 0.3966, 0.9623 }, + { 0.3938, 0.9866 }, + { 0.5240, 0.0673 }, + { 0.5213, 0.0913 }, + { 0.5185, 0.1156 }, + { 0.5157, 0.1399 }, + { 0.5129, 0.1643 }, + { 0.5101, 0.1886 }, + { 0.5073, 0.2126 }, + { 0.5045, 0.2370 }, + { 0.5017, 0.2613 }, + { 0.4989, 0.2856 }, + { 0.4961, 0.3100 }, + { 0.4934, 0.3340 }, + { 0.4906, 0.3583 }, + { 0.4878, 0.3827 }, + { 0.4850, 0.4070 }, + { 0.4822, 0.4313 }, + { 0.4794, 0.4553 }, + { 0.4767, 0.4797 }, + { 0.4739, 0.5040 }, + { 0.4711, 0.5283 }, + { 0.4683, 0.5527 }, + { 0.4655, 0.5767 }, + { 0.4627, 0.6010 }, + { 0.4599, 0.6254 }, + { 0.4571, 0.6497 }, + { 0.4543, 0.6740 }, + { 0.4516, 0.6981 }, + { 0.4488, 0.7224 }, + { 0.4460, 0.7467 }, + { 0.4432, 0.7711 }, + { 0.4404, 0.7954 }, + { 0.4376, 0.8194 }, + { 0.4348, 0.8437 }, + { 0.4320, 0.8681 }, + { 0.4292, 0.8924 }, + { 0.4265, 0.9167 }, + { 0.4237, 0.9408 }, + { 0.4209, 0.9651 }, + { 0.4181, 0.9894 }, + { 0.5483, 0.0700 }, + { 0.5455, 0.0941 }, + { 0.5427, 0.1184 }, + { 0.5399, 0.1427 }, + { 0.5371, 0.1671 }, + { 0.5343, 0.1914 }, + { 0.5316, 0.2154 }, + { 0.5288, 0.2397 }, + { 0.5260, 0.2641 }, + { 0.5232, 0.2884 }, + { 0.5204, 0.3128 }, + { 0.5176, 0.3368 }, + { 0.5148, 0.3611 }, + { 0.5121, 0.3854 }, + { 0.5093, 0.4098 }, + { 0.5065, 0.4341 }, + { 0.5037, 0.4581 }, + { 0.5009, 0.4825 }, + { 0.4981, 0.5068 }, + { 0.4953, 0.5311 }, + { 0.4925, 0.5555 }, + { 0.4898, 0.5795 }, + { 0.4870, 0.6038 }, + { 0.4842, 0.6282 }, + { 0.4814, 0.6525 }, + { 0.4786, 0.6768 }, + { 0.4758, 0.7008 }, + { 0.4730, 0.7252 }, + { 0.4702, 0.7495 }, + { 0.4674, 0.7738 }, + { 0.4646, 0.7982 }, + { 0.4619, 0.8222 }, + { 0.4591, 0.8465 }, + { 0.4563, 0.8709 }, + { 0.4535, 0.8952 }, + { 0.4507, 0.9195 }, + { 0.4479, 0.9436 }, + { 0.4452, 0.9679 }, + { 0.4424, 0.9922 }, + { 0.5725, 0.0728 }, + { 0.5698, 0.0968 }, + { 0.5670, 0.1212 }, + { 0.5642, 0.1455 }, + { 0.5614, 0.1698 }, + { 0.5586, 0.1942 }, + { 0.5558, 0.2182 }, + { 0.5530, 0.2425 }, + { 0.5502, 0.2669 }, + { 0.5475, 0.2912 }, + { 0.5447, 0.3155 }, + { 0.5419, 0.3396 }, + { 0.5391, 0.3639 }, + { 0.5363, 0.3882 }, + { 0.5335, 0.4126 }, + { 0.5307, 0.4369 }, + { 0.5280, 0.4609 }, + { 0.5252, 0.4852 }, + { 0.5224, 0.5096 }, + { 0.5196, 0.5339 }, + { 0.5168, 0.5583 }, + { 0.5140, 0.5823 }, + { 0.5112, 0.6066 }, + { 0.5084, 0.6309 }, + { 0.5056, 0.6553 }, + { 0.5028, 0.6796 }, + { 0.5001, 0.7036 }, + { 0.4973, 0.7280 }, + { 0.4945, 0.7523 }, + { 0.4917, 0.7766 }, + { 0.4889, 0.8010 }, + { 0.4861, 0.8250 }, + { 0.4833, 0.8493 }, + { 0.4806, 0.8737 }, + { 0.4778, 0.8980 }, + { 0.4750, 0.9223 }, + { 0.4722, 0.9463 }, + { 0.4694, 0.9707 }, + { 0.4666, 0.9950 }, + { 0.5968, 0.0756 }, + { 0.5941, 0.0996 }, + { 0.5913, 0.1240 }, + { 0.5885, 0.1483 }, + { 0.5857, 0.1726 }, + { 0.5829, 0.1970 }, + { 0.5801, 0.2210 }, + { 0.5773, 0.2453 }, + { 0.5745, 0.2697 }, + { 0.5717, 0.2940 }, + { 0.5690, 0.3183 }, + { 0.5662, 0.3423 }, + { 0.5634, 0.3667 }, + { 0.5606, 0.3910 }, + { 0.5578, 0.4153 }, + { 0.5550, 0.4397 }, + { 0.5523, 0.4637 }, + { 0.5495, 0.4880 }, + { 0.5467, 0.5124 }, + { 0.5439, 0.5367 }, + { 0.5411, 0.5610 }, + { 0.5383, 0.5851 }, + { 0.5355, 0.6094 }, + { 0.5327, 0.6337 }, + { 0.5299, 0.6581 }, + { 0.5271, 0.6824 }, + { 0.5244, 0.7064 }, + { 0.5216, 0.7308 }, + { 0.5188, 0.7551 }, + { 0.5160, 0.7794 }, + { 0.5132, 0.8038 }, + { 0.5104, 0.8278 }, + { 0.5076, 0.8521 }, + { 0.5048, 0.8764 }, + { 0.5021, 0.9008 }, + { 0.4993, 0.9251 }, + { 0.4965, 0.9491 }, + { 0.4937, 0.9735 }, + { 0.4909, 0.9978 }, + { 0.6211, 0.0784 }, + { 0.6183, 0.1024 }, + { 0.6155, 0.1268 }, + { 0.6127, 0.1511 }, + { 0.6099, 0.1754 }, + { 0.6071, 0.1998 }, + { 0.6044, 0.2238 }, + { 0.6016, 0.2481 }, + { 0.5988, 0.2724 }, + { 0.5960, 0.2968 }, + { 0.5932, 0.3211 }, + { 0.5904, 0.3451 }, + { 0.5877, 0.3695 }, + { 0.5849, 0.3938 }, + { 0.5821, 0.4181 }, + { 0.5793, 0.4425 }, + { 0.5765, 0.4665 }, + { 0.5737, 0.4908 }, + { 0.5709, 0.5152 }, + { 0.5681, 0.5395 }, + { 0.5653, 0.5638 }, + { 0.5626, 0.5878 }, + { 0.5598, 0.6122 }, + { 0.5570, 0.6365 }, + { 0.5542, 0.6608 }, + { 0.5514, 0.6852 }, + { 0.5486, 0.7092 }, + { 0.5458, 0.7335 }, + { 0.5430, 0.7579 }, + { 0.5402, 0.7822 }, + { 0.5375, 0.8065 }, + { 0.5347, 0.8306 }, + { 0.5319, 0.8549 }, + { 0.5291, 0.8792 }, + { 0.5263, 0.9036 }, + { 0.5235, 0.9279 }, + { 0.5208, 0.9519 }, + { 0.5180, 0.9762 }, + { 0.5152, 1.0006 }, + { 0.6454, 0.0812 }, + { 0.6426, 0.1052 }, + { 0.6398, 0.1295 }, + { 0.6370, 0.1539 }, + { 0.6342, 0.1782 }, + { 0.6314, 0.2025 }, + { 0.6287, 0.2266 }, + { 0.6259, 0.2509 }, + { 0.6231, 0.2752 }, + { 0.6203, 0.2996 }, + { 0.6175, 0.3239 }, + { 0.6147, 0.3479 }, + { 0.6119, 0.3723 }, + { 0.6092, 0.3966 }, + { 0.6064, 0.4209 }, + { 0.6036, 0.4453 }, + { 0.6008, 0.4693 }, + { 0.5980, 0.4936 }, + { 0.5952, 0.5179 }, + { 0.5924, 0.5423 }, + { 0.5896, 0.5666 }, + { 0.5869, 0.5906 }, + { 0.5841, 0.6150 }, + { 0.5813, 0.6393 }, + { 0.5785, 0.6636 }, + { 0.5757, 0.6880 }, + { 0.5729, 0.7120 }, + { 0.5701, 0.7363 }, + { 0.5673, 0.7607 }, + { 0.5645, 0.7850 }, + { 0.5617, 0.8093 }, + { 0.5590, 0.8333 }, + { 0.5562, 0.8577 }, + { 0.5534, 0.8820 }, + { 0.5506, 0.9064 }, + { 0.5478, 0.9307 }, + { 0.5451, 0.9547 }, + { 0.5423, 0.9790 }, + { 0.5395, 1.0034 }, + { 0.6696, 0.0840 }, + { 0.6669, 0.1080 }, + { 0.6641, 0.1323 }, + { 0.6613, 0.1567 }, + { 0.6585, 0.1810 }, + { 0.6557, 0.2053 }, + { 0.6529, 0.2294 }, + { 0.6501, 0.2537 }, + { 0.6473, 0.2780 }, + { 0.6446, 0.3024 }, + { 0.6418, 0.3267 }, + { 0.6390, 0.3507 }, + { 0.6362, 0.3750 }, + { 0.6334, 0.3994 }, + { 0.6306, 0.4237 }, + { 0.6278, 0.4480 }, + { 0.6251, 0.4721 }, + { 0.6223, 0.4964 }, + { 0.6195, 0.5207 }, + { 0.6167, 0.5451 }, + { 0.6139, 0.5694 }, + { 0.6111, 0.5934 }, + { 0.6083, 0.6178 }, + { 0.6055, 0.6421 }, + { 0.6027, 0.6664 }, + { 0.5999, 0.6908 }, + { 0.5972, 0.7148 }, + { 0.5944, 0.7391 }, + { 0.5916, 0.7634 }, + { 0.5888, 0.7878 }, + { 0.5860, 0.8121 }, + { 0.5832, 0.8361 }, + { 0.5805, 0.8605 }, + { 0.5777, 0.8848 }, + { 0.5749, 0.9091 }, + { 0.5721, 0.9335 }, + { 0.5693, 0.9575 }, + { 0.5665, 0.9818 }, + { 0.5637, 1.0062 }, + { 0.6939, 0.0868 }, + { 0.6911, 0.1108 }, + { 0.6883, 0.1351 }, + { 0.6855, 0.1595 }, + { 0.6827, 0.1838 }, + { 0.6800, 0.2081 }, + { 0.6772, 0.2321 }, + { 0.6744, 0.2565 }, + { 0.6716, 0.2808 }, + { 0.6688, 0.3051 }, + { 0.6660, 0.3295 }, + { 0.6633, 0.3535 }, + { 0.6605, 0.3778 }, + { 0.6577, 0.4022 }, + { 0.6549, 0.4265 }, + { 0.6521, 0.4508 }, + { 0.6493, 0.4749 }, + { 0.6465, 0.4992 }, + { 0.6437, 0.5235 }, + { 0.6409, 0.5479 }, + { 0.6381, 0.5722 }, + { 0.6354, 0.5962 }, + { 0.6326, 0.6205 }, + { 0.6298, 0.6449 }, + { 0.6270, 0.6692 }, + { 0.6242, 0.6935 }, + { 0.6214, 0.7176 }, + { 0.6186, 0.7419 }, + { 0.6158, 0.7662 }, + { 0.6131, 0.7906 }, + { 0.6103, 0.8149 }, + { 0.6075, 0.8389 }, + { 0.6047, 0.8633 }, + { 0.6019, 0.8876 }, + { 0.5991, 0.9119 }, + { 0.5963, 0.9363 }, + { 0.5936, 0.9603 }, + { 0.5908, 0.9846 }, + { 0.5880, 1.0089 }, + { 0.7182, 0.0896 }, + { 0.7154, 0.1136 }, + { 0.7126, 0.1379 }, + { 0.7098, 0.1622 }, + { 0.7070, 0.1866 }, + { 0.7042, 0.2109 }, + { 0.7015, 0.2349 }, + { 0.6987, 0.2593 }, + { 0.6959, 0.2836 }, + { 0.6931, 0.3079 }, + { 0.6903, 0.3323 }, + { 0.6876, 0.3563 }, + { 0.6848, 0.3806 }, + { 0.6820, 0.4050 }, + { 0.6792, 0.4293 }, + { 0.6764, 0.4536 }, + { 0.6736, 0.4776 }, + { 0.6708, 0.5020 }, + { 0.6680, 0.5263 }, + { 0.6652, 0.5506 }, + { 0.6624, 0.5750 }, + { 0.6597, 0.5990 }, + { 0.6569, 0.6233 }, + { 0.6541, 0.6477 }, + { 0.6513, 0.6720 }, + { 0.6485, 0.6963 }, + { 0.6457, 0.7204 }, + { 0.6429, 0.7447 }, + { 0.6401, 0.7690 }, + { 0.6373, 0.7934 }, + { 0.6346, 0.8177 }, + { 0.6318, 0.8417 }, + { 0.6290, 0.8660 }, + { 0.6262, 0.8904 }, + { 0.6234, 0.9147 }, + { 0.6206, 0.9390 }, + { 0.6179, 0.9631 }, + { 0.6151, 0.9874 }, + { 0.6123, 1.0117 }, + { 0.7424, 0.0923 }, + { 0.7397, 0.1164 }, + { 0.7369, 0.1407 }, + { 0.7341, 0.1650 }, + { 0.7313, 0.1894 }, + { 0.7285, 0.2137 }, + { 0.7257, 0.2377 }, + { 0.7229, 0.2620 }, + { 0.7202, 0.2864 }, + { 0.7174, 0.3107 }, + { 0.7146, 0.3351 }, + { 0.7118, 0.3591 }, + { 0.7090, 0.3834 }, + { 0.7062, 0.4077 }, + { 0.7034, 0.4321 }, + { 0.7006, 0.4564 }, + { 0.6979, 0.4804 }, + { 0.6951, 0.5048 }, + { 0.6923, 0.5291 }, + { 0.6895, 0.5534 }, + { 0.6867, 0.5778 }, + { 0.6839, 0.6018 }, + { 0.6811, 0.6261 }, + { 0.6783, 0.6505 }, + { 0.6755, 0.6748 }, + { 0.6727, 0.6991 }, + { 0.6700, 0.7231 }, + { 0.6672, 0.7475 }, + { 0.6644, 0.7718 }, + { 0.6616, 0.7961 }, + { 0.6588, 0.8205 }, + { 0.6561, 0.8445 }, + { 0.6533, 0.8688 }, + { 0.6505, 0.8932 }, + { 0.6477, 0.9175 }, + { 0.6449, 0.9418 }, + { 0.6421, 0.9659 }, + { 0.6393, 0.9902 }, + { 0.6365, 1.0145 }, + { 0.7667, 0.0951 }, + { 0.7640, 0.1191 }, + { 0.7612, 0.1435 }, + { 0.7584, 0.1678 }, + { 0.7556, 0.1922 }, + { 0.7528, 0.2165 }, + { 0.7500, 0.2405 }, + { 0.7472, 0.2648 }, + { 0.7444, 0.2892 }, + { 0.7417, 0.3135 }, + { 0.7389, 0.3378 }, + { 0.7361, 0.3619 }, + { 0.7333, 0.3862 }, + { 0.7305, 0.4105 }, + { 0.7277, 0.4349 }, + { 0.7249, 0.4592 }, + { 0.7222, 0.4832 }, + { 0.7194, 0.5076 }, + { 0.7166, 0.5319 }, + { 0.7138, 0.5562 }, + { 0.7110, 0.5806 }, + { 0.7082, 0.6046 }, + { 0.7054, 0.6289 }, + { 0.7026, 0.6532 }, + { 0.6998, 0.6776 }, + { 0.6970, 0.7019 }, + { 0.6943, 0.7259 }, + { 0.6915, 0.7503 }, + { 0.6887, 0.7746 }, + { 0.6859, 0.7989 }, + { 0.6831, 0.8233 }, + { 0.6803, 0.8473 }, + { 0.6776, 0.8716 }, + { 0.6748, 0.8960 }, + { 0.6720, 0.9203 }, + { 0.6692, 0.9446 }, + { 0.6664, 0.9686 }, + { 0.6636, 0.9930 }, + { 0.6608, 1.0173 }, + { 0.7910, 0.0979 }, + { 0.7882, 0.1219 }, + { 0.7854, 0.1463 }, + { 0.7826, 0.1706 }, + { 0.7798, 0.1949 }, + { 0.7771, 0.2193 }, + { 0.7743, 0.2433 }, + { 0.7715, 0.2676 }, + { 0.7687, 0.2920 }, + { 0.7659, 0.3163 }, + { 0.7631, 0.3406 }, + { 0.7604, 0.3646 }, + { 0.7576, 0.3890 }, + { 0.7548, 0.4133 }, + { 0.7520, 0.4377 }, + { 0.7492, 0.4620 }, + { 0.7464, 0.4860 }, + { 0.7436, 0.5103 }, + { 0.7408, 0.5347 }, + { 0.7380, 0.5590 }, + { 0.7352, 0.5833 }, + { 0.7325, 0.6074 }, + { 0.7297, 0.6317 }, + { 0.7269, 0.6560 }, + { 0.7241, 0.6804 }, + { 0.7213, 0.7047 }, + { 0.7185, 0.7287 }, + { 0.7157, 0.7531 }, + { 0.7130, 0.7774 }, + { 0.7102, 0.8017 }, + { 0.7074, 0.8261 }, + { 0.7046, 0.8501 }, + { 0.7018, 0.8744 }, + { 0.6990, 0.8987 }, + { 0.6962, 0.9231 }, + { 0.6934, 0.9474 }, + { 0.6907, 0.9714 }, + { 0.6879, 0.9958 }, + { 0.6851, 1.0201 }, + { 0.8152, 0.1007 }, + { 0.8125, 0.1247 }, + { 0.8097, 0.1491 }, + { 0.8069, 0.1734 }, + { 0.8041, 0.1977 }, + { 0.8013, 0.2221 }, + { 0.7986, 0.2461 }, + { 0.7958, 0.2704 }, + { 0.7930, 0.2947 }, + { 0.7902, 0.3191 }, + { 0.7874, 0.3434 }, + { 0.7846, 0.3674 }, + { 0.7818, 0.3918 }, + { 0.7790, 0.4161 }, + { 0.7762, 0.4404 }, + { 0.7734, 0.4648 }, + { 0.7707, 0.4888 }, + { 0.7679, 0.5131 }, + { 0.7651, 0.5375 }, + { 0.7623, 0.5618 }, + { 0.7595, 0.5861 }, + { 0.7567, 0.6101 }, + { 0.7539, 0.6345 }, + { 0.7511, 0.6588 }, + { 0.7483, 0.6831 }, + { 0.7456, 0.7075 }, + { 0.7428, 0.7315 }, + { 0.7400, 0.7558 }, + { 0.7372, 0.7802 }, + { 0.7344, 0.8045 }, + { 0.7316, 0.8288 }, + { 0.7289, 0.8529 }, + { 0.7261, 0.8772 }, + { 0.7233, 0.9015 }, + { 0.7205, 0.9259 }, + { 0.7177, 0.9502 }, + { 0.7149, 0.9742 }, + { 0.7121, 0.9986 }, + { 0.7093, 1.0229 }, + { 0.8395, 0.1035 }, + { 0.8368, 0.1275 }, + { 0.8340, 0.1518 }, + { 0.8312, 0.1762 }, + { 0.8284, 0.2005 }, + { 0.8256, 0.2248 }, + { 0.8228, 0.2489 }, + { 0.8201, 0.2732 }, + { 0.8173, 0.2975 }, + { 0.8145, 0.3219 }, + { 0.8117, 0.3462 }, + { 0.8089, 0.3702 }, + { 0.8061, 0.3946 }, + { 0.8033, 0.4189 }, + { 0.8005, 0.4432 }, + { 0.7977, 0.4676 }, + { 0.7950, 0.4916 }, + { 0.7922, 0.5159 }, + { 0.7894, 0.5402 }, + { 0.7866, 0.5646 }, + { 0.7838, 0.5889 }, + { 0.7810, 0.6129 }, + { 0.7782, 0.6373 }, + { 0.7754, 0.6616 }, + { 0.7726, 0.6859 }, + { 0.7698, 0.7103 }, + { 0.7671, 0.7343 }, + { 0.7643, 0.7586 }, + { 0.7615, 0.7830 }, + { 0.7587, 0.8073 }, + { 0.7559, 0.8316 }, + { 0.7532, 0.8556 }, + { 0.7504, 0.8800 }, + { 0.7476, 0.9043 }, + { 0.7448, 0.9287 }, + { 0.7420, 0.9530 }, + { 0.7392, 0.9770 }, + { 0.7364, 1.0013 }, + { 0.7336, 1.0257 }, + { 0.8638, 0.1063 }, + { 0.8610, 0.1303 }, + { 0.8582, 0.1546 }, + { 0.8555, 0.1790 }, + { 0.8527, 0.2033 }, + { 0.8499, 0.2276 }, + { 0.8471, 0.2517 }, + { 0.8443, 0.2760 }, + { 0.8415, 0.3003 }, + { 0.8387, 0.3247 }, + { 0.8359, 0.3490 }, + { 0.8332, 0.3730 }, + { 0.8304, 0.3973 }, + { 0.8276, 0.4217 }, + { 0.8248, 0.4460 }, + { 0.8220, 0.4703 }, + { 0.8192, 0.4944 }, + { 0.8164, 0.5187 }, + { 0.8136, 0.5430 }, + { 0.8108, 0.5674 }, + { 0.8080, 0.5917 }, + { 0.8053, 0.6157 }, + { 0.8025, 0.6401 }, + { 0.7997, 0.6644 }, + { 0.7969, 0.6887 }, + { 0.7941, 0.7131 }, + { 0.7913, 0.7371 }, + { 0.7886, 0.7614 }, + { 0.7858, 0.7857 }, + { 0.7830, 0.8101 }, + { 0.7802, 0.8344 }, + { 0.7774, 0.8584 }, + { 0.7746, 0.8828 }, + { 0.7718, 0.9071 }, + { 0.7690, 0.9314 }, + { 0.7662, 0.9558 }, + { 0.7635, 0.9798 }, + { 0.7607, 1.0041 }, + { 0.7579, 1.0285 }, + { 0.8881, 0.1091 }, + { 0.8853, 0.1331 }, + { 0.8825, 0.1574 }, + { 0.8797, 0.1818 }, + { 0.8770, 0.2061 }, + { 0.8742, 0.2304 }, + { 0.8714, 0.2544 }, + { 0.8686, 0.2788 }, + { 0.8658, 0.3031 }, + { 0.8630, 0.3274 }, + { 0.8602, 0.3518 }, + { 0.8575, 0.3758 }, + { 0.8547, 0.4001 }, + { 0.8519, 0.4245 }, + { 0.8491, 0.4488 }, + { 0.8463, 0.4731 }, + { 0.8435, 0.4972 }, + { 0.8407, 0.5215 }, + { 0.8379, 0.5458 }, + { 0.8351, 0.5702 }, + { 0.8323, 0.5945 }, + { 0.8296, 0.6185 }, + { 0.8268, 0.6428 }, + { 0.8240, 0.6672 }, + { 0.8212, 0.6915 }, + { 0.8184, 0.7159 }, + { 0.8156, 0.7399 }, + { 0.8128, 0.7642 }, + { 0.8101, 0.7885 }, + { 0.8073, 0.8129 }, + { 0.8045, 0.8372 }, + { 0.8017, 0.8612 }, + { 0.7989, 0.8856 }, + { 0.7961, 0.9099 }, + { 0.7933, 0.9342 }, + { 0.7905, 0.9586 }, + { 0.7878, 0.9826 }, + { 0.7850, 1.0069 }, + { 0.7822, 1.0313 }, + { 0.9123, 0.1119 }, + { 0.9096, 0.1359 }, + { 0.9068, 0.1602 }, + { 0.9040, 0.1845 }, + { 0.9012, 0.2089 }, + { 0.8984, 0.2332 }, + { 0.8957, 0.2572 }, + { 0.8929, 0.2816 }, + { 0.8901, 0.3059 }, + { 0.8873, 0.3302 }, + { 0.8845, 0.3546 }, + { 0.8817, 0.3786 }, + { 0.8789, 0.4029 }, + { 0.8761, 0.4273 }, + { 0.8733, 0.4516 }, + { 0.8705, 0.4759 }, + { 0.8678, 0.4999 }, + { 0.8650, 0.5243 }, + { 0.8622, 0.5486 }, + { 0.8594, 0.5729 }, + { 0.8566, 0.5973 }, + { 0.8538, 0.6213 }, + { 0.8510, 0.6456 }, + { 0.8482, 0.6700 }, + { 0.8455, 0.6943 }, + { 0.8427, 0.7186 }, + { 0.8399, 0.7427 }, + { 0.8371, 0.7670 }, + { 0.8343, 0.7913 }, + { 0.8315, 0.8157 }, + { 0.8287, 0.8400 }, + { 0.8260, 0.8640 }, + { 0.8232, 0.8883 }, + { 0.8204, 0.9127 }, + { 0.8176, 0.9370 }, + { 0.8148, 0.9614 }, + { 0.8120, 0.9854 }, + { 0.8092, 1.0097 }, + { 0.8064, 1.0340 }, + { 0.9366, 0.1146 }, + { 0.9338, 0.1387 }, + { 0.9311, 0.1630 }, + { 0.9283, 0.1873 }, + { 0.9255, 0.2117 }, + { 0.9227, 0.2360 }, + { 0.9199, 0.2600 }, + { 0.9171, 0.2844 }, + { 0.9143, 0.3087 }, + { 0.9115, 0.3330 }, + { 0.9087, 0.3574 }, + { 0.9060, 0.3814 }, + { 0.9032, 0.4057 }, + { 0.9004, 0.4300 }, + { 0.8976, 0.4544 }, + { 0.8948, 0.4787 }, + { 0.8920, 0.5027 }, + { 0.8892, 0.5271 }, + { 0.8864, 0.5514 }, + { 0.8836, 0.5757 }, + { 0.8808, 0.6001 }, + { 0.8781, 0.6241 }, + { 0.8753, 0.6484 }, + { 0.8725, 0.6728 }, + { 0.8697, 0.6971 }, + { 0.8669, 0.7214 }, + { 0.8642, 0.7454 }, + { 0.8614, 0.7698 }, + { 0.8586, 0.7941 }, + { 0.8558, 0.8184 }, + { 0.8530, 0.8428 }, + { 0.8502, 0.8668 }, + { 0.8474, 0.8911 }, + { 0.8446, 0.9155 }, + { 0.8418, 0.9398 }, + { 0.8390, 0.9641 }, + { 0.8363, 0.9882 }, + { 0.8335, 1.0125 }, + { 0.8307, 1.0368 }, + { 0.9581, 0.1414 }, + { 0.9553, 0.1658 }, + { 0.9526, 0.1901 }, + { 0.9498, 0.2145 }, + { 0.9470, 0.2388 }, + { 0.9442, 0.2628 }, + { 0.9414, 0.2871 }, + { 0.9386, 0.3115 }, + { 0.9358, 0.3358 }, + { 0.9330, 0.3601 }, + { 0.9303, 0.3842 }, + { 0.9275, 0.4085 }, + { 0.9247, 0.4328 }, + { 0.9219, 0.4572 }, + { 0.9191, 0.4815 }, + { 0.9163, 0.5055 }, + { 0.9135, 0.5299 }, + { 0.9107, 0.5542 }, + { 0.9079, 0.5785 }, + { 0.9051, 0.6029 }, + { 0.9024, 0.6269 }, + { 0.8996, 0.6512 }, + { 0.8968, 0.6755 }, + { 0.8940, 0.6999 }, + { 0.8912, 0.7242 }, + { 0.8884, 0.7482 }, + { 0.8857, 0.7726 }, + { 0.8829, 0.7969 }, + { 0.8801, 0.8212 }, + { 0.8773, 0.8456 }, + { 0.8745, 0.8696 }, + { 0.8717, 0.8939 }, + { 0.8689, 0.9183 }, + { 0.8661, 0.9426 }, + { 0.8633, 0.9669 }, + { 0.8606, 0.9909 }, + { 0.8578, 1.0153 }, + { 0.8550, 1.0396 }, + { 0.8522, 1.0639 }, +}; + diff --git a/src/Demos/hangglide/trees.cpp b/src/Demos/hangglide/trees.cpp new file mode 100644 index 000000000..b5d87b2f1 --- /dev/null +++ b/src/Demos/hangglide/trees.cpp @@ -0,0 +1,275 @@ +#include + +#include +#include +#include +#include +#include +#include +#include +#include + +#include + +#include "hat.h" + +#ifdef WIN32 +#pragma warning( disable : 4244 ) +#pragma warning( disable : 4305 ) +#endif + +using namespace osg; + +#define sqr(x) ((x)*(x)) + +extern void getDatabaseCenterRadius( float dbcenter[3], float *dbradius ); + +static float dbcenter[3], dbradius; + +static struct _tree +{ + int n; + float x, y, z; + float w, h; +} + + +trees[] = +{ + { 0, -0.4769, -0.8972, -0.4011, 0.2000, 0.1200 }, + { 1, -0.2543, -0.9117, -0.3873, 0.2000, 0.1200 }, + { 2, -0.0424, -0.8538, -0.3728, 0.2000, 0.1200 }, + { 3, 0.1590, -0.8827, -0.3594, 0.2000, 0.1200 }, + { 4, -0.4981, -1.0853, -0.4016, 0.3500, 0.1200 }, + { 5, -0.5405, -1.2590, -0.4050, 0.2000, 0.1200 }, + { 6, -0.5723, -1.5339, -0.4152, 0.2000, 0.1200 }, + { 7, -0.6252, -1.8667, -0.4280, 0.2000, 0.1200 }, + { 8, -0.5617, -2.1851, -0.4309, 0.2000, 0.1200 }, + { 9, -0.5087, -2.4166, -0.4215, 0.2000, 0.1200 }, + { 10, -0.4345, -2.3443, -0.4214, 0.2000, 0.1200 }, + { 11, -3.0308, -1.5484, -0.4876, 0.2000, 0.1200 }, + { 12, -3.0202, -1.6497, -0.4963, 0.2000, 0.1200 }, + { 13, -2.9355, -1.8378, -0.4969, 0.2000, 0.1200 }, + { 14, -0.6040, -2.0259, -0.4300, 0.2000, 0.1200 }, + { 15, -0.5442, -1.3442, -0.4080, 0.1000, 0.1200 }, + { 16, -0.5639, -1.6885, -0.4201, 0.1000, 0.1200 }, + { 17, 0.9246, 3.4835, 0.5898, 0.2500, 0.1000 }, + { 18, 0.0787, 3.8687, 0.3329, 0.2500, 0.1200 }, + { 19, 0.2885, 3.7130, 0.4047, 0.2500, 0.1200 }, + { 20, 0.2033, 3.6228, 0.3704, 0.2500, 0.1200 }, + { 21, -0.2098, 3.9015, 0.2327, 0.2500, 0.1200 }, + { 22, -0.3738, 3.7376, 0.1722, 0.2500, 0.1200 }, + { 23, -0.2557, 3.6064, 0.1989, 0.2500, 0.1200 }, + { 24, 0.0590, 3.7294, 0.3210, 0.2500, 0.1200 }, + { 25, -0.4721, 3.8851, 0.1525, 0.2500, 0.1200 }, + { 26, 0.9639, 3.2048, 0.5868, 0.1200, 0.0800 }, + { 27, 0.7082, -1.0409, -0.3221, 0.1000, 0.1000 }, + { 28, -0.2426, -2.3442, -0.4150, 0.1000, 0.1380 }, + { 29, -0.1770, -2.4179, -0.4095, 0.1000, 0.1580 }, + { 30, -0.0852, -2.5327, -0.4056, 0.1000, 0.1130 }, + { 31, -0.0131, -2.6065, -0.4031, 0.1000, 0.1150 }, + { 32, 0.0787, -2.6638, -0.4012, 0.1000, 0.1510 }, + { 33, 0.1049, -2.7622, -0.3964, 0.1000, 0.1270 }, + { 34, 0.1770, -2.8687, -0.3953, 0.1000, 0.1100 }, + { 35, 0.3213, -2.9507, -0.3974, 0.1000, 0.1190 }, + { 36, 0.4065, -3.0163, -0.4014, 0.1000, 0.1120 }, + { 37, 0.3738, -3.1802, -0.4025, 0.1000, 0.1860 }, + { 38, 0.5508, -3.2048, -0.3966, 0.1000, 0.1490 }, + { 39, 0.5836, -3.3031, -0.3900, 0.1000, 0.1670 }, + { 40, -0.3082, -2.7212, -0.3933, 0.1000, 0.1840 }, + { 41, -0.1967, -2.6474, -0.4017, 0.1000, 0.1600 }, + { 42, -0.1180, -2.7458, -0.3980, 0.1000, 0.1250 }, + { 43, -0.3344, -2.8359, -0.3964, 0.1000, 0.1430 }, + { 44, -0.2492, -2.8933, -0.3838, 0.1000, 0.1890 }, + { 45, -0.1246, -3.0491, -0.3768, 0.1000, 0.1830 }, + { 46, 0.0000, -3.0818, -0.3696, 0.1000, 0.1370 }, + { 47, -0.2295, -3.0409, -0.3706, 0.1000, 0.1660 }, + { 48, -1.3245, 2.6638, 0.0733, 0.0500, 0.0500 }, + { 49, 2.2425, -1.5491, -0.2821, 0.2300, 0.1200 }, + { 50, 0.2164, -2.1311, -0.4000, 0.1000, 0.0690 }, + { 51, 0.2885, -2.2130, -0.4000, 0.1000, 0.0790 }, + { 52, 0.3606, -2.2786, -0.4000, 0.1000, 0.0565 }, + { 53, 0.4328, -2.3442, -0.4000, 0.1000, 0.0575 }, + { 54, 0.5246, -2.4343, -0.4086, 0.1000, 0.0755 }, + { 55, 0.6360, -2.5245, -0.4079, 0.1000, 0.0635 }, + { 56, 0.7541, -2.4261, -0.4007, 0.1000, 0.0550 }, + { 57, 0.7934, -2.2786, -0.3944, 0.1000, 0.0595 }, + { 58, 1.0295, -2.2868, -0.3837, 0.1000, 0.0560 }, + { 59, 0.8459, -2.6474, -0.4051, 0.1000, 0.0930 }, + { 60, 1.0426, -2.6884, -0.4001, 0.1000, 0.0745 }, + { 61, 1.1475, -2.7458, -0.3883, 0.1000, 0.0835 }, + { 62, -0.1967, -1.4180, -0.3988, 0.1000, 0.0920 }, + { 63, -0.0131, -1.2704, -0.3856, 0.1000, 0.0690 }, + { 64, 0.2098, -1.2049, -0.3664, 0.1000, 0.0790 }, + { 65, 0.3410, -1.3196, -0.3652, 0.1000, 0.0565 }, + { 66, 0.5705, -1.2704, -0.3467, 0.1000, 0.0575 }, + { 67, 0.6360, -1.4344, -0.3532, 0.1000, 0.0755 }, + { 68, 0.9246, -1.4180, -0.3329, 0.1000, 0.0635 }, + { 69, 1.0623, -1.3360, -0.3183, 0.1000, 0.0550 }, + { 70, 1.2393, -1.3934, -0.3103, 0.1000, 0.0595 }, + { 71, 1.3639, -1.4753, -0.3079, 0.1000, 0.0560 }, + { 72, 1.4819, -1.5983, -0.3210, 0.1000, 0.0930 }, + { 73, 1.7835, -1.5819, -0.3065, 0.1000, 0.0745 }, + { 74, 1.9343, -2.1065, -0.3307, 0.1000, 0.0835 }, + { 75, 2.1245, -2.3196, -0.3314, 0.1000, 0.0920 }, + { 76, 2.2556, -2.3032, -0.3230, 0.1000, 0.0800 }, + { 77, 2.4196, -2.3688, -0.3165, 0.1000, 0.0625 }, + { 78, 1.7835, -2.5327, -0.3543, 0.1000, 0.0715 }, + { 79, 1.7180, -2.8933, -0.3742, 0.1000, 0.0945 }, + { 80, 1.9343, -3.0409, -0.3727, 0.1000, 0.0915 }, + { 81, 2.4524, -3.4671, -0.3900, 0.1000, 0.0685 }, + { 82, 2.4786, -2.8851, -0.3538, 0.1000, 0.0830 }, + { 83, 2.3343, -2.6228, -0.3420, 0.1000, 0.0830 }, + { 84, 2.8130, -2.0737, -0.2706, 0.1000, 0.0890 }, + { 85, 2.6360, -1.8278, -0.2661, 0.1000, 0.0975 }, + { 86, 2.3958, -1.7130, -0.2774, 0.2000, 0.1555 }, + { 87, 2.2688, -1.2868, -0.2646, 0.1000, 0.0835 }, + { 88, 2.4196, -1.1147, -0.2486, 0.1000, 0.0770 }, + { 89, 2.7802, -2.3933, -0.3017, 0.1000, 0.0655 }, + { 90, 3.0163, -2.4179, -0.2905, 0.1000, 0.0725 }, + { 91, 2.9310, -2.2540, -0.2798, 0.1000, 0.0910 }, + { 92, 2.6622, -2.0983, -0.2823, 0.1000, 0.0680 }, + { 93, 2.3147, -1.9753, -0.2973, 0.1000, 0.0620 }, + { 94, 2.1573, -1.8770, -0.3013, 0.1000, 0.0525 }, + { 95, 2.0196, -1.7868, -0.3044, 0.1000, 0.0970 }, + { 96, 2.7802, -3.3031, -0.3900, 0.1000, 0.0510 }, + { 97, 2.8589, -3.1720, -0.3900, 0.1000, 0.0755 }, + { 98, 3.0163, -2.8114, -0.3383, 0.1000, 0.0835 }, + { 99, 3.5081, -2.4179, -0.2558, 0.1000, 0.0770 }, + { 100, 3.5277, -2.3196, -0.2366, 0.1000, 0.0765 }, + { 101, 3.6654, -2.5819, -0.2566, 0.1000, 0.0805 }, + { 102, 3.7179, -2.7622, -0.2706, 0.1000, 0.0980 }, + { 103, 3.7769, -2.4671, -0.2339, 0.1000, 0.0640 }, + { 104, 3.3441, -2.4671, -0.2693, 0.1000, 0.0940 }, + { -1, 0, 0, 0, 0, 0 }, +}; + +static GeoSet *makeTree( _tree *tree, StateSet *dstate ) +{ + float vv[][3] = + { + { -tree->w/2.0, 0.0, 0.0 }, + { tree->w/2.0, 0.0, 0.0 }, + { tree->w/2.0, 0.0, 2 * tree->h }, + { -tree->w/2.0, 0.0, 2 * tree->h }, + }; + + Vec3 *v = new Vec3[4]; + Vec2 *t = new Vec2[4]; + Vec4 *l = new Vec4[1]; + + int i; + + l[0][0] = l[0][1] = l[0][2] = l[0][3] = 1; + + for( i = 0; i < 4; i++ ) + { + v[i][0] = vv[i][0]; + v[i][1] = vv[i][1]; + v[i][2] = vv[i][2]; + } + + t[0][0] = 0.0; t[0][1] = 0.0; + t[1][0] = 1.0; t[1][1] = 0.0; + t[2][0] = 1.0; t[2][1] = 1.0; + t[3][0] = 0.0; t[3][1] = 1.0; + + GeoSet *gset = new GeoSet; + + gset->setCoords( v ); + + gset->setTextureCoords( t ); + gset->setTextureBinding( GeoSet::BIND_PERVERTEX ); + + gset->setColors( l ); + gset->setColorBinding( GeoSet::BIND_OVERALL ); + + gset->setPrimType( GeoSet::QUADS ); + gset->setNumPrims( 1 ); + + gset->setStateSet( dstate ); + + return gset; +} + + +static float ttx, tty; + +static int ct( const void *a, const void *b ) +{ + _tree *ta = (_tree *)a; + _tree *tb = (_tree *)b; + + float da = sqrtf( sqr(ta->x - ttx) + sqr(ta->y - tty) ); + float db = sqrtf( sqr(tb->x - ttx) + sqr(tb->y - tty) ); + + if( da < db ) + return -1; + else + return 1; +} + + +Node *makeTrees( void ) +{ + Group *group = new Group; + int i; + + getDatabaseCenterRadius( dbcenter, &dbradius ); + struct _tree *t; + + Texture *tex = new Texture; + tex->setImage(osgDB::readImageFile("tree0.rgba")); + + StateSet *dstate = new StateSet; + + dstate->setAttributeAndModes( tex, StateAttribute::ON ); + dstate->setAttribute( new TexEnv ); + + dstate->setAttributeAndModes( new Transparency, StateAttribute::ON ); + + AlphaFunc* alphaFunc = new AlphaFunc; + alphaFunc->setFunction(AlphaFunc::GEQUAL,0.05f); + dstate->setAttributeAndModes( alphaFunc, StateAttribute::ON ); + + dstate->setMode( GL_LIGHTING, StateAttribute::OFF ); + + dstate->setRenderingHint( StateSet::TRANSPARENT_BIN ); + + int tt[] = { 15, 30, 45, 58, 72, 75, 93, 96, 105, -1 }; + int *ttp = tt; + + i = 0; + while( i < 105 ) + { + ttx = trees[i].x; + tty = trees[i].y; + qsort( &trees[i], 105 - i, sizeof( _tree ), ct ); + + i += *ttp; + ttp++; + } + + t = trees; + i = 0; + ttp = tt; + while( *ttp != -1 ) + { + Billboard *bb = new Billboard; + //int starti = i; + + for( ; i < (*ttp); i++ ) + { + t->x -= 0.3f; + float h = Hat(t->x, t->y, t->z ); + Vec3 pos( t->x, t->y, t->z-h ); + GeoSet *gset = makeTree( t, dstate ); + bb->addDrawable( gset, pos ); + t++; + } + group->addChild( bb ); + ttp++; + } + + return group; +} diff --git a/src/Demos/osgconv/Makedepend b/src/Demos/osgconv/Makedepend new file mode 100644 index 000000000..e69de29bb diff --git a/src/Demos/osgconv/Makefile b/src/Demos/osgconv/Makefile new file mode 100644 index 000000000..2145c2f36 --- /dev/null +++ b/src/Demos/osgconv/Makefile @@ -0,0 +1,20 @@ +#!smake +include ../../../Make/makedefs + +C++FILES = \ + osgconv.cpp + +TARGET = ../../../bin/osgconv + +TARGET_BIN_FILES = osgconv + +#note, use this library list when using the Performer osgPlugin. +#LIBS = ${PFLIBS} -losgDB -losg -lGLU -lGL -lm -lXmu -lX11 -lXi + +#note, standard library list. +LIBS = -losgDB -losg -lGLU -lGL -lm -lXmu -lX11 -lXi + +C++FLAGS += -I../../../include +LDFLAGS += -L../../../lib + +include ../../../Make/makerules diff --git a/src/Demos/osgconv/osgconv.cpp b/src/Demos/osgconv/osgconv.cpp new file mode 100644 index 000000000..cc49e43f1 --- /dev/null +++ b/src/Demos/osgconv/osgconv.cpp @@ -0,0 +1,119 @@ +#include +#include + +#include +#include +#include + +int main( int argc, char **argv ) +{ + + if (argc<2) + { + osg::notify(osg::NOTICE)< FileNameList; + FileNameList fileNames; + + for(int i = 1; i < argc; i++ ) + { + + if (argv[i][0]=='-') + { + switch(argv[i][1]) + { + case('l'): + ++i; + if (iloadLibrary(argv[i]); + } + break; + case('e'): + ++i; + if (icreateLibraryNameForExt(argv[i]); + osgDB::Registry::instance()->loadLibrary(libName); + } + break; + } + } else + { + fileNames.push_back(argv[i]); + } + + } + + if (fileNames.empty()) + { + osg::notify(osg::NOTICE)<<"No files specfied."<addChild(child); + } + } + + if (group->getNumChildren()==0) + { + osg::notify(osg::NOTICE)<<"Error no data loaded."<getNumChildren()==1) + { + osgDB::writeNodeFile(*(group->getChild(0)),fileNameOut); + } + else + { + osgDB::writeNodeFile(*group,fileNameOut); + } + + } + + return 0; +} diff --git a/src/Demos/osgcube/Makedepend b/src/Demos/osgcube/Makedepend new file mode 100644 index 000000000..e69de29bb diff --git a/src/Demos/osgcube/Makefile b/src/Demos/osgcube/Makefile new file mode 100644 index 000000000..362211f93 --- /dev/null +++ b/src/Demos/osgcube/Makefile @@ -0,0 +1,15 @@ +#!smake +include ../../../Make/makedefs + +C++FILES = \ + osgcube.cpp + +TARGET = ../../../bin/osgcube + +TARGET_BIN_FILES = osgcube + +LIBS = -losgGLUT -losgDB -losgUtil -losg $(GLUTLIB) -lGLU -lGL -lm -lXmu -lX11 -lXi +C++FLAGS += -I../../../include +LDFLAGS += -L../../../lib + +include ../../../Make/makerules diff --git a/src/Demos/osgcube/osgcube.cpp b/src/Demos/osgcube/osgcube.cpp new file mode 100644 index 000000000..ade9fba5a --- /dev/null +++ b/src/Demos/osgcube/osgcube.cpp @@ -0,0 +1,189 @@ +// simple animation demo written by Graeme Harkness. +// note from Robert to Robert. The animiation techinque +// present here using glut timer callbacks is one +// approach, other approaches will soon be supported +// within the osg itself via an app cullback which +// can be attached to nodes themselves. This later +// method will be the prefered approach (have a look +// at osgreflect's app visitor for a clue.) + + +#include +#include +#include +#include +#include + +#include + +#include + +#include + +#include + +// ---------------------------------------------------------------------- +// Global variables - this is basically the stuff which will be animated +// ---------------------------------------------------------------------- +osg::Transform* myTransform; +osg::GeoSet* cube; + +int mytime=0; // in milliseconds +unsigned int dt=50; // in milliseconds +double omega=0.002; // in inverse milliseconds + +// ---------------------------------------------------------------- +// This is the callback function registered with GLUT to be called +// at a future time in the GLUT loop +// ---------------------------------------------------------------- +void timedCB( int delta_t ) +{ + + static float lastdx = 0; + static float lastdy = 0; + static float lastdz = 0; + + mytime+=dt; + + // --------------------------------------------------------- + // Update the Transform so that the cube will appear to oscillate + // --------------------------------------------------------- + double dx = 0.5 * cos( (double) omega * (double) mytime ); + double dy = 0.5 * sin( (double) omega * (double) mytime ); + double dz = 0.0; + myTransform->preTranslate( -lastdx, -lastdy, -lastdz ); + myTransform->preTranslate( (float) dx, (float) dy, dz ); + lastdx=dx; lastdy=dy; lastdz=dz; + + // Graeme, commeted out this call as the cube itself remains static. + // cube->dirtyDisplayList(); + + // ------------------------------------------- + // If required, reschedule the timed callback + // ------------------------------------------- + if ( delta_t != 0 ) + { + glutTimerFunc( (unsigned int) delta_t, timedCB, delta_t ); + } +} + + +osg::Geode* createCube() +{ + osg::Geode* geode = new osg::Geode(); + + // ------------------------------------------- + // Set up a new GeoSet which will be our cube + // ------------------------------------------- + cube = new osg::GeoSet(); + + // set up the primitives + cube->setPrimType( osg::GeoSet::POLYGON ); + cube->setNumPrims( 6 ); // the six square faces + + // set up the primitive indices + int* cubeLengthList = new int[6]; + cubeLengthList[0] = 4; // each side of the cube has 4 vertices + cubeLengthList[1] = 4; + cubeLengthList[2] = 4; + cubeLengthList[3] = 4; + cubeLengthList[4] = 4; + cubeLengthList[5] = 4; + + cube->setPrimLengths( cubeLengthList ); + + + // set up the coordinates. + osg::Vec3 *cubeCoords = new osg::Vec3[24]; + cubeCoords[0].set( -1.0000f, 1.0000f, -1.000f ); + cubeCoords[1].set( 1.0000f, 1.0000f, -1.0000f ); + cubeCoords[2].set( 1.0000f, -1.0000f, -1.0000f ); + cubeCoords[3].set( -1.0000f, -1.0000f, -1.000 ); + + cubeCoords[4].set( 1.0000f, 1.0000f, -1.0000f ); + cubeCoords[5].set( 1.0000f, 1.0000f, 1.0000f ); + cubeCoords[6].set( 1.0000f, -1.0000f, 1.0000f ); + cubeCoords[7].set( 1.0000f, -1.0000f, -1.0000f ); + + cubeCoords[8].set( 1.0000f, 1.0000f, 1.0000f ); + cubeCoords[9].set( -1.0000f, 1.0000f, 1.000f ); + cubeCoords[10].set( -1.0000f, -1.0000f, 1.000f ); + cubeCoords[11].set( 1.0000f, -1.0000f, 1.0000f ); + + cubeCoords[12].set( -1.0000f, 1.0000f, 1.000 ); + cubeCoords[13].set( -1.0000f, 1.0000f, -1.000 ); + cubeCoords[14].set( -1.0000f, -1.0000f, -1.000 ); + cubeCoords[15].set( -1.0000f, -1.0000f, 1.000 ); + + cubeCoords[16].set( -1.0000f, 1.0000f, 1.000 ); + cubeCoords[17].set( 1.0000f, 1.0000f, 1.0000f ); + cubeCoords[18].set( 1.0000f, 1.0000f, -1.0000f ); + cubeCoords[19].set( -1.0000f, 1.0000f, -1.000f ); + + cubeCoords[20].set( -1.0000f, -1.0000f, 1.000f ); + cubeCoords[21].set( -1.0000f, -1.0000f, -1.000f ); + cubeCoords[22].set( 1.0000f, -1.0000f, -1.0000f ); + cubeCoords[23].set( 1.0000f, -1.0000f, 1.0000f ); + + cube->setCoords( cubeCoords ); + + + // set up the normals. + osg::Vec3 *cubeNormals = new osg::Vec3[6]; + cubeNormals[0].set(0.0f,0.0f,-1.0f); + cubeNormals[1].set(1.0f,0.0f,0.0f); + cubeNormals[2].set(0.0f,0.0f,1.0f); + cubeNormals[3].set(-1.0f,0.0f,0.0f); + cubeNormals[4].set(0.0f,1.0f,0.0f); + cubeNormals[5].set(0.0f,-1.0f,0.0f); + cube->setNormals( cubeNormals ); + cube->setNormalBinding( osg::GeoSet::BIND_PERPRIM ); + + // --------------------------------------- + // Set up a StateSet to make the cube red + // --------------------------------------- + osg::StateSet* cubeState = new osg::StateSet(); + osg::Material* redMaterial = new osg::Material(); + osg::Vec4 red( 1.0f, 0.0f, 0.0f, 1.0f ); + redMaterial->setEmission( osg::Material::FRONT_AND_BACK, red ); + redMaterial->setAmbient( osg::Material::FRONT_AND_BACK, red ); + redMaterial->setDiffuse( osg::Material::FRONT_AND_BACK, red ); + redMaterial->setSpecular( osg::Material::FRONT_AND_BACK, red ); + cubeState->setAttribute( redMaterial ); + + cube->setStateSet( cubeState ); + + geode->addDrawable( cube ); + + return geode; +} + +int main( int argc, char **argv ) +{ + + glutInit( &argc, argv ); + + + myTransform = new osg::Transform(); + myTransform->addChild( createCube() ); + + // --------------------------------------------------------------------- + // Register a timer callback with GLUT, in the first instance as a test + // This will call the function "timedCB(value)" after dt ms + // I have decided to use value as the time for the next scheduling + // If the last parameter=0 then don't reschedule the timer. + // --------------------------------------------------------------------- + glutTimerFunc( dt, timedCB, dt ); + + osgGLUT::Viewer viewer; + viewer.addViewport( myTransform ); + + // register trackball, flight and drive. + viewer.registerCameraManipulator(new osgUtil::TrackballManipulator); + + viewer.open(); + + viewer.run(); + + return 0; +} diff --git a/src/Demos/osgimpostor/Makedepend b/src/Demos/osgimpostor/Makedepend new file mode 100644 index 000000000..e69de29bb diff --git a/src/Demos/osgimpostor/Makefile b/src/Demos/osgimpostor/Makefile new file mode 100644 index 000000000..e01b550e1 --- /dev/null +++ b/src/Demos/osgimpostor/Makefile @@ -0,0 +1,21 @@ +#!smake +include ../../../Make/makedefs + +C++FILES = \ + osgimpostor.cpp + +TARGET = ../../../bin/osgimpostor + +TARGET_BIN_FILES = osgimpostor + +#note, use this library list when using the Performer osgPlugin. +#LIBS = ${PFLIBS} -losgGLUT -losgUtil -losgDB -losg $(GLUTLIB) -lGLU -lGL -lm -lXmu -lX11 -lXi + +#note, standard library list. +LIBS = -losgGLUT -losgUtil -losgDB -losg $(GLUTLIB) -lGLU -lGL -lm -lXmu -lX11 -lXi + +C++FLAGS += -I../../../include +LDFLAGS += -L../../../lib + +include ../../../Make/makerules + diff --git a/src/Demos/osgimpostor/README b/src/Demos/osgimpostor/README new file mode 100644 index 000000000..6e2603a66 --- /dev/null +++ b/src/Demos/osgimpostor/README @@ -0,0 +1,26 @@ +Note: Using sgv with Peformer (for IRIX and Linux users only) +============================================================= + +If you find problems with loading .pfb files its likely that its due to undefined +symbols. This isn't a problem with the OSG implementation, but alas the only +current solution is to directly link you app with the Performer libraries. The +Makefile contains two library list. In Makefile you'll see something like : + + #note, use this library list when using the Performer osgPlugin. + #LIBS = ${PFLIBS} -losgGLUT -losgDB -losg -lGLU -lGL -lm -lXmu -lX11 -lXi + + #note, standard library list. + LIBS = -losgGLUT -losgDB -losg -lGLU -lGL -lm -lXmu -lX11 -lXi + +Simple comment in the LIBS line with PFLIBS and comment out the standard LIBS, +then : + + make clean + make + +Hopefully the Performer distribution will eventually work as a dynamic plugin +but until that day we're stuck with this 'hack'... + + +Robert Osfield, +March 20001. diff --git a/src/Demos/osgimpostor/osgimpostor.cpp b/src/Demos/osgimpostor/osgimpostor.cpp new file mode 100644 index 000000000..5ccb0f7ba --- /dev/null +++ b/src/Demos/osgimpostor/osgimpostor.cpp @@ -0,0 +1,198 @@ +#ifdef USE_MEM_CHECK +#include +#endif + +#include +#include + +#include +#include + +#include +#include +#include +#include + +#include +#include + +#include + +/* + * Function to read several files (typically one) as specified on the command + * line, and return them in an osg::Node + */ +osg::Node* getNodeFromFiles(int argc,char **argv) +{ + osg::Node *rootnode = new osg::Node; + + int i; + + typedef std::vector NodeList; + NodeList nodeList; + for( i = 1; i < argc; i++ ) + { + + if (argv[i][0]=='-') + { + switch(argv[i][1]) + { + case('l'): + ++i; + if (iloadLibrary(argv[i]); + } + break; + case('e'): + ++i; + if (icreateLibraryNameForExt(argv[i]); + osgDB::Registry::instance()->loadLibrary(libName); + } + break; + } + } else + { + osg::Node *node = osgDB::readNodeFile( argv[i] ); + + if( node != (osg::Node *)0L ) + { + if (node->getName().empty()) node->setName( argv[i] ); + nodeList.push_back(node); + } + } + + } + + if (nodeList.size()==0) + { + osg::notify(osg::WARN) << "No data loaded."<1 + { + osg::Group* group = new osg::Group(); + for(NodeList::iterator itr=nodeList.begin(); + itr!=nodeList.end(); + ++itr) + { + group->addChild(*itr); + } + + rootnode = group; + } + + return rootnode; +} + + +int main( int argc, char **argv ) +{ + +#ifdef USE_MEM_CHECK + mtrace(); +#endif + + // initialize the GLUT + glutInit( &argc, argv ); + + if (argc<2) + { + osg::notify(osg::NOTICE)<<"usage:"<(model)==0) + { + const osg::BoundingSphere& bs = model->getBound(); + if (bs.isValid()) + { + + osg::Impostor* impostor = new osg::Impostor; + + // standard LOD settings + impostor->addChild(model); + impostor->setRange(0,0.0f); + impostor->setRange(1,1e7f); + impostor->setCenter(bs.center()); + + // impostor specfic settings. + impostor->setImpostorThresholdToBound(5.0f); + + model = impostor; + + } + } + + // we insert an impostor node above the model, so we keep a handle + // on the rootnode of the model, the is required since the + // InsertImpostorsVisitor can add a new root in automatically and + // we would know about it, other than by following the parent path + // up from model. This is really what should be done, but I'll pass + // on it right now as it requires a getRoots() method to be added to + // osg::Node, and we're about to make a release so no new features! + osg::Group* rootnode = new osg::Group; + rootnode->addChild(model); + + + // now insert impostors in the model using the InsertImpostorsVisitor. + osgUtil::InsertImpostorsVisitor ov; + + // traverse the model and collect all osg::Group's and osg::LOD's. + // however, don't traverse the rootnode since we want to keep it as + // the start of traversal, otherwise the insertImpostor could insert + // and Impostor above the current root, making it nolonger a root! + model->accept(ov); + + // insert the Impostors above groups and LOD's + ov.insertImpostors(); + + + osg::Timer_t after_load = timer.tick(); + cout << "Time for load = "< +#endif + +#include +#include + +#include +#include + +#include +#include +#include + +#include +#include + +#include + +/* + * Function to read several files (typically one) as specified on the command + * line, and return them in an osg::Node + */ +osg::Node* getNodeFromFiles(int argc,char **argv) +{ + osg::Node *rootnode = new osg::Node; + + int i; + + typedef std::vector NodeList; + NodeList nodeList; + for( i = 1; i < argc; i++ ) + { + + if (argv[i][0]=='-') + { + switch(argv[i][1]) + { + case('l'): + ++i; + if (iloadLibrary(argv[i]); + } + break; + case('e'): + ++i; + if (icreateLibraryNameForExt(argv[i]); + osgDB::Registry::instance()->loadLibrary(libName); + } + break; + } + } else + { + osg::Node *node = osgDB::readNodeFile( argv[i] ); + + if( node != (osg::Node *)0L ) + { + if (node->getName().empty()) node->setName( argv[i] ); + nodeList.push_back(node); + } + } + + } + + if (nodeList.size()==0) + { + osg::notify(osg::WARN) << "No data loaded."<1 + { + osg::Group* group = new osg::Group(); + for(NodeList::iterator itr=nodeList.begin(); + itr!=nodeList.end(); + ++itr) + { + group->addChild(*itr); + } + + rootnode = group; + } + + return rootnode; +} + + +int main( int argc, char **argv ) +{ + +#ifdef USE_MEM_CHECK + mtrace(); +#endif + + // initialize the GLUT + glutInit( &argc, argv ); + + if (argc<2) + { + osg::notify(osg::NOTICE)<<"usage:"< +#endif + +#include +#include + +#include +#include + +#include +#include +#include #include -#include "osgGLUT/Viewer" +#include + +#include /* * Function to read several files (typically one) as specified on the command @@ -25,33 +36,33 @@ osg::Node* getNodeFromFiles(int argc,char **argv) { switch(argv[i][1]) { - case('l'): - ++i; - if (iloadLibrary(argv[i]); - } - break; - case('e'): - ++i; - if (icreateLibraryNameForExt(argv[i]); - osg::Registry::instance()->loadLibrary(libName); - } - break; + case('l'): + ++i; + if (iloadLibrary(argv[i]); + } + break; + case('e'): + ++i; + if (icreateLibraryNameForExt(argv[i]); + osgDB::Registry::instance()->loadLibrary(libName); + } + break; } } else { - osg::Node *node = osg::loadNodeFile( argv[i] ); + osg::Node *node = osgDB::readNodeFile( argv[i] ); if( node != (osg::Node *)0L ) { if (node->getName().empty()) node->setName( argv[i] ); nodeList.push_back(node); - } + } } - + } if (nodeList.size()==0) @@ -59,12 +70,12 @@ osg::Node* getNodeFromFiles(int argc,char **argv) osg::notify(osg::WARN) << "No data loaded."<1 + else // size >1 { osg::Group* group = new osg::Group(); for(NodeList::iterator itr=nodeList.begin(); @@ -76,7 +87,7 @@ osg::Node* getNodeFromFiles(int argc,char **argv) rootnode = group; } - + return rootnode; } @@ -84,6 +95,13 @@ osg::Node* getNodeFromFiles(int argc,char **argv) int main( int argc, char **argv ) { +#ifdef USE_MEM_CHECK + mtrace(); +#endif + + // initialize the GLUT + glutInit( &argc, argv ); + if (argc<2) { osg::notify(osg::NOTICE)<<"usage:"< + +#include +#include +#include +#include +#include +#include +#include + +using namespace osg; + +#include "app.h" +DECLARE_APP(wxosgApp) + +//#include + +#include "SceneGraphDlg.h" + +#if defined(__WXGTK__) || defined(__WXMOTIF__) +# include "wxsgv.xpm" +# include "icon1.xpm" +# include "icon2.xpm" +# include "icon3.xpm" +# include "icon4.xpm" +# include "icon5.xpm" +# include "icon6.xpm" +# include "icon7.xpm" +# include "icon8.xpm" +# include "icon9.xpm" +# include "icon10.xpm" +#endif + +///////////////////////////// + +class MyTreeItemData : public wxTreeItemData +{ +public: + MyTreeItemData(Node *pNode) + { + m_pNode = pNode; + } + Node *m_pNode; +}; + + +// WDR: class implementations + +//---------------------------------------------------------------------------- +// SceneGraphDlg +//---------------------------------------------------------------------------- + +// WDR: event table for SceneGraphDlg + +BEGIN_EVENT_TABLE(SceneGraphDlg,wxDialog) + EVT_INIT_DIALOG (SceneGraphDlg::OnInitDialog) + EVT_TREE_SEL_CHANGED( ID_SCENETREE, SceneGraphDlg::OnTreeSelChanged ) + EVT_BUTTON( ID_ZOOMTO, SceneGraphDlg::OnZoomTo ) + EVT_BUTTON( ID_REFRESH, SceneGraphDlg::OnRefresh ) +END_EVENT_TABLE() + +SceneGraphDlg::SceneGraphDlg( wxWindow *parent, wxWindowID id, const wxString &title, + const wxPoint &position, const wxSize& size, long style ) : + wxDialog( parent, id, title, position, size, style ) +{ + SceneGraphFunc( this, TRUE ); + + m_pZoomTo = GetZoomto(); + m_pTree = GetScenetree(); + + m_pZoomTo->Enable(false); + + m_imageListNormal = NULL; + CreateImageList(16); +} + +SceneGraphDlg::~SceneGraphDlg() +{ +} + +/////////// + +void SceneGraphDlg::CreateImageList(int size) +{ + delete m_imageListNormal; + + if ( size == -1 ) + { + m_imageListNormal = NULL; + return; + } + // Make an image list containing small icons + m_imageListNormal = new wxImageList(size, size, TRUE); + + // should correspond to TreeCtrlIcon_xxx enum + wxIcon icons[10]; + icons[0] = wxICON(icon1); + icons[1] = wxICON(icon2); + icons[2] = wxICON(icon3); + icons[3] = wxICON(icon4); + icons[4] = wxICON(icon5); + icons[5] = wxICON(icon6); + icons[6] = wxICON(icon7); + icons[7] = wxICON(icon8); + icons[8] = wxICON(icon9); + icons[9] = wxICON(icon10); + + int sizeOrig = icons[0].GetWidth(); + for ( size_t i = 0; i < WXSIZEOF(icons); i++ ) + { + if ( size == sizeOrig ) + m_imageListNormal->Add(icons[i]); + else + m_imageListNormal->Add(wxImage(icons[i]).Rescale(size, size). + ConvertToBitmap()); + } + m_pTree->SetImageList(m_imageListNormal); +} + + +void SceneGraphDlg::RefreshTreeContents() +{ + // start with a blank slate + m_pTree->DeleteAllItems(); + + Node *pRoot = wxGetApp().Root(); + if (!pRoot) + return; + + // Fill in the tree with nodes + wxTreeItemId hRootItem = m_pTree->AddRoot("Root"); + AddNodeItemsRecursively(hRootItem, pRoot, 0); + m_pTree->Expand(hRootItem); + + m_pSelectedNode = NULL; +} + + +void SceneGraphDlg::AddNodeItemsRecursively(wxTreeItemId hParentItem, + Node *pNode, int depth) +{ + wxString str; + int nImage; + wxTreeItemId hNewItem; + + if (!pNode) return; + + else if (dynamic_cast(pNode)) + { + str = "Light"; + nImage = 4; + } + else if (dynamic_cast(pNode)) + { + str = "Geode"; + nImage = 2; + } + else if (dynamic_cast(pNode)) + { + str = "LOD"; + nImage = 5; + } + else if (dynamic_cast(pNode)) + { + str = "XForm"; + nImage = 9; + } + else if (dynamic_cast(pNode)) + { + // must be just a group for grouping's sake + str = "Group"; + nImage = 3; + } + else + { + // must be something else + str = "Other"; + nImage = 8; + } + std::string name = pNode->getName(); + if (!name.empty()) + { + const char *name2 = name.c_str(); + str += " \""; + str += name2; + str += "\""; + } + + hNewItem = m_pTree->AppendItem(hParentItem, str, nImage, nImage); + + Geode *pGeode = dynamic_cast(pNode); + if (pGeode) + { + int num_mesh = pGeode->getNumDrawables(); + wxTreeItemId hDItem; + + for (int i = 0; i < num_mesh; i++) + { + Drawable *pDraw = pGeode->getDrawable(i); + GeoSet *pGeoSet = dynamic_cast(pDraw); + if (pGeoSet) + { + int iNumPrim = pGeoSet->getNumPrims(); + + GeoSet::PrimitiveType pt = pGeoSet->getPrimType(); + const char *mtype; + switch (pt) + { + case (GeoSet::POINTS) : mtype = "Points"; break; + case (GeoSet::LINES) : mtype = "Lines"; break; + case (GeoSet::LINE_LOOP) : mtype = "LineLoop"; break; + case (GeoSet::LINE_STRIP): mtype = "LineStrip"; break; + case (GeoSet::FLAT_LINE_STRIP) : mtype = "FlatLineStrip"; break; + case (GeoSet::TRIANGLES) : mtype = "Triangles"; break; + case (GeoSet::TRIANGLE_STRIP) : mtype = "TriStrip"; break; + case (GeoSet::FLAT_TRIANGLE_STRIP) : mtype = "FlatTriStrip"; break; + case (GeoSet::TRIANGLE_FAN) : mtype = "TriFan"; break; + case (GeoSet::FLAT_TRIANGLE_FAN) : mtype = "FlatTriFan"; break; + case (GeoSet::QUADS) : mtype = "Quads"; break; + case (GeoSet::QUAD_STRIP) : mtype = "QuadStrip"; break; + case (GeoSet::POLYGON) : mtype = "Polygon"; break; + } + str.Printf("GeoSet %d, %s, %d prims", i, mtype, iNumPrim); + hDItem = m_pTree->AppendItem(hNewItem, str, 6, 6); + } + ImpostorSprite *pImpostorSprite = dynamic_cast(pDraw); + if (pImpostorSprite) + { + str.Printf("ImposterSprite"); + hDItem = m_pTree->AppendItem(hNewItem, str, 9, 9); + } + } + } + + m_pTree->SetItemData(hNewItem, new MyTreeItemData(pNode)); + + Group *pGroup = dynamic_cast(pNode); + if (pGroup) + { + int num_children = pGroup->getNumChildren(); + if (num_children > 200) + { + wxTreeItemId hSubItem; + str.Format("(%d children)", num_children); + hSubItem = m_pTree->AppendItem(hNewItem, str, 8, 8); + } + else + { + for (int i = 0; i < num_children; i++) + { + Node *pChild = pGroup->getChild(i); + if (!pChild) continue; + + AddNodeItemsRecursively(hNewItem, pChild, depth+1); + } + } + } + // expand a bit so that the tree is initially partially exposed + if (depth < 2) + m_pTree->Expand(hNewItem); +} + + +// WDR: handler implementations for SceneGraphDlg + +void SceneGraphDlg::OnRefresh( wxCommandEvent &event ) +{ + RefreshTreeContents(); +} + +void SceneGraphDlg::OnZoomTo( wxCommandEvent &event ) +{ + if (m_pSelectedNode) + wxGetApp().ZoomTo(m_pSelectedNode); +} + +void SceneGraphDlg::OnTreeSelChanged( wxTreeEvent &event ) +{ + wxTreeItemId item = event.GetItem(); + MyTreeItemData *data = (MyTreeItemData *)m_pTree->GetItemData(item); + + m_pSelectedNode = NULL; + + if (data && data->m_pNode) + { + m_pSelectedNode = data->m_pNode; + m_pZoomTo->Enable(true); + } + else + m_pZoomTo->Enable(false); +} + +void SceneGraphDlg::OnInitDialog(wxInitDialogEvent& event) +{ + RefreshTreeContents(); + + wxWindow::OnInitDialog(event); +} + diff --git a/src/Demos/wxsgv/SceneGraphDlg.h b/src/Demos/wxsgv/SceneGraphDlg.h new file mode 100644 index 000000000..ba7d0fbee --- /dev/null +++ b/src/Demos/wxsgv/SceneGraphDlg.h @@ -0,0 +1,65 @@ +// +// Name: SceneGraphDlg.h +// Author: Ben Discoe, ben@washedashore.com +// + +#ifndef __SceneGraphDlg_H__ +#define __SceneGraphDlg_H__ + +#ifdef __GNUG__ + #pragma interface "SceneGraphDlg.cpp" +#endif + +#include "wx/imaglist.h" +#include "wxsgv_wdr.h" + +// WDR: class declarations + +//---------------------------------------------------------------------------- +// SceneGraphDlg +//---------------------------------------------------------------------------- + +class SceneGraphDlg: public wxDialog +{ +public: + // constructors and destructors + SceneGraphDlg( wxWindow *parent, wxWindowID id, const wxString &title, + const wxPoint& pos = wxDefaultPosition, + const wxSize& size = wxDefaultSize, + long style = wxDEFAULT_DIALOG_STYLE ); + ~SceneGraphDlg(); + + void OnInitDialog(wxInitDialogEvent& event); + wxButton *m_pZoomTo; + wxCheckBox *m_pEnabled; + wxTreeCtrl *m_pTree; + + osg::Node *m_pSelectedNode; + + void CreateImageList(int size = 16); + void RefreshTreeContents(); + void AddNodeItemsRecursively(wxTreeItemId hParentItem, + osg::Node *pNode, int depth); + + // WDR: method declarations for SceneGraphDlg + wxButton* GetZoomto() { return (wxButton*) FindWindow( ID_ZOOMTO ); } + wxTreeCtrl* GetScenetree() { return (wxTreeCtrl*) FindWindow( ID_SCENETREE ); } + +private: + // WDR: member variable declarations for SceneGraphDlg + wxImageList *m_imageListNormal; + +private: + // WDR: handler declarations for SceneGraphDlg + void OnRefresh( wxCommandEvent &event ); + void OnZoomTo( wxCommandEvent &event ); + void OnTreeSelChanged( wxTreeEvent &event ); + +private: + DECLARE_EVENT_TABLE() +}; + + + + +#endif diff --git a/src/Demos/wxsgv/app.cpp b/src/Demos/wxsgv/app.cpp new file mode 100644 index 000000000..7cf4d26e2 --- /dev/null +++ b/src/Demos/wxsgv/app.cpp @@ -0,0 +1,110 @@ +// +// Name: app.cpp +// Purpose: The application class for a wxWindows application. +// Author: Ben Discoe, ben@washedashore.com +// + +#ifdef __GNUG__ +#pragma implementation +#pragma interface +#endif + +// For compilers that support precompilation, includes "wx.h". +#include "wx/wxprec.h" + +#ifndef WX_PRECOMP +#include "wx/wx.h" +#endif + +#include +#include +#include +#include +#include + +using namespace osg; +using namespace osgWX; + +#include "app.h" +#include "frame.h" + +IMPLEMENT_APP(wxosgApp) + +wxosgApp::wxosgApp() +{ + m_bInitialized = false; +} + +// +// Initialize the app object +// +bool wxosgApp::OnInit() +{ + // Create the main frame window + wxString title = "wxsgv Demo Viewer"; + wxosgFrame *frame = new wxosgFrame(NULL, title, + wxPoint(50, 50), wxSize(800, 600)); + + // + // Create the 3d scene + // + m_pSceneView = new osgUtil::SceneView(); + m_pSceneView->setDefaults(); + Camera *pCam = new Camera(); + m_pSceneView->setCamera(pCam); + + m_pCameraManipulator = new osgUtil::TrackballManipulator(); + m_pCameraManipulator->setCamera(pCam); + + ref_ptr ea = new WXEventAdapter; + m_pCameraManipulator->init(*ea, *this); + + m_bInitialized = true; + + return true; +} + +void wxosgApp::DoUpdate() +{ + if (!m_bInitialized) + return; + + m_pSceneView->setViewport(0, 0, m_winx, m_winy); + m_pSceneView->cull(); + m_pSceneView->draw(); +} + +void wxosgApp::SetWindowSize(int x, int y) +{ + m_winx = x; + m_winy = y; +} + +void wxosgApp::LoadFile(const char *filename) +{ + Node *node = osgDB::readNodeFile(filename); + + if (!node) + return; + + m_pSceneView->setSceneData(node); + m_pCameraManipulator->setNode(node); + + ref_ptr ea = new WXEventAdapter; + m_pCameraManipulator->home(*ea, *this); +} + +osg::Node *wxosgApp::Root() +{ + return m_pSceneView->getSceneData(); +} + +void wxosgApp::ZoomTo(Node *node) +{ + m_pCameraManipulator->setNode(node); + ref_ptr ea = new WXEventAdapter; + m_pCameraManipulator->home(*ea, *this); +} + + + diff --git a/src/Demos/wxsgv/app.h b/src/Demos/wxsgv/app.h new file mode 100644 index 000000000..7ae735453 --- /dev/null +++ b/src/Demos/wxsgv/app.h @@ -0,0 +1,41 @@ +// +// Copyright (c) 2001 Virtual Terrain Project +// Free for all uses, see license.txt for details. +// + +// forward declaration +namespace osgUtil { + class SceneView; + class CameraManipulator; +} + +#include + +#include +#include + +// Define a new application type +class wxosgApp: public wxApp, public osgUtil::GUIActionAdapter +{ +public: + wxosgApp(); + bool OnInit(); + void DoUpdate(); + void SetWindowSize(int x, int y); + void LoadFile(const char *filename); + void ZoomTo(osg::Node *node); + + osgUtil::CameraManipulator *Manip() { return m_pCameraManipulator.get(); } + osg::Node *Root(); + + virtual void requestRedraw() {} + virtual void requestContinuousUpdate(bool needed=true) {} + virtual void requestWarpPointer(int x,int y) {} + +protected: + osg::ref_ptr m_pSceneView; + osg::ref_ptr m_pCameraManipulator; + int m_winx, m_winy; // Window size + bool m_bInitialized; +}; + diff --git a/src/Demos/wxsgv/canvas.cpp b/src/Demos/wxsgv/canvas.cpp new file mode 100644 index 000000000..6271d5253 --- /dev/null +++ b/src/Demos/wxsgv/canvas.cpp @@ -0,0 +1,188 @@ +// +// Name: canvas.cpp +// Purpose: Implements the canvas class for a wxWindows application. +// Author: Ben Discoe, ben@washedashore.com +// + +// For compilers that support precompilation, includes "wx.h". +#include "wx/wxprec.h" + +#ifndef WX_PRECOMP +#include "wx/wx.h" +#endif + +#include +#include + +using namespace osg; +using namespace osgWX; + +#include "canvas.h" +#include "frame.h" +#include "app.h" + +DECLARE_APP(wxosgApp) + +/* + * wxosgGLCanvas implementation + */ +BEGIN_EVENT_TABLE(wxosgGLCanvas, wxGLCanvas) + EVT_CLOSE(wxosgGLCanvas::OnClose) + EVT_SIZE(wxosgGLCanvas::OnSize) + EVT_PAINT(wxosgGLCanvas::OnPaint) + EVT_CHAR(wxosgGLCanvas::OnChar) + EVT_MOUSE_EVENTS(wxosgGLCanvas::OnMouseEvent) + EVT_ERASE_BACKGROUND(wxosgGLCanvas::OnEraseBackground) +END_EVENT_TABLE() + +wxosgGLCanvas::wxosgGLCanvas(wxWindow *parent, wxWindowID id, + const wxPoint& pos, const wxSize& size, long style, const wxString& name, int* gl_attrib): + wxGLCanvas(parent, id, pos, size, style, name, gl_attrib) +{ + parent->Show(TRUE); + SetCurrent(); + + m_bPainting = false; + m_bRunning = true; + QueueRefresh(FALSE); + + m_initialTick = m_timer.tick(); +} + + +wxosgGLCanvas::~wxosgGLCanvas(void) +{ +} + +void wxosgGLCanvas::QueueRefresh(bool eraseBackground) + // A Refresh routine we can call from inside OnPaint. + // (queues the events rather than dispatching them immediately). +{ + // With wxGTK, you can't do a Refresh() in OnPaint because it doesn't + // queue (post) a Refresh event for later. Rather it dispatches + // (processes) the underlying events immediately via ProcessEvent + // (read, recursive call). See the wxPostEvent docs and Refresh code + // for more details. + if ( eraseBackground ) + { + wxEraseEvent eevent( GetId() ); + eevent.SetEventObject( this ); + wxPostEvent( GetEventHandler(), eevent ); + } + + wxPaintEvent event( GetId() ); + event.SetEventObject( this ); + wxPostEvent( GetEventHandler(), event ); +} + + +void wxosgGLCanvas::OnPaint( wxPaintEvent& event ) +{ + // place the dc inside a scope, to delete it before the end of function + if (1) + { + // This is a dummy, to avoid an endless succession of paint messages. + // OnPaint handlers must always create a wxPaintDC. + wxPaintDC dc(this); +#ifdef __WXMSW__ + if (!GetContext()) return; +#endif + + if (m_bPainting || !m_bRunning) return; + + m_bPainting = true; + + glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT); + + // update the camera manipulator. + if (wxGetApp().Manip()) + { + ref_ptr ea = new WXEventAdapter; + ea->adaptFrame(clockSeconds()); + wxGetApp().Manip()->handle(*ea, wxGetApp()); + } + + // Render the OSG scene + wxGetApp().DoUpdate(); + + SwapBuffers(); + +#ifdef WIN32 + // Call Refresh again for continuous rendering, + if (m_bRunning) + Refresh(FALSE); +#else + // Queue another refresh for continuous rendering. + // (Yield first so we don't starve out keyboard & mouse events.) + // + // FIXME: We may want to use a frame timer instead of immediate- + // redraw so we don't eat so much CPU on machines that can + // easily handle the frame rate. + wxYield(); + QueueRefresh(FALSE); +#endif + + m_bPainting = false; + } + + // Must allow some idle processing to occur - or the toolbars will not + // update, and the close box will not respond! + wxGetApp().ProcessIdle(); +} + +static void Reshape(int width, int height) +{ + glViewport(0, 0, (GLint)width, (GLint)height); +} + +void wxosgGLCanvas::OnClose(wxCloseEvent& event) +{ + m_bRunning = false; +} + +void wxosgGLCanvas::OnSize(wxSizeEvent& event) +{ + // Presumably this is a wxMSWism. + // For wxGTK & wxMotif, all canvas resize events occur before the context + // is set. So ignore this context check and grab the window width/height + // when we get it so it (and derived values such as aspect ratio and + // viewport parms) are computed correctly. +#ifdef __WXMSW__ + if (!GetContext()) return; +#endif + + SetCurrent(); + int width, height; + GetClientSize(& width, & height); + Reshape(width, height); + + if (wxGetApp().Manip()) + { + ref_ptr ea = new WXEventAdapter; + ea->adaptResize(clockSeconds(), 0, 0, width, height); + wxGetApp().Manip()->handle(*ea, wxGetApp()); + } + + wxGetApp().SetWindowSize(width, height); +} + +void wxosgGLCanvas::OnChar(wxKeyEvent& event) +{ + ref_ptr ea = new WXEventAdapter; + ea->adaptKeyboard(clockSeconds(), event.KeyCode(), event.GetX(), event.GetY()); + wxGetApp().Manip()->handle(*ea, wxGetApp()); +} + +void wxosgGLCanvas::OnMouseEvent(wxMouseEvent& event) +{ + // turn WX mouse event into a OSG mouse event + ref_ptr ea = new WXEventAdapter; + ea->adaptMouse(clockSeconds(), &event); + wxGetApp().Manip()->handle(*ea, wxGetApp()); +} + +void wxosgGLCanvas::OnEraseBackground(wxEraseEvent& event) +{ + // Do nothing, to avoid flashing. +} + diff --git a/src/Demos/wxsgv/canvas.h b/src/Demos/wxsgv/canvas.h new file mode 100644 index 000000000..574ec47bb --- /dev/null +++ b/src/Demos/wxsgv/canvas.h @@ -0,0 +1,50 @@ +// +// Name: canvas.h +// +// Copyright (c) 2001 Virtual Terrain Project +// Free for all uses, see license.txt for details. +// + +#ifndef CANVASH +#define CANVASH + +#if !wxUSE_GLCANVAS +#error Please set wxUSE_GLCANVAS to 1 in setup.h. +#endif +#include "wx/glcanvas.h" + +#include + +// +// A Canvas for the main view area. +// +class wxosgGLCanvas: public wxGLCanvas +{ +public: + wxosgGLCanvas(wxWindow *parent, const wxWindowID id = -1, const wxPoint& pos = wxDefaultPosition, + const wxSize& size = wxDefaultSize, long style = 0, const wxString& name = "wxosgGLCanvas", + int* gl_attrib = NULL); + ~wxosgGLCanvas(void); + + void OnPaint(wxPaintEvent& event); + void OnSize(wxSizeEvent& event); + void OnEraseBackground(wxEraseEvent& event); + void OnChar(wxKeyEvent& event); + void OnMouseEvent(wxMouseEvent& event); + void OnClose(wxCloseEvent& event); + void QueueRefresh(bool eraseBackground); + + bool m_bPainting; + bool m_bRunning; + + // time since initClock() in seconds. + float clockSeconds() { return m_timer.delta_s(m_initialTick, m_timer.tick()); } + osg::Timer m_timer; + osg::Timer_t clockTick() { return m_timer.tick(); } + osg::Timer_t m_initialTick; + +protected: + DECLARE_EVENT_TABLE() +}; + +#endif diff --git a/src/Demos/wxsgv/frame.cpp b/src/Demos/wxsgv/frame.cpp new file mode 100644 index 000000000..1b0ef71e1 --- /dev/null +++ b/src/Demos/wxsgv/frame.cpp @@ -0,0 +1,111 @@ +// +// Name: frame.cpp +// Purpose: The frame class for a wxWindows application. +// Author: Ben Discoe, ben@washedashore.com +// + +#ifdef __GNUG__ +#pragma implementation +#pragma interface +#endif + +// For compilers that support precompilation, includes "wx.h". +#include "wx/wxprec.h" + +#ifndef WX_PRECOMP +#include "wx/wx.h" +#endif + +#include "app.h" +#include "frame.h" +#include "canvas.h" + +// IDs for the menu commands +enum +{ + ID_FILE_OPEN, + ID_SCENE_BROWSE +}; + +DECLARE_APP(wxosgApp) + +BEGIN_EVENT_TABLE(wxosgFrame, wxFrame) + EVT_MENU(wxID_EXIT, wxosgFrame::OnExit) + EVT_MENU(ID_FILE_OPEN, wxosgFrame::OnOpen) + EVT_MENU(ID_SCENE_BROWSE, wxosgFrame::OnSceneBrowse) +END_EVENT_TABLE() + +// My frame constructor +wxosgFrame::wxosgFrame(wxFrame *parent, const wxString& title, const wxPoint& pos, + const wxSize& size, long style): + wxFrame(parent, -1, title, pos, size, style) +{ + // Make a wxosgGLCanvas + // FIXME: Can remove this special case once wxMotif 2.3 is released +#ifdef __WXMOTIF__ + int gl_attrib[20] = { GLX_RGBA, GLX_RED_SIZE, 1, GLX_GREEN_SIZE, 1, + GLX_BLUE_SIZE, 1, GLX_DEPTH_SIZE, 1, + GLX_DOUBLEBUFFER, None }; +#else + int *gl_attrib = NULL; +#endif + + m_canvas = new wxosgGLCanvas(this, -1, wxPoint(0, 0), wxSize(-1, -1), 0, + "wxosgGLCanvas", gl_attrib); + + // File (project) menu + wxMenu *fileMenu = new wxMenu; + fileMenu->Append(ID_FILE_OPEN, "&Open\tCtrl+O", "Open OSG File"); + fileMenu->AppendSeparator(); + fileMenu->Append(wxID_EXIT, "&Exit\tEsc", "Exit Viewer"); + + // Scene menu + wxMenu *sceneMenu = new wxMenu; + sceneMenu->Append(ID_SCENE_BROWSE, "&Browse Scene Graph\tCtrl+G", "Browse Scene Graph"); + + wxMenuBar *menuBar = new wxMenuBar; + menuBar->Append(fileMenu, "&Project"); + menuBar->Append(sceneMenu, "&Scene"); + SetMenuBar(menuBar); + + // Show the frame + Show(TRUE); + +#if 1 + m_pSceneGraphDlg = new SceneGraphDlg(this, -1, "Scene Graph", + wxDefaultPosition, wxDefaultSize, wxDEFAULT_DIALOG_STYLE | wxRESIZE_BORDER); + m_pSceneGraphDlg->SetSize(250, 350); +#endif + + m_canvas->SetCurrent(); +} + +wxosgFrame::~wxosgFrame() +{ + delete m_canvas; +} + + +// +// Handle menu commands +// + +void wxosgFrame::OnExit(wxCommandEvent& event) +{ + m_canvas->m_bRunning = false; + Destroy(); +} + +void wxosgFrame::OnOpen(wxCommandEvent& event) +{ + wxFileDialog loadFile(NULL, "Load Project", "", "", + "OSG Files (*.osg)|*.osg|", wxOPEN); + if (loadFile.ShowModal() == wxID_OK) + wxGetApp().LoadFile(loadFile.GetPath()); +} + +void wxosgFrame::OnSceneBrowse(wxCommandEvent& event) +{ + m_pSceneGraphDlg->Show(TRUE); +} + diff --git a/src/Demos/wxsgv/frame.h b/src/Demos/wxsgv/frame.h new file mode 100644 index 000000000..7645651e7 --- /dev/null +++ b/src/Demos/wxsgv/frame.h @@ -0,0 +1,35 @@ +// +// Name: frame.h +// +// Copyright (c) 2001 Virtual Terrain Project +// Free for all uses, see license.txt for details. +// + +#ifndef FRAMEH +#define FRAMEH + +#include "SceneGraphDlg.h" + +class wxosgFrame: public wxFrame +{ +public: + wxosgFrame(wxFrame *frame, const wxString& title, const wxPoint& pos, + const wxSize& size, long style = wxDEFAULT_FRAME_STYLE); + ~wxosgFrame(); + + // command handlers + void OnExit(wxCommandEvent& event); + void OnOpen(wxCommandEvent& event); + void OnSceneBrowse(wxCommandEvent& event); + +public: + class wxosgGLCanvas *m_canvas; + SceneGraphDlg *m_pSceneGraphDlg; + +protected: + +DECLARE_EVENT_TABLE() +}; + +#endif + diff --git a/src/Demos/wxsgv/icons/camera.ico b/src/Demos/wxsgv/icons/camera.ico new file mode 100644 index 000000000..449029ac7 Binary files /dev/null and b/src/Demos/wxsgv/icons/camera.ico differ diff --git a/src/Demos/wxsgv/icons/engine.ico b/src/Demos/wxsgv/icons/engine.ico new file mode 100644 index 000000000..5b52a4179 Binary files /dev/null and b/src/Demos/wxsgv/icons/engine.ico differ diff --git a/src/Demos/wxsgv/icons/geom.ico b/src/Demos/wxsgv/icons/geom.ico new file mode 100644 index 000000000..597c89f8a Binary files /dev/null and b/src/Demos/wxsgv/icons/geom.ico differ diff --git a/src/Demos/wxsgv/icons/group.ico b/src/Demos/wxsgv/icons/group.ico new file mode 100644 index 000000000..636845406 Binary files /dev/null and b/src/Demos/wxsgv/icons/group.ico differ diff --git a/src/Demos/wxsgv/icons/icon1.xpm b/src/Demos/wxsgv/icons/icon1.xpm new file mode 100644 index 000000000..4926b2622 --- /dev/null +++ b/src/Demos/wxsgv/icons/icon1.xpm @@ -0,0 +1,29 @@ +/* XPM */ +static char *icon1_xpm[] = { +/* width height ncolors chars_per_pixel */ +"16 16 6 1", +/* colors */ +"` c #000000", +"a c #C0C0C0", +"b c #FF0000", +"c c #FFFFFF", +"d c #FFFF00", +"e c #808000", +/* pixels */ +"cccccccccccccccc", +"cccccccccceddecc", +"ccccccccceddddec", +"ccbbbcccceddddec", +"cc```cccceddddec", +"a`````````edde`a", +"``````accca`````", +"``aaa`ccccc`````", +"`````ccccccc````", +"``````ccccc`````", +"``````accca`````", +"a``````````````a", +"ca````````````ac", +"cccccccccccccccc", +"cccccccccccccccc", +"cccccccccccccccc" +}; diff --git a/src/Demos/wxsgv/icons/icon10.xpm b/src/Demos/wxsgv/icons/icon10.xpm new file mode 100644 index 000000000..21d51f409 --- /dev/null +++ b/src/Demos/wxsgv/icons/icon10.xpm @@ -0,0 +1,28 @@ +/* XPM */ +static char *icon10_xpm[] = { +/* width height ncolors chars_per_pixel */ +"16 16 5 1", +/* colors */ +"` c #00FF00", +"a c #FF0000", +"b c #FFFFFF", +"c c #808000", +"d c #0000FF", +/* pixels */ +"bbbbbbbbbbbbbbbb", +"bbbbbbbbbbbbbbbb", +"bbb``bbbbbbbbbbb", +"bb````bbbbdddbbb", +"bbb``bbbbbdddbbb", +"bbb``bbbbddddbbb", +"bbb``bbbdddbbbbb", +"bbb``bbdddbbbbbb", +"bbb``bdddbbbbbbb", +"bbb``dddbbbbbbbb", +"bbb``ddbbbbbabbb", +"bbb`caaaaaaaaabb", +"bbbcaaaaaaaaaabb", +"bbbbbbbbbbbbabbb", +"bbbbbbbbbbbbbbbb", +"bbbbbbbbbbbbbbbb" +}; diff --git a/src/Demos/wxsgv/icons/icon2.xpm b/src/Demos/wxsgv/icons/icon2.xpm new file mode 100644 index 000000000..e6a052a25 --- /dev/null +++ b/src/Demos/wxsgv/icons/icon2.xpm @@ -0,0 +1,27 @@ +/* XPM */ +static char *icon2_xpm[] = { +/* width height ncolors chars_per_pixel */ +"16 16 4 1", +/* colors */ +"` c #000000", +"a c #C0C0C0", +"b c #808080", +"c c #FFFFFF", +/* pixels */ +"cccccccccccccccc", +"ccccb`bccb`bcccc", +"cccca``cc``acccc", +"ccccc``bb``ccccc", +"ca`ccb````bcc`ac", +"c```b``````b```c", +"ca`````bb`````ac", +"cccb``bccb``bccc", +"cccb``bccb``bccc", +"ca`````bb`````ac", +"c```b``````b```c", +"ca`ccb````bcc`ac", +"ccccc``bb``ccccc", +"cccca``cc``acccc", +"ccccb`bccb`bcccc", +"cccccccccccccccc" +}; diff --git a/src/Demos/wxsgv/icons/icon3.xpm b/src/Demos/wxsgv/icons/icon3.xpm new file mode 100644 index 000000000..b020786fe --- /dev/null +++ b/src/Demos/wxsgv/icons/icon3.xpm @@ -0,0 +1,30 @@ +/* XPM */ +static char *icon3_xpm[] = { +/* width height ncolors chars_per_pixel */ +"16 16 7 1", +/* colors */ +"` c #000000", +"a c #00FF00", +"b c #C0C0C0", +"c c #000080", +"d c #FFFFFF", +"e c #008000", +"f c #0000FF", +/* pixels */ +"ddddddd`dddddddd", +"dddddd```ddddddd", +"ddddd`a``bdddddd", +"dddd`aa`f`dddddd", +"ddd`aaa`ff`ddddd", +"dd`aaaa`fff`dddd", +"d`aaaaacfff`bddd", +"`aaaaaecffff`ddd", +"b`aaaaecfffff`dd", +"d`aaaa`fffffff`d", +"dd`aaa`fffffff`b", +"ddd`aa`fffffff``", +"dddb`a`fff````bd", +"dddd`a````bddddd", +"ddddd``bdddddddd", +"dddddddddddddddd" +}; diff --git a/src/Demos/wxsgv/icons/icon4.xpm b/src/Demos/wxsgv/icons/icon4.xpm new file mode 100644 index 000000000..8c21f6b86 --- /dev/null +++ b/src/Demos/wxsgv/icons/icon4.xpm @@ -0,0 +1,27 @@ +/* XPM */ +static char *icon4_xpm[] = { +/* width height ncolors chars_per_pixel */ +"16 16 4 1", +/* colors */ +"` c #000000", +"a c #FFFFFF", +"b c #FFFF00", +"c c #808000", +/* pixels */ +"aaaaaaaaaaaaaaaa", +"aaaaac````caaaaa", +"aaac`bbbbbb`caaa", +"aac`bbbbbbbb`caa", +"aa`bbbc``cbbb`aa", +"accbb`caac`bbcca", +"a`bbccaaaaccbbca", +"a`bb`aaaaaa`bb`a", +"a`bb`aaaaaa`bb`a", +"a`bbccaaaaccbbca", +"accbb`caac`bbcca", +"aa`bbbc``cbbb`aa", +"aaa`bbbbbbbb`aaa", +"aaaa`bbbbbb`aaaa", +"aaaaac````caaaaa", +"aaaaaaaaaaaaaaaa" +}; diff --git a/src/Demos/wxsgv/icons/icon5.xpm b/src/Demos/wxsgv/icons/icon5.xpm new file mode 100644 index 000000000..d626c5164 --- /dev/null +++ b/src/Demos/wxsgv/icons/icon5.xpm @@ -0,0 +1,28 @@ +/* XPM */ +static char *icon5_xpm[] = { +/* width height ncolors chars_per_pixel */ +"16 16 5 1", +/* colors */ +"` c #000000", +"a c #C0C0C0", +"b c #FFFFFF", +"c c #FFFF00", +"d c #808000", +/* pixels */ +"bbbbbbbbbbbbbbbb", +"bbbbdbbbbbbbdbbb", +"dbbbbd````bdbbbb", +"bdbbb`bbcb`bbbbb", +"bbdd`bbcccb`bbbb", +"bbbb`bcbcbc`dddd", +"bbbb`cccbcb`bbbb", +"bbdd`ccccbc`dbbb", +"ddbb`bccccc`bddb", +"bbbbb`bccb`bbbbd", +"bbbbdb````bbdbbb", +"bbbdbb````bbbdbb", +"bbbdbb````bbbdbb", +"bbdbbb````bbbbdb", +"bbbbbba``abbbbbb", +"bbbbbbbbbbbbbbbb" +}; diff --git a/src/Demos/wxsgv/icons/icon6.xpm b/src/Demos/wxsgv/icons/icon6.xpm new file mode 100644 index 000000000..f68291f6c --- /dev/null +++ b/src/Demos/wxsgv/icons/icon6.xpm @@ -0,0 +1,29 @@ +/* XPM */ +static char *icon6_xpm[] = { +/* width height ncolors chars_per_pixel */ +"16 16 6 1", +/* colors */ +"` c #000000", +"a c #C0C0C0", +"b c #808080", +"c c #FFFFFF", +"d c #FFFF00", +"e c #808000", +/* pixels */ +"cccccccccccccccc", +"cabbbbbbbbaccccc", +"cb````````bccccc", +"cb`dddddd`bccccc", +"cb`dddddd`bbaccc", +"cb`dddddd```bacc", +"cb`dddddd`dd`bcc", +"cb`dddddd`dd`bac", +"cb`dddddd`ddd`bc", +"cb````````ddd`bc", +"cabbb`ddddddebac", +"cccab`dddddd`bcc", +"ccccab``dde`bacc", +"cccccabb``bbaccc", +"cccccccabbaccccc", +"cccccccccccccccc" +}; diff --git a/src/Demos/wxsgv/icons/icon7.xpm b/src/Demos/wxsgv/icons/icon7.xpm new file mode 100644 index 000000000..0596ceaa0 --- /dev/null +++ b/src/Demos/wxsgv/icons/icon7.xpm @@ -0,0 +1,29 @@ +/* XPM */ +static char *icon7_xpm[] = { +/* width height ncolors chars_per_pixel */ +"16 16 6 1", +/* colors */ +"` c #000000", +"a c #00FF00", +"b c #C0C0C0", +"c c #808080", +"d c #FFFFFF", +"e c #008000", +/* pixels */ +"dddddddddddddddd", +"dddddddddddddddd", +"ddddddd`dddddddd", +"ddddddbe`ddddddd", +"dddddd`aebdddddd", +"dddddbeaa`dddddd", +"ddddd`aaaebddddd", +"ddddbeaaaa`ddddd", +"dddd`aaaaaaedddd", +"ddddeaaaaaa`dddd", +"dddeaaaaaaaa`ddd", +"ddd`aaaaaaaaebdd", +"ddbeaaaaaaaaa`dd", +"dd`aaaaaaaaaaacd", +"dd`````````````d", +"dddddddddddddddd" +}; diff --git a/src/Demos/wxsgv/icons/icon8.xpm b/src/Demos/wxsgv/icons/icon8.xpm new file mode 100644 index 000000000..59298efa4 --- /dev/null +++ b/src/Demos/wxsgv/icons/icon8.xpm @@ -0,0 +1,26 @@ +/* XPM */ +static char *icon8_xpm[] = { +/* width height ncolors chars_per_pixel */ +"16 16 3 1", +/* colors */ +"` c #000000", +"a c #FFFFFF", +"b c #0000FF", +/* pixels */ +"aaaaaaaaaaaaaaaa", +"aaaaaaaa`aaaaaaa", +"aaaaaaaa``aaaaaa", +"aaaaaaaa`b`aaaaa", +"aaaaaaaa`bb`aaaa", +"aaaaaaaa`bbb`aaa", +"a````````bbbb`aa", +"a`bbbbbbbbbbbb`a", +"a`bbbbbbbbbbbb`a", +"a````````bbbb`aa", +"aaaaaaaa`bbb`aaa", +"aaaaaaaa`bb`aaaa", +"aaaaaaaa`b`aaaaa", +"aaaaaaaa``aaaaaa", +"aaaaaaaa`aaaaaaa", +"aaaaaaaaaaaaaaaa" +}; diff --git a/src/Demos/wxsgv/icons/icon9.xpm b/src/Demos/wxsgv/icons/icon9.xpm new file mode 100644 index 000000000..d9244139b --- /dev/null +++ b/src/Demos/wxsgv/icons/icon9.xpm @@ -0,0 +1,28 @@ +/* XPM */ +static char *icon9_xpm[] = { +/* width height ncolors chars_per_pixel */ +"16 16 5 1", +/* colors */ +"` c #000000", +"a c #C0C0C0", +"b c #808080", +"c c #000080", +"d c #FFFFFF", +/* pixels */ +"dddddddddddddddd", +"dddddacccccadddd", +"ddddacccccccaddd", +"dddacccbdacccddd", +"dddacccddacccddd", +"dddabcbddacccddd", +"ddddddddacccaddd", +"dddddddacccaaddd", +"ddddddaacccadddd", +"ddddddacccaddddd", +"ddddddabcbaddddd", +"dddddddddddddddd", +"dddddddb`bdddddd", +"ddddddacccaddddd", +"dddddddbcbdddddd", +"dddddddddddddddd" +}; diff --git a/src/Demos/wxsgv/icons/light.ico b/src/Demos/wxsgv/icons/light.ico new file mode 100644 index 000000000..fb0187402 Binary files /dev/null and b/src/Demos/wxsgv/icons/light.ico differ diff --git a/src/Demos/wxsgv/icons/lod.ico b/src/Demos/wxsgv/icons/lod.ico new file mode 100644 index 000000000..eb2c216a9 Binary files /dev/null and b/src/Demos/wxsgv/icons/lod.ico differ diff --git a/src/Demos/wxsgv/icons/mesh.ico b/src/Demos/wxsgv/icons/mesh.ico new file mode 100644 index 000000000..ce76f84d6 Binary files /dev/null and b/src/Demos/wxsgv/icons/mesh.ico differ diff --git a/src/Demos/wxsgv/icons/top.ico b/src/Demos/wxsgv/icons/top.ico new file mode 100644 index 000000000..99f87d22c Binary files /dev/null and b/src/Demos/wxsgv/icons/top.ico differ diff --git a/src/Demos/wxsgv/icons/unknown.ico b/src/Demos/wxsgv/icons/unknown.ico new file mode 100644 index 000000000..46a492dda Binary files /dev/null and b/src/Demos/wxsgv/icons/unknown.ico differ diff --git a/src/Demos/wxsgv/icons/wxsgv.ico b/src/Demos/wxsgv/icons/wxsgv.ico new file mode 100644 index 000000000..c517e7962 Binary files /dev/null and b/src/Demos/wxsgv/icons/wxsgv.ico differ diff --git a/src/Demos/wxsgv/icons/wxsgv.xpm b/src/Demos/wxsgv/icons/wxsgv.xpm new file mode 100644 index 000000000..4e4333417 --- /dev/null +++ b/src/Demos/wxsgv/icons/wxsgv.xpm @@ -0,0 +1,48 @@ +/* XPM */ +static char *wxsgv[] = { +/* width height num_colors chars_per_pixel */ +" 32 32 9 1", +/* colors */ +". c #000000", +"# c #000080", +"a c #0000ff", +"b c #008000", +"c c #00ff00", +"d c #808000", +"e c #808080", +"f c #ffff00", +"g c #ffffff", +/* pixels */ +"gggggggggggggggggggggggggggggggg", +"ggggd....dgggggggggggggggggggggg", +"ggd.ffffffddgggggggggggggggggggg", +"gd.ffffffffddggggggggggggggggggg", +"g.fffd..dfffdggggggggggggggggggg", +"ddffddggdddfddgggggggggggggggggg", +".ffddggggddffdgggggggggggggggggg", +".ff.gggggg.dfdgggggggggggggggggg", +".ff.gggggg.dfdgggggggggggggggggg", +".ffddgggg.ddfdgggggggggggggggggg", +"ddffddgg..dffdgggggggggggggggggg", +"g.ffdd..ddffdggggggggggggggggggg", +"ggdfffdddffdgggggggggggggggggggg", +"gggdffffffdggggggggggggggggggggg", +"ggggddddddgggggggggggggggggggggg", +"gggggggggggggggggggggggggggggggg", +"gggggggeggggggggggggggg.gggggggg", +"gggggggggggggggggggggg...ggggggg", +"gggggggeggggggggggggg.b..egggggg", +"gggggggggggggggggggg.cc.##gggggg", +"gggeeeeeeeeeggggggg.ccc.#a#ggggg", +"gggegggggggegggggg.cccc.#aa#gggg", +"gggeggg.gggeggggg.ccccc#aaa#eggg", +"gggeggg.gggegggg.bccccb#aaaa#ggg", +"gggeg.....gegegeebccccb#aaaaa#gg", +"gggeggg.gggeggggg.ccccb#aaaaaa#g", +"gggeggg.gggeggggggbccc.aaaaaaa#e", +"gggegggggggegggggggbcc.aaaaaaa#.", +"gggeeeeeeeeegggggggebc.aaa#####g", +"gggggggggggggggggggg.c.###eggggg", +"gggggggggggggggggggggb.egggggggg", +"gggggggggggggggggggggggggggggggg" +}; diff --git a/src/Demos/wxsgv/icons/xform.ico b/src/Demos/wxsgv/icons/xform.ico new file mode 100644 index 000000000..7e85d0d17 Binary files /dev/null and b/src/Demos/wxsgv/icons/xform.ico differ diff --git a/src/Demos/wxsgv/wxsgv.rc b/src/Demos/wxsgv/wxsgv.rc new file mode 100644 index 000000000..fc8e0ec8b --- /dev/null +++ b/src/Demos/wxsgv/wxsgv.rc @@ -0,0 +1,14 @@ + +application ICON "wxsgv.ico" +#include "wx/msw/wx.rc" + +icon1 ICON "icons/camera.ico" +icon2 ICON "icons/engine.ico" +icon3 ICON "icons/geom.ico" +icon4 ICON "icons/group.ico" +icon5 ICON "icons/light.ico" +icon6 ICON "icons/lod.ico" +icon7 ICON "icons/mesh.ico" +icon8 ICON "icons/top.ico" +icon9 ICON "icons/unknown.ico" +icon10 ICON "icons/xform.ico" diff --git a/src/Demos/wxsgv/wxsgv.wdr b/src/Demos/wxsgv/wxsgv.wdr new file mode 100644 index 000000000..55ecfe3b0 Binary files /dev/null and b/src/Demos/wxsgv/wxsgv.wdr differ diff --git a/src/Demos/wxsgv/wxsgv_wdr.cpp b/src/Demos/wxsgv/wxsgv_wdr.cpp new file mode 100644 index 000000000..a27437b61 --- /dev/null +++ b/src/Demos/wxsgv/wxsgv_wdr.cpp @@ -0,0 +1,125 @@ +//------------------------------------------------------------------------------ +// Source code generated by wxDesigner from file: wxsgv.wdr +// Do not modify this file, all changes will be lost! +//------------------------------------------------------------------------------ + +#ifdef __GNUG__ + #pragma implementation "wxsgv_wdr.cpp" +#endif + +// For compilers that support precompilation +#include "wx/wxprec.h" + +#ifdef __BORLANDC__ + #pragma hdrstop +#endif + +// Include private header +#include "wxsgv_wdr.h" + + +// Implement window functions + +void SceneGraphFunc( wxPanel *parent, bool call_fit ) +{ + wxSizer *item0 = new wxBoxSizer( wxVERTICAL ); + + wxTreeCtrl *item1 = new wxTreeCtrl( parent, ID_SCENETREE, wxDefaultPosition, wxDefaultSize, wxTR_HAS_BUTTONS|wxSUNKEN_BORDER ); + item0->Add( item1, 1, wxGROW|wxALIGN_CENTER_VERTICAL|wxALL, 5 ); + + wxSizer *item2 = new wxBoxSizer( wxHORIZONTAL ); + + wxButton *item3 = new wxButton( parent, ID_ZOOMTO, "Zoom To", wxDefaultPosition, wxSize(60,-1), 0 ); + item2->Add( item3, 0, wxALIGN_CENTRE|wxALL, 5 ); + + wxButton *item4 = new wxButton( parent, ID_REFRESH, "Refresh", wxDefaultPosition, wxSize(55,-1), 0 ); + item2->Add( item4, 0, wxALIGN_CENTRE|wxALL, 5 ); + + item0->Add( item2, 0, wxALIGN_CENTRE|wxALL, 0 ); + + parent->SetAutoLayout( TRUE ); + parent->SetSizer( item0 ); + if (call_fit) + { + item0->Fit( parent ); + item0->SetSizeHints( parent ); + } +} + +void CameraDialogFunc( wxPanel *parent, bool call_fit ) +{ + wxSizer *item0 = new wxBoxSizer( wxVERTICAL ); + + wxSizer *item1 = new wxBoxSizer( wxHORIZONTAL ); + + wxStaticText *item2 = new wxStaticText( parent, ID_TEXT, "Horizontal FOV (degrees)", wxDefaultPosition, wxDefaultSize, 0 ); + item1->Add( item2, 0, wxALIGN_CENTRE|wxALL, 5 ); + + wxTextCtrl *item3 = new wxTextCtrl( parent, ID_FOV, "", wxDefaultPosition, wxSize(60,-1), 0 ); + item1->Add( item3, 0, wxALIGN_CENTRE|wxALL, 0 ); + + wxSlider *item4 = new wxSlider( parent, ID_FOVSLIDER, 0, 0, 100, wxDefaultPosition, wxSize(100,-1), 0 ); + item1->Add( item4, 0, wxALIGN_CENTRE|wxALL, 0 ); + + item0->Add( item1, 0, wxALIGN_RIGHT|wxALIGN_CENTER_VERTICAL|wxTOP, 5 ); + + wxSizer *item5 = new wxBoxSizer( wxHORIZONTAL ); + + wxStaticText *item6 = new wxStaticText( parent, ID_TEXT, "Near Clipping Plane (meters):", wxDefaultPosition, wxDefaultSize, 0 ); + item5->Add( item6, 0, wxALIGN_CENTRE|wxALL, 5 ); + + wxTextCtrl *item7 = new wxTextCtrl( parent, ID_NEAR, "", wxDefaultPosition, wxSize(60,-1), 0 ); + item5->Add( item7, 0, wxALIGN_CENTRE|wxALL, 0 ); + + wxSlider *item8 = new wxSlider( parent, ID_NEARSLIDER, 0, 0, 100, wxDefaultPosition, wxSize(100,-1), 0 ); + item5->Add( item8, 0, wxALIGN_CENTRE|wxALL, 0 ); + + item0->Add( item5, 0, wxALIGN_RIGHT|wxALIGN_CENTER_VERTICAL|wxALL, 0 ); + + wxSizer *item9 = new wxBoxSizer( wxHORIZONTAL ); + + wxStaticText *item10 = new wxStaticText( parent, ID_TEXT, "Far Clipping Plane (meters):", wxDefaultPosition, wxDefaultSize, 0 ); + item9->Add( item10, 0, wxALIGN_CENTRE|wxALL, 5 ); + + wxTextCtrl *item11 = new wxTextCtrl( parent, ID_FAR, "", wxDefaultPosition, wxSize(60,-1), 0 ); + item9->Add( item11, 0, wxALIGN_CENTRE|wxALL, 0 ); + + wxSlider *item12 = new wxSlider( parent, ID_FARSLIDER, 0, 0, 100, wxDefaultPosition, wxSize(100,-1), 0 ); + item9->Add( item12, 0, wxALIGN_CENTRE|wxALL, 0 ); + + item0->Add( item9, 0, wxALIGN_RIGHT|wxALIGN_CENTER_VERTICAL|wxALL, 0 ); + + wxStaticLine *item13 = new wxStaticLine( parent, ID_LINE, wxDefaultPosition, wxSize(20,-1), wxLI_HORIZONTAL ); + item0->Add( item13, 0, wxGROW|wxALIGN_CENTER_VERTICAL|wxALL, 5 ); + + wxSizer *item14 = new wxBoxSizer( wxHORIZONTAL ); + + wxStaticText *item15 = new wxStaticText( parent, ID_TEXT, "Navigation Speed (m/frame):", wxDefaultPosition, wxDefaultSize, 0 ); + item14->Add( item15, 0, wxALIGN_CENTRE|wxALL, 5 ); + + wxTextCtrl *item16 = new wxTextCtrl( parent, ID_SPEED, "", wxDefaultPosition, wxSize(60,-1), 0 ); + item14->Add( item16, 0, wxALIGN_CENTRE|wxALL, 0 ); + + wxSlider *item17 = new wxSlider( parent, ID_SPEEDSLIDER, 0, 0, 100, wxDefaultPosition, wxSize(100,-1), 0 ); + item14->Add( item17, 0, wxALIGN_CENTRE, 0 ); + + item0->Add( item14, 0, wxALIGN_RIGHT|wxALIGN_CENTER_VERTICAL|wxBOTTOM, 5 ); + + parent->SetAutoLayout( TRUE ); + parent->SetSizer( item0 ); + if (call_fit) + { + item0->Fit( parent ); + item0->SetSizeHints( parent ); + } +} + +// Implement bitmap functions + +wxBitmap MyBitmapsFunc( size_t index ) +{ + return wxNullBitmap; +} + + +// End of generated file diff --git a/src/Demos/wxsgv/wxsgv_wdr.h b/src/Demos/wxsgv/wxsgv_wdr.h new file mode 100644 index 000000000..fd234fc59 --- /dev/null +++ b/src/Demos/wxsgv/wxsgv_wdr.h @@ -0,0 +1,53 @@ +//------------------------------------------------------------------------------ +// Header generated by wxDesigner from file: wxsgv.wdr +// Do not modify this file, all changes will be lost! +//------------------------------------------------------------------------------ + +#ifndef __WDR_wxsgv_H__ +#define __WDR_wxsgv_H__ + +#ifdef __GNUG__ + #pragma interface "wxsgv_wdr.cpp" +#endif + +// Include wxWindows' headers + +#ifndef WX_PRECOMP + #include +#endif + +#include +#include +#include +#include +#include +#include +#include +#include + +// Declare window functions + +#define ID_SCENETREE 10000 +#define ID_ZOOMTO 10001 +#define ID_REFRESH 10002 +void SceneGraphFunc( wxPanel *parent, bool call_fit = TRUE ); + +#define ID_TEXT 10003 +#define ID_FOV 10004 +#define ID_FOVSLIDER 10005 +#define ID_NEAR 10006 +#define ID_NEARSLIDER 10007 +#define ID_FAR 10008 +#define ID_FARSLIDER 10009 +#define ID_LINE 10010 +#define ID_SPEED 10011 +#define ID_SPEEDSLIDER 10012 +void CameraDialogFunc( wxPanel *parent, bool call_fit = TRUE ); + +// Declare bitmap functions + +wxBitmap MyBitmapsFunc( size_t index ); + +#endif + +// End of generated file diff --git a/src/Makefile b/src/Makefile index 646f6e5e4..2e37ea70c 100644 --- a/src/Makefile +++ b/src/Makefile @@ -2,35 +2,38 @@ SHELL=/bin/sh -DIRS = osg osgUtil osgGLUT Demos osgPlugins +DIRS = osg osgDB osgUtil osgGLUT Demos osgPlugins all : - for f in $(DIRS) ; do cd $$f; make ; cd ..; done + for f in $(DIRS) ; do cd $$f; $(MAKE) || exit 1; cd ..; done clean : - for f in $(DIRS) ; do cd $$f; make clean; cd ..; done + for f in $(DIRS) ; do cd $$f; $(MAKE) clean; cd ..; done clobber : - for f in $(DIRS) ; do cd $$f; make clobber; cd ..; done + for f in $(DIRS) ; do cd $$f; $(MAKE) clobber; cd ..; done depend : - for f in $(DIRS) ; do cd $$f; make depend; cd ..; done + for f in $(DIRS) ; do cd $$f; $(MAKE) depend; cd ..; done docs : - (cd osg; make docs;) - (cd osgUtil; make docs; ) - (cd osgGLUT; make docs; ) + (cd osg; $(MAKE) docs;) + (cd osgUtil; $(MAKE) docs; ) + (cd osgDB; $(MAKE) docs; ) + (cd osgGLUT; $(MAKE) docs; ) to_unix : for f in $(DIRS) ; do cd $$f; to_unix Makefile Makefile; cd ..; done - for f in $(DIRS) ; do cd $$f; make to_unix; cd ..; done + for f in $(DIRS) ; do cd $$f; $(MAKE) to_unix; cd ..; done +beautify : + for f in $(DIRS) ; do cd $$f; $(MAKE) beautify; cd ..; done install : - for f in $(DIRS) ; do cd $$f; make install; cd ..; done + for f in $(DIRS) ; do cd $$f; $(MAKE) install; cd ..; done instlinks : - for f in $(DIRS) ; do cd $$f; make instlinks; cd ..; done + for f in $(DIRS) ; do cd $$f; $(MAKE) instlinks; cd ..; done instclean : - for f in $(DIRS) ; do cd $$f; make instclean; cd ..; done + for f in $(DIRS) ; do cd $$f; $(MAKE) instclean; cd ..; done diff --git a/src/osg/AlphaFunc.cpp b/src/osg/AlphaFunc.cpp index 98e93deb6..7c74e7b9f 100644 --- a/src/osg/AlphaFunc.cpp +++ b/src/osg/AlphaFunc.cpp @@ -1,8 +1,4 @@ -#include "osg/GL" #include "osg/AlphaFunc" -#include "osg/Output" -#include "osg/Input" - using namespace osg; @@ -12,90 +8,13 @@ AlphaFunc::AlphaFunc() _referenceValue = 1.0f; } + AlphaFunc::~AlphaFunc() { } -AlphaFunc* AlphaFunc::instance() -{ - static ref_ptr s_AlphaFunc(new AlphaFunc); - return s_AlphaFunc.get(); -} - -void AlphaFunc::enable() -{ - glEnable(GL_ALPHA_TEST); -} - -void AlphaFunc::disable() -{ - glDisable(GL_ALPHA_TEST); -} - -void AlphaFunc::apply() +void AlphaFunc::apply(State&) const { glAlphaFunc((GLenum)_comparisonFunc,_referenceValue); } - -bool AlphaFunc::readLocalData(Input& fr) -{ - bool iteratorAdvanced = false; - - ComparisonFunction func; - if (fr[0].matchWord("comparisonFunc") && matchFuncStr(fr[1].getStr(),func)) - { - _comparisonFunc = func; - fr+=2; - iteratorAdvanced = true; - } - - float ref; - if (fr[0].matchWord("referenceValue") && fr[1].getFloat(ref)) - { - _referenceValue = ref; - fr+=2; - iteratorAdvanced = true; - } - - return iteratorAdvanced; -} - - -bool AlphaFunc::writeLocalData(Output& fw) -{ - fw.indent() << "comparisonFunc " << getFuncStr(_comparisonFunc) << endl; - fw.indent() << "referenceValue " << _referenceValue << endl; - return true; -} - -bool AlphaFunc::matchFuncStr(const char* str,ComparisonFunction& func) -{ - if (strcmp(str,"NEVER")==0) func = NEVER; - else if (strcmp(str,"LESS")==0) func = LESS; - else if (strcmp(str,"EQUAL")==0) func = EQUAL; - else if (strcmp(str,"LEQUAL")==0) func = LEQUAL; - else if (strcmp(str,"GREATER")==0) func = GREATER; - else if (strcmp(str,"NOTEQUAL")==0) func = NOTEQUAL; - else if (strcmp(str,"GEQUAL")==0) func = GEQUAL; - else if (strcmp(str,"ALWAYS")==0) func = ALWAYS; - else return false; - return true; -} - - -const char* AlphaFunc::getFuncStr(ComparisonFunction func) -{ - switch(func) - { - case(NEVER): return "NEVER"; - case(LESS): return "LESS"; - case(EQUAL): return "EQUAL"; - case(LEQUAL): return "LEQUAL"; - case(GREATER): return "GREATER"; - case(NOTEQUAL): return "NOTEQUAL"; - case(GEQUAL): return "GEQUAL"; - case(ALWAYS): return "ALWAYS"; - } - return ""; -} diff --git a/src/osg/Billboard.cpp b/src/osg/Billboard.cpp index fc8ce9061..160095fd3 100644 --- a/src/osg/Billboard.cpp +++ b/src/osg/Billboard.cpp @@ -1,20 +1,15 @@ #include #include #include "osg/Billboard" -#include "osg/Input" -#include "osg/Output" -#include "osg/Registry" using namespace osg; -RegisterObjectProxy g_BillboardProxy; - #define square(x) ((x)*(x)) Billboard::Billboard() { _mode = AXIAL_ROT; -// _mode = POINT_ROT_WORLD; + // _mode = POINT_ROT_WORLD; _axis.set(0.0f,0.0f,1.0f); } @@ -23,12 +18,13 @@ Billboard::~Billboard() { } -bool Billboard::addGeoSet(GeoSet *gset) + +const bool Billboard::addDrawable(Drawable *gset) { - if (Geode::addGeoSet(gset)) + if (Geode::addDrawable(gset)) { Vec3 pos(0.0f,0.0f,0.0f); - while (_positionList.size()<_geosets.size()) + while (_positionList.size()<_drawables.size()) { _positionList.push_back(pos); } @@ -37,11 +33,12 @@ bool Billboard::addGeoSet(GeoSet *gset) return false; } -bool Billboard::addGeoSet(GeoSet *gset,const Vec3& pos) + +const bool Billboard::addDrawable(Drawable *gset,const Vec3& pos) { - if (Geode::addGeoSet(gset)) + if (Geode::addDrawable(gset)) { - while (_positionList.size()<_geosets.size()) + while (_positionList.size()<_drawables.size()) { _positionList.push_back(pos); } @@ -50,36 +47,41 @@ bool Billboard::addGeoSet(GeoSet *gset,const Vec3& pos) return false; } -bool Billboard::removeGeoSet( GeoSet *gset ) + +const bool Billboard::removeDrawable( Drawable *gset ) { PositionList::iterator pitr = _positionList.begin(); - for (GeoSetList::iterator itr=_geosets.begin(); - itr!=_geosets.end(); - ++itr,++pitr) + for (DrawableList::iterator itr=_drawables.begin(); + itr!=_drawables.end(); + ++itr,++pitr) { if (itr->get()==gset) { // note ref_ptr<> automatically handles decrementing gset's reference count. - _geosets.erase(itr); + _drawables.erase(itr); _positionList.erase(pitr); _bsphere_computed = false; return true; } } - return false; + return false; } -void Billboard::calcRotation(const Vec3& eye_local, const Vec3& pos_local,Matrix& mat) +void Billboard::calcRotation(const Vec3& eye_local, const Vec3& pos_local,Matrix& mat) const { switch(_mode) { case(AXIAL_ROT): { + // note currently assumes that axis is (0,0,1) for speed of + // executation and implementation. This will be rewritten + // on second pass of Billboard. Robert Osfield Jan 2001. Vec3 ev = pos_local-eye_local; ev.z() = 0.0f; float ev_length = ev.length(); - if (ev_length>0.0f) { + if (ev_length>0.0f) + { //float rotation_zrotation_z = atan2f(ev.x(),ev.y()); //mat.makeRot(rotation_z*180.0f/M_PI,0.0f,0.0f,1.0f); float inv = 1.0f/ev_length; @@ -92,9 +94,16 @@ void Billboard::calcRotation(const Vec3& eye_local, const Vec3& pos_local,Matrix } break; } - case(POINT_ROT_WORLD): + case(POINT_ROT_WORLD): case(POINT_ROT_EYE): { + // currently treat both POINT_ROT_WORLD and POINT_ROT_EYE the same, + // this is only a temporary and 'incorrect' implementation, will + // implement fully on second pass of Billboard. + // Will also need up vector to calc POINT_ROT_EYE, so this will + // have to be added to the above method paramters. + // Robert Osfield, Jan 2001. + Vec3 ev = pos_local-eye_local; ev.normalize(); @@ -120,122 +129,24 @@ void Billboard::calcRotation(const Vec3& eye_local, const Vec3& pos_local,Matrix } } -void Billboard::calcTransform(const Vec3& eye_local, const Vec3& pos_local,Matrix& mat) + +void Billboard::calcTransform(const Vec3& eye_local, const Vec3& pos_local,Matrix& mat) const { -// mat.makeTrans(pos_local[0],pos_local[1],pos_local[2]); -// mat.makeIdent(); + // mat.makeTrans(pos_local[0],pos_local[1],pos_local[2]); + // mat.makeIdent(); calcRotation(eye_local,pos_local,mat); -// mat.postTrans(pos_local[0],pos_local[1],pos_local[2]); + // mat.postTrans(pos_local[0],pos_local[1],pos_local[2]); mat._mat[3][0] += pos_local[0]; mat._mat[3][1] += pos_local[1]; mat._mat[3][2] += pos_local[2]; } -bool Billboard::readLocalData(Input& fr) -{ - // note, free done by Node::read(Input& fr) - - bool iteratorAdvanced = false; - - if (fr[0].matchWord("Mode")) - { - if (fr[1].matchWord("AXIAL_ROT")) - { - _mode = AXIAL_ROT; - fr+=2; - iteratorAdvanced = true; - } - else if (fr[1].matchWord("POINT_ROT_EYE")) - { - _mode = POINT_ROT_EYE; - fr+=2; - iteratorAdvanced = true; - } - else if (fr[1].matchWord("POINT_ROT_WORLD")) - { - _mode = POINT_ROT_WORLD; - fr+=2; - iteratorAdvanced = true; - } - } - - // read the position data. - bool matchFirst = false; - if ((matchFirst=fr.matchSequence("Positions {")) || fr.matchSequence("Positions %i {")) - { - - // set up coordinates. - int entry = fr[0].getNoNestedBrackets(); - - if (matchFirst) - { - fr += 2; - } - else - { - //_positionList.(capacity); - fr += 3; - } - - Vec3 pos; - while (!fr.eof() && fr[0].getNoNestedBrackets()>entry) - { - if (fr[0].getFloat(pos[0]) && fr[1].getFloat(pos[1]) && fr[2].getFloat(pos[2])) - { - fr += 3; - _positionList.push_back(pos); - } - else - { - ++fr; - } - } - - iteratorAdvanced = true; - ++fr; - - } - - if (Geode::readLocalData(fr)) iteratorAdvanced = true; - - return iteratorAdvanced; -} - -bool Billboard::writeLocalData(Output& fw) -{ - - switch(_mode) - { - case(AXIAL_ROT): fw.indent() << "Mode AXIAL_ROT"<getBound(); _bsphere._center += bbox.center(); @@ -255,7 +166,7 @@ bool Billboard::computeBound( void ) float maxd = 0.0; for( i = 0; i < ngsets; ++i ) { - GeoSet *gset = _geosets[i].get(); + const Drawable *gset = _drawables[i].get(); const BoundingBox& bbox = gset->getBound(); Vec3 local_center = _bsphere._center-_positionList[i]; for(unsigned int c=0;c<8;++c) diff --git a/src/osg/BoundingBox.cpp b/src/osg/BoundingBox.cpp index ac3e60e1b..e817791d3 100644 --- a/src/osg/BoundingBox.cpp +++ b/src/osg/BoundingBox.cpp @@ -7,38 +7,40 @@ void BoundingBox::expandBy(const Vec3& v) { if(v.x()<_min.x()) _min.x() = v.x(); if(v.x()>_max.x()) _max.x() = v.x(); - + if(v.y()<_min.y()) _min.y() = v.y(); if(v.y()>_max.y()) _max.y() = v.y(); - + if(v.z()<_min.z()) _min.z() = v.z(); if(v.z()>_max.z()) _max.z() = v.z(); } + void BoundingBox::expandBy(const BoundingBox& bb) { if (!bb.isValid()) return; if(bb._min.x()<_min.x()) _min.x() = bb._min.x(); if(bb._max.x()>_max.x()) _max.x() = bb._max.x(); - + if(bb._min.y()<_min.y()) _min.y() = bb._min.y(); if(bb._max.y()>_max.y()) _max.y() = bb._max.y(); - + if(bb._min.z()<_min.z()) _min.z() = bb._min.z(); if(bb._max.z()>_max.z()) _max.z() = bb._max.z(); } + void BoundingBox::expandBy(const BoundingSphere& sh) { if (!sh.isValid()) return; if(sh._center.x()-sh._radius<_min.x()) _min.x() = sh._center.x()-sh._radius; if(sh._center.x()+sh._radius>_max.x()) _max.x() = sh._center.x()+sh._radius; - + if(sh._center.y()-sh._radius<_min.y()) _min.y() = sh._center.y()-sh._radius; if(sh._center.y()+sh._radius>_max.y()) _max.y() = sh._center.y()+sh._radius; - + if(sh._center.z()-sh._radius<_min.z()) _min.z() = sh._center.z()-sh._radius; if(sh._center.z()+sh._radius>_max.z()) _max.z() = sh._center.z()+sh._radius; } diff --git a/src/osg/BoundingSphere.cpp b/src/osg/BoundingSphere.cpp index 9aae7d804..4729e7ead 100644 --- a/src/osg/BoundingSphere.cpp +++ b/src/osg/BoundingSphere.cpp @@ -9,11 +9,11 @@ void BoundingSphere::expandBy(const Vec3& v) Vec3 dv = v-_center; float r = dv.length(); if (r>_radius) - { + { float dr = (r-_radius)*0.5f; _center += dv*(dr/r); _radius += dr; - } // else do nothing as vertex is within sphere. + } // else do nothing as vertex is within sphere. } else { @@ -22,6 +22,7 @@ void BoundingSphere::expandBy(const Vec3& v) } } + void BoundingSphere::expandRadiusBy(const Vec3& v) { if (isValid()) @@ -37,6 +38,7 @@ void BoundingSphere::expandRadiusBy(const Vec3& v) } } + void BoundingSphere::expandBy(const BoundingSphere& sh) { if (sh.isValid()) @@ -47,13 +49,13 @@ void BoundingSphere::expandBy(const BoundingSphere& sh) float dv_len = dv.length(); if (dv_len+sh._radius>_radius) { - + Vec3 e1 = _center-(dv*(_radius/dv_len)); Vec3 e2 = sh._center+(dv*(sh._radius/dv_len)); _center = (e1+e2)*0.5f; _radius = (e2-_center).length(); - - } // else do nothing as vertex is within sphere. + + } // else do nothing as vertex is within sphere. } else { @@ -62,6 +64,8 @@ void BoundingSphere::expandBy(const BoundingSphere& sh) } } } + + void BoundingSphere::expandRadiusBy(const BoundingSphere& sh) { if (sh.isValid()) diff --git a/src/osg/Camera.cpp b/src/osg/Camera.cpp index 8663493c3..e78081fb5 100644 --- a/src/osg/Camera.cpp +++ b/src/osg/Camera.cpp @@ -1,85 +1,705 @@ -#include "osg/GL" +#include #include +#include +#include using namespace osg; +#define DEG2RAD(x) ((x)*M_PI/180.0) +#define RAD2DEG(x) ((x)*180.0/M_PI) + Camera::Camera() { - _fovy = 60.0; - _aspectRatio = 1.0; - home(); + + // projection details. + setPerspective(60,1.0,1.0,1000.0); + + // look at details. + _lookAtType =USE_HOME_POSITON; + + _eye.set(0.0f,0.0f,0.0f); + _center.set(0.0f,0.0f,-1.0f); + _up.set(0.0f,1.0f,0.0f); + + _focalLength = 1.0f; + + _useNearClippingPlane = false; + _useFarClippingPlane = false; + } + Camera::~Camera() { } + + +/** Set a orthographics projection. See glOrtho for further details.*/ +void Camera::setOrtho(const double left, const double right, + const double bottom, const double top, + const double zNear, const double zFar) +{ + _projectionType = ORTHO; + _left = left; + _right = right; + _bottom = bottom; + _top = top; + _zNear = zNear; + _zFar = zFar; + + _dirty = true; +} + + +/** Set a 2D orthographics projection. See gluOrtho2D for further details.*/ +void Camera::setOrtho2D(const double left, const double right, + const double bottom, const double top) +{ + _projectionType = ORTHO2D; + _left = left; + _right = right; + _bottom = bottom; + _top = top; + _zNear = -1.0; + _zFar = 1.0; + + _dirty = true; +} + + +/** Set a perspective projection. See glFrustum for further details.*/ +void Camera::setFrustum(const double left, const double right, + const double bottom, const double top, + const double zNear, const double zFar) +{ + _projectionType = FRUSTUM; + // note, in Frustum/Perspective mode these values are scaled + // by the zNear from when they were initialised to ensure that + // subsequent changes in zNear do not affect them. + _left = left/zNear; + _right = right/zNear; + _bottom = bottom/zNear; + _top = top/zNear; + _zNear = zNear; + _zFar = zFar; + + _dirty = true; +} + + + +/** Set a sysmetical perspective projection, See gluPerspective for further details.*/ +void Camera::setPerspective(const double fovy,const double aspectRatio, + const double zNear, const double zFar) +{ + _projectionType = PERSPECTIVE; + + // note, in Frustum/Perspective mode these values are scaled + // by the zNear from when they were initialised to ensure that + // subsequent changes in zNear do not affect them. + + // calculate the appropriate left, right etc. + double tan_fovy = tan(DEG2RAD(fovy*0.5)); + _right = tan_fovy * aspectRatio; + _left = -_right; + _top = tan_fovy; + _bottom = -_top; + + _zNear = zNear; + _zFar = zFar; + + notify(INFO)<<"osg::Camera::setPerspective(fovy="<invert(*_eyeToModelTransform); + } + else + { + _attachedTransformMode = NO_ATTACHED_TRANSFORM; + _modelToEyeTransform = NULL; + } + } + break; + case(MODEL_TO_EYE): + { + _modelToEyeTransform = matrix; + if (_modelToEyeTransform.valid()) + { + _attachedTransformMode = mode; + if (!_eyeToModelTransform.valid()) _eyeToModelTransform = new Matrix; + _eyeToModelTransform->invert(*_modelToEyeTransform); + } + else + { + _attachedTransformMode = NO_ATTACHED_TRANSFORM; + _eyeToModelTransform = NULL; + } + } + break; + case(NO_ATTACHED_TRANSFORM): + _attachedTransformMode = NO_ATTACHED_TRANSFORM; + _eyeToModelTransform = NULL; + _modelToEyeTransform = NULL; + break; + default: + _attachedTransformMode = NO_ATTACHED_TRANSFORM; + notify(WARN)<<"Warning: invalid TransformMode pass to osg::Camera::attachTransform(..)"<invert(*_eyeToModelTransform); + break; + case(MODEL_TO_EYE): + // should be safe to assume that these matrices are valid + // as attachTransform will ensure it. + _eyeToModelTransform->invert(*_modelToEyeTransform); + break; + } + +} + +Matrix* Camera::getTransform(const TransformMode mode) +{ + switch(mode) + { + case(EYE_TO_MODEL): return _eyeToModelTransform.get(); + case(MODEL_TO_EYE): return _modelToEyeTransform.get(); + default: return NULL; + } +} + +const Matrix* Camera::getTransform(const TransformMode mode) const +{ + switch(mode) + { + case(EYE_TO_MODEL): return _eyeToModelTransform.get(); + case(MODEL_TO_EYE): return _modelToEyeTransform.get(); + default: return NULL; + } +} + + +const Vec3 Camera::getEyePoint_Model() const +{ + if (_eyeToModelTransform.valid()) return _eye*(*_eyeToModelTransform); + else return _eye; +} + +const Vec3 Camera::getCenterPoint_Model() const +{ + if (_eyeToModelTransform.valid()) return _center*(*_eyeToModelTransform); + else return _center; +} + + +const Vec3 Camera::getLookVector_Model() const +{ + if (_eyeToModelTransform.valid()) + { + Vec3 zero_transformed = Vec3(0.0f,0.0f,0.0f)*(*_eyeToModelTransform); + Vec3 look_transformed = getLookVector()*(*_eyeToModelTransform); + look_transformed -= zero_transformed; + look_transformed.normalize(); + return look_transformed; + } + else return getLookVector(); +} + +const Vec3 Camera::getUpVector_Model() const +{ + if (_eyeToModelTransform.valid()) + { + Vec3 zero_transformed = Vec3(0.0f,0.0f,0.0f)*(*_eyeToModelTransform); + Vec3 up_transformed = getUpVector()*(*_eyeToModelTransform); + up_transformed -= zero_transformed; + up_transformed.normalize(); + return up_transformed; + } + else return getUpVector(); +} + +const Vec3 Camera::getSideVector_Model() const +{ + if (_eyeToModelTransform.valid()) + { + Vec3 zero_transformed = Vec3(0.0f,0.0f,0.0f)*(*_eyeToModelTransform); + Vec3 side_transformed = getSideVector()*(*_eyeToModelTransform); + side_transformed -= zero_transformed; + side_transformed.normalize(); + return side_transformed; + } + else return getSideVector(); +} + +const Matrix& Camera::getModelViewMatrix() const +{ + if (_dirty) calculateMatricesAndClippingVolume(); + return *_modelViewMatrix; +} + +void Camera::setUseNearClippingPlane(const bool use) +{ + if (_useNearClippingPlane != use) + { + _useNearClippingPlane = use; + _dirty = true; + } +} + +void Camera::setUseFarClippingPlane(const bool use) +{ + if (_useFarClippingPlane != use) + { + _useFarClippingPlane = use; + _dirty = true; + } +} + +const ClippingVolume& Camera::getClippingVolume() const +{ + if (_dirty) calculateMatricesAndClippingVolume(); + return _clippingVolume; +} + +void Camera::calculateMatricesAndClippingVolume() const +{ + + // set up the projection matrix. + switch(_projectionType) + { + case(ORTHO): + case(ORTHO2D): + { + float A = 2.0/(_right-_left); + float B = 2.0/(_top-_bottom); + float C = -2.0 / (_zFar-_zNear); + float tx = -(_right+_left)/(_right-_left); + float ty = -(_top+_bottom)/(_top-_bottom); + float tz = -(_zFar+_zNear)/(_zFar-_zNear); + + _projectionMatrix = new Matrix( + A, 0.0f, 0.0f, 0.0f, + 0.0f, B, 0.0f, 0.0f, + 0.0f, 0.0f, C, 0.0f, + tx, ty, tz, 1.0f ); + } + break; + case(FRUSTUM): + case(PERSPECTIVE): + { + + // note, in Frustum/Perspective mode these values are scaled + // by the zNear from when they were initialised to ensure that + // subsequent changes in zNear do not affect them. + + float A = (2.0)/(_right-_left); + float B = (2.0)/(_top-_bottom); + float C = (_right+_left) / (_right-_left); + float D = (_top+_bottom) / (_top-_bottom); + float E = -(_zFar+_zNear) / (_zFar-_zNear); + float F = -(2.0*_zFar*_zNear) / (_zFar-_zNear); + + _projectionMatrix = new Matrix( + A, 0.0f, 0.0f, 0.0f, + 0.0f, B, 0.0f, 0.0f, + C, D, E, -1.0f, + 0.0f, 0.0f, F, 0.0f ); + + } + break; + + } + + + // set up the model view matrix. + switch(_lookAtType) + { + case(USE_HOME_POSITON): + if (_modelToEyeTransform.valid()) + { + _modelViewMatrix = _modelToEyeTransform; + } + else + { + _modelViewMatrix = new Matrix; + _modelViewMatrix->makeIdent(); + } + break; + case(USE_EYE_AND_QUATERNION): // not implemented yet, default to eye,center,up. + case(USE_EYE_CENTER_AND_UP): + default: + { + + Vec3 f(_center-_eye); + f.normalize(); + Vec3 s(f^_up); + s.normalize(); + Vec3 u(s^f); + u.normalize(); + + ref_ptr matrix = new Matrix( + s[0], u[0], -f[0], 0.0f, + s[1], u[1], -f[1], 0.0f, + s[2], u[2], -f[2], 0.0f, + 0.0f, 0.0f, 0.0f, 1.0f); + + matrix->preTrans(-_eye[0], -_eye[1], -_eye[2]); + + if (_modelToEyeTransform.valid()) + { + _modelViewMatrix = new Matrix; + _modelViewMatrix->mult(*matrix,*_modelToEyeTransform); + } + else + { + _modelViewMatrix = matrix; + } + + } + break; + } + + _clippingVolume.clear(); + + // set the clipping volume. + switch(_projectionType) + { + case(ORTHO): + case(ORTHO2D): + { + } + break; + case(FRUSTUM): + case(PERSPECTIVE): + { + // calculate the frustum normals, postive pointing inwards. + // left clipping plane + // note, _left,_right,_top and _bottom are already devided + // by _zNear so no need to take into account for normal + // calculations. + Vec3 leftNormal (1.0f,0.0f,_left); + leftNormal.normalize(); + _clippingVolume.add(Plane(leftNormal,0.0f)); + + + Vec3 rightNormal (-1.0f,0.0f,-_right); + rightNormal.normalize(); + _clippingVolume.add(Plane(rightNormal,0.0f)); + + Vec3 bottomNormal(0.0f,1.0f,_bottom); + bottomNormal.normalize(); + _clippingVolume.add(Plane(bottomNormal,0.0f)); + + Vec3 topNormal(0.0f,-1.0f,-_top); + topNormal.normalize(); + _clippingVolume.add(Plane(topNormal,0.0f)); + + if (_useNearClippingPlane) + { + _clippingVolume.add(Plane(0.0f,0.0f,-1.0f,-_zNear)); + } + + if (_useFarClippingPlane) + { + _clippingVolume.add(Plane(0.0f,0.0f,1.0f,_zFar)); + } + + } + break; + + } + + _clippingVolume.transformProvidingInverse(*_modelViewMatrix); + + if (!_MP.valid()) _MP = new Matrix; + _MP->mult(*_modelViewMatrix,*_projectionMatrix); + + if (!_inverseMP.valid()) _inverseMP = new Matrix; + _inverseMP->invert(*_MP); + + _dirty = false; } void Camera::ensureOrthogonalUpVector() { - Vec3 lv = _lookPoint-_eyePoint; - Vec3 sv = lv^_upVector; - _upVector = sv^lv; - _upVector.normalize(); + Vec3 lv = _center-_eye; + Vec3 sv = lv^_up; + _up = sv^lv; + _up.normalize(); } -void Camera::mult(const Camera& camera,const Matrix& m) +const bool Camera::project(const Vec3& obj,const int* view,Vec3& win) const { - // transform camera. - _upVector = (camera._lookPoint+camera._upVector)*m; - _eyePoint = camera._eyePoint*m; - _lookPoint = camera._lookPoint*m; - _upVector -= _lookPoint; - - // now reset up vector so it remains at 90 degrees to look vector, - // as it may drift during transformation. - ensureOrthogonalUpVector(); + if (_MP.valid()) + { + Vec3 v = obj * (*_MP); + + win.set( + view[0] + view[2]*(v[0]+1.0f)*0.5f, + view[1] + view[3]*(v[1]+1.0f)*0.5f, + (v[2]+1.0f)*0.5f + ); + + return true; + } + else + return false; } -void Camera::mult(const Matrix& m,const Camera& camera) +const bool Camera::unproject(const Vec3& win,const int* view,Vec3& obj) const { - // transform camera. - _upVector = m*(camera._lookPoint+camera._upVector); - _eyePoint = m*camera._eyePoint; - _lookPoint = m*camera._lookPoint; - _upVector -= _lookPoint; - - // now reset up vector so it remains at 90 degrees to look vector, - // as it may drift during transformation. - ensureOrthogonalUpVector(); + if (_inverseMP.valid()) + { + Vec3 v( + 2.0f*(win[0]-view[0])/view[2] - 1.0f, + 2.0f*(win[1]-view[1])/view[3] - 1.0f, + 2.0f*(win[2]) - 1.0f + ); + + obj = v * (*_inverseMP); + + return true; + } + else + return false; } - diff --git a/src/osg/CullFace.cpp b/src/osg/CullFace.cpp index 2a8747374..6b05e61d5 100644 --- a/src/osg/CullFace.cpp +++ b/src/osg/CullFace.cpp @@ -1,8 +1,5 @@ #include "osg/GL" #include "osg/CullFace" -#include "osg/Output" -#include "osg/Input" - using namespace osg; @@ -11,70 +8,12 @@ CullFace::CullFace() _mode = BACK; } + CullFace::~CullFace() { } -CullFace* CullFace::instance() -{ - static ref_ptr s_CullFace(new CullFace); - return s_CullFace.get(); -} - -void CullFace::enable( void ) -{ - glEnable( GL_CULL_FACE ); -} - - -void CullFace::disable( void ) -{ - glDisable( GL_CULL_FACE ); -} - -void CullFace::apply() +void CullFace::apply(State&) const { glCullFace((GLenum)_mode); } - - -bool CullFace::readLocalData(Input& fr) -{ - bool iteratorAdvanced = false; - - if (fr[0].matchWord("mode")) - { - if (fr[1].matchWord("FRONT")) - { - _mode = FRONT; - fr+=2; - iteratorAdvanced = true; - } - else if (fr[1].matchWord("BACK")) - { - _mode = BACK; - fr+=2; - iteratorAdvanced = true; - } - else if (fr[1].matchWord("FRONT_AND_BACK")) - { - _mode = FRONT_AND_BACK; - fr+=2; - iteratorAdvanced = true; - } - } - - return iteratorAdvanced; -} - - -bool CullFace::writeLocalData(Output& fw) -{ - switch(_mode) - { - case(FRONT): fw.indent() << "mode FRONT" << endl; break; - case(BACK): fw.indent() << "mode BACK" << endl; break; - case(FRONT_AND_BACK): fw.indent() << "mode FRONT_AND_BACK" << endl; break; - } - return true; -} diff --git a/src/osg/Fog.cpp b/src/osg/Fog.cpp index 4a9dc816c..44b2a485c 100644 --- a/src/osg/Fog.cpp +++ b/src/osg/Fog.cpp @@ -1,9 +1,8 @@ -#include "osg/GL" #include "osg/Fog" using namespace osg; -Fog::Fog( void ) +Fog::Fog() { _mode = EXP; _density = 1.0f; @@ -13,31 +12,11 @@ Fog::Fog( void ) } -Fog::~Fog( void ) +Fog::~Fog() { } - -Fog* Fog::instance() -{ - static ref_ptr s_fog(new Fog); - return s_fog.get(); -} - - -void Fog::enable( void ) -{ - glEnable( GL_FOG ); -} - - -void Fog::disable( void ) -{ - glDisable( GL_FOG ); -} - - -void Fog::apply( void ) +void Fog::apply(State&) const { glFogi( GL_FOG_MODE, _mode ); glFogf( GL_FOG_DENSITY, _density ); diff --git a/src/osg/GeoSet.cpp b/src/osg/GeoSet.cpp index b6149c1fc..669e9ade6 100644 --- a/src/osg/GeoSet.cpp +++ b/src/osg/GeoSet.cpp @@ -1,44 +1,39 @@ +#if defined(_MSC_VER) + #pragma warning( disable : 4786 ) +#endif + #include #include #include #include "osg/GeoSet" -#include "osg/Input" -#include "osg/Output" #include "osg/Notify" +//#include "osg/mem_ptr" + using namespace osg; GeoSet::GeoSet() { - _coords = (Vec3 *)0; - _cindex = (ushort *)0; + _coords = (Vec3 *)0; _normals = (Vec3 *)0; - _nindex = (ushort *)0; _colors = (Vec4 *)0; - _colindex = (ushort *)0; _tcoords = (Vec2 *)0; - _tindex = (ushort *)0; _iarray = (float *)0L; - _iaindex = (ushort *)0; _iaformat = IA_OFF; _ogliaformat = 0; - _bbox_computed = 0; _numprims = 0; _primtype = NO_TYPE; _oglprimtype = 0xFFFF; - _needprimlen = 0; + _needprimlen = 0; _primLengths = (int *)0; - _useDisplayList = true; - _globj = 0; - _numcoords = 0; _normal_binding = BIND_OFF; @@ -46,15 +41,17 @@ GeoSet::GeoSet() _texture_binding = BIND_OFF; _fast_path = 1; + + // cout << endl << "Above allocated"<* ma = newMemoryAdapter::instance(); + // mem_ptr coords(ma->allocate(100),ma); + // cout << "Registered"< s_geoset(new GeoSet); - return s_geoset.get(); -} -bool GeoSet::readLocalData(Input& fr) -{ - bool iteratorAdvanced = false; - - if (fr[0].matchWord("Use")) - { - if (fr[1].isString()) { - GeoState* geostate = dynamic_cast(fr.getObjectForUniqueID(fr[1].getStr())); - if (geostate) { - fr+=2; - setGeoState(geostate); - iteratorAdvanced = true; - } - } - } - - if (GeoState* readState = static_cast(GeoState::instance()->readClone(fr))) - { - setGeoState(readState); - iteratorAdvanced = true; - } - - Vec3* coordList = NULL; - ushort* coordIndexList = NULL; - Vec3* normalList = NULL; - ushort* normalIndexList = NULL; - Vec4* colorList = NULL; - ushort* colorIndexList = NULL; - Vec2* textureList = NULL; - ushort* textureIndexList = NULL; - float* interleavedArray = NULL; - ushort* interleavedIndexArray = NULL; - - BindingType bind=BIND_OFF; - BindingType normal_bind=BIND_OFF; - BindingType color_bind=BIND_OFF; - BindingType texture_bind=BIND_OFF; - InterleaveArrayType iaType = IA_OFF; - - int start_indent = fr[0].getNoNestedBrackets(); - while (!fr.eof() && fr[0].getNoNestedBrackets()>=start_indent) - { - - bool fieldAdvanced = false; - - bool readPrimitiveLengths = false; - if (fr.matchSequence("tstrips %i {")) - { - readPrimitiveLengths = true; - setPrimType(TRIANGLE_STRIP); - } - else if (fr.matchSequence("flat_tstrips %i {")) - { - readPrimitiveLengths = true; - setPrimType(FLAT_TRIANGLE_STRIP); - } - else if (fr.matchSequence("polys %i {")) - { - readPrimitiveLengths = true; - setPrimType(POLYGON); - } - else if (fr.matchSequence("quadstrip %i {")) - { - readPrimitiveLengths = true; - setPrimType(QUAD_STRIP); - } - else if (fr.matchSequence("lineloops %i {")) - { - readPrimitiveLengths = true; - setPrimType(LINE_LOOP); - } - else if (fr.matchSequence("linestrip %i {")) - { - readPrimitiveLengths = true; - setPrimType(LINE_STRIP); - } - else if (fr.matchSequence("flat_linestrip %i {")) - { - readPrimitiveLengths = true; - setPrimType(LINE_STRIP); - } - else if (fr.matchSequence("tfans %i {")) - { - readPrimitiveLengths = true; - setPrimType(TRIANGLE_FAN); - } - else if (fr.matchSequence("flat_tfans %i {")) - { - readPrimitiveLengths = true; - setPrimType(FLAT_TRIANGLE_FAN); - } - - if (readPrimitiveLengths) - { - - int entry = fr[1].getNoNestedBrackets(); - fr += 3; - - int capacity; - if (!fr[1].getInt(capacity)) capacity=100; - int size = 0; - int* list = new int [capacity]; - - while (!fr.eof() && fr[0].getNoNestedBrackets()>entry) - { - int primLength; - if (fr[0].getInt(primLength)) - { - - if (size>=capacity) - { - int oldCapacity = capacity; - while(capacity<=size) capacity *= 2; - int* oldList = list; - list = new int[capacity]; - for(int i=0;ientry) - { - float x,y,z; - if (fr[0].getFloat(x) && fr[1].getFloat(y) && fr[2].getFloat(z)) - { - fr += 3; - - if (size>=capacity) - { - int oldCapacity = capacity; - while(capacity<=size) capacity *= 2; - Vec3* oldList = coordList; - coordList = new Vec3[capacity]; - for(int i=0;ientry) - { - int index; - if (fr[0].getInt(index)) - { - - if (size>=capacity) - { - int oldCapacity = capacity; - while(capacity<=size) capacity *= 2; - ushort* oldList = coordIndexList; - coordIndexList = new ushort[capacity]; - for(int i=0;ientry) - { - float x,y,z; - if (fr[0].getFloat(x) && fr[1].getFloat(y) && fr[2].getFloat(z)) - { - fr += 3; - - if (size>=capacity) - { - int oldCapacity = capacity; - while(capacity<=size) capacity *= 2; - Vec3* oldList = normalList; - normalList = new Vec3[capacity]; - for(int i=0;ientry) - { - int index; - if (fr[0].getInt(index)) - { - - if (size>=capacity) - { - int oldCapacity = capacity; - while(capacity<=size) capacity *= 2; - ushort* oldList = normalIndexList; - normalIndexList = new ushort[capacity]; - for(int i=0;ientry) - { - float r,g,b,a; - if (fr[0].getFloat(r) && fr[1].getFloat(g) && fr[2].getFloat(b) && fr[3].getFloat(a)) - { - - fr += 4; - - if (size>=capacity) - { - int oldCapacity = capacity; - while(capacity<=size) capacity *= 2; - Vec4* oldList = colorList; - colorList = new Vec4[capacity]; - for(int i=0;ientry) - { - int index; - if (fr[0].getInt(index)) - { - - if (size>=capacity) - { - int oldCapacity = capacity; - while(capacity<=size) capacity *= 2; - ushort* oldList = colorIndexList; - colorIndexList = new ushort[capacity]; - for(int i=0;ientry) - { - float r,s; - if (fr[0].getFloat(r) && fr[1].getFloat(s)) - { - fr += 2; - if (size>=capacity) - { - int oldCapacity = capacity; - while(capacity<=size) capacity *= 2; - Vec2* oldList = textureList; - textureList = new Vec2[capacity]; - for(int i=0;ientry) - { - int index; - if (fr[0].getInt(index)) - { - - if (size>=capacity) - { - int oldCapacity = capacity; - while(capacity<=size) capacity *= 2; - ushort* oldList = textureIndexList; - textureIndexList = new ushort[capacity]; - for(int i=0;ientry) ++fr; - } - else - { - // now read the data rows between the {}. - const char* rowComp = getInterleavedRowComposition(iaType); - int rowLength = getInterleavedRowLength(iaType); - - int size = 0; - unsigned char* dataList = new unsigned char[capacity*rowLength]; - - unsigned char* rowData = new unsigned char [rowLength]; - - float floatData; - int intData; - while (!fr.eof() && fr[0].getNoNestedBrackets()>entry) - { - - unsigned char* itrRowData = rowData; - const char* itrRowComp = rowComp; - int rn = 0; - while (*itrRowComp!=0) - { - if (*itrRowComp=='f') - { - - if (!fr[rn].getFloat(floatData)) break; - *(float*)itrRowData = floatData; - itrRowData += 4; - } - else - { - if (!fr[rn].getInt(intData)) break; - *itrRowData = (unsigned char)intData; - itrRowData += 1; - } - ++rn; - } - if (*itrRowComp==0) - { - fr += rn; - if (size>=capacity) - { - int oldCapacity = capacity; - while(capacity<=size) capacity *= 2; - unsigned char* oldList = dataList; - dataList = new unsigned char[capacity*rowLength]; - memcpy(dataList,oldList,oldCapacity*rowLength); - delete [] oldList; - } - memcpy(dataList+size*rowLength,rowData,rowLength); - ++size; - - } - else - { - ++fr; - } - } - - interleavedArray = (float*)dataList; - } - - fieldAdvanced = true; - ++fr; - - } - - if ((matchFirst=fr.matchSequence("InterleavedArrayIndex {")) || fr.matchSequence("InterleavedArrayIndex %i {")) - { - - int entry = fr[0].getNoNestedBrackets(); - - int capacity = 100; - if (matchFirst) - { - fr += 2; - } - else - { - fr[1].getInt(capacity); - fr += 3; - } - - int size = 0; - - interleavedIndexArray = new ushort[capacity]; - - while (!fr.eof() && fr[0].getNoNestedBrackets()>entry) - { - int index; - if (fr[0].getInt(index)) - { - - if (size>=capacity) - { - int oldCapacity = capacity; - while(capacity<=size) capacity *= 2; - ushort* oldList = interleavedIndexArray; - interleavedIndexArray = new ushort[capacity]; - for(int i=0;istart_indent) fr.advanceToEndOfBlock(start_indent+1); - else ++fr; - } - iteratorAdvanced = true; - - - } - - -// set up the coord lists. - if (coordList) - { - if (coordIndexList) - { - setCoords(coordList,coordIndexList); - } - else - { - setCoords(coordList); - } - } - -// set up the normal lists. - if (normalList) - { - setNormalBinding(normal_bind); - if (normalIndexList) - { - setNormals(normalList,normalIndexList); - } - else - { - setNormals(normalList); - } - } else setNormalBinding(BIND_OFF); - -// set up the color lists. - if (colorList) - { - setColorBinding(color_bind); - if (colorIndexList) - { - setColors(colorList,colorIndexList); - } - else - { - setColors(colorList); - } - } else setColorBinding(BIND_OFF); - - if (textureList) - { - setTextureBinding(texture_bind); - if (textureIndexList) - { - setTextureCoords(textureList,textureIndexList); - } - else - { - setTextureCoords(textureList); - } - } else setTextureBinding(BIND_OFF); - - if (interleavedArray) - { - if (interleavedIndexArray) - { - setInterleavedArray(iaType,interleavedArray,interleavedIndexArray); - } - else - { - setInterleavedArray(iaType,interleavedArray); - } - } else _iaformat = IA_OFF; - - return iteratorAdvanced; -} - - -bool GeoSet::writeLocalData(Output& fw) -{ - int i; - - if (_state.valid()) - { - _state->write(fw); - } - - // write out primitives. - bool writeOutPrimitiveLengths = false; - switch(getPrimType()) - { - case (TRIANGLE_STRIP): - fw.indent()<<"tstrips "<< getNumPrims() << endl; - writeOutPrimitiveLengths = true; - break; - case (FLAT_TRIANGLE_STRIP): - fw.indent()<<"flat_tstrips "<< getNumPrims() << endl; - writeOutPrimitiveLengths = true; - break; - case (POLYGON): - fw.indent()<<"polys "<< getNumPrims() << endl; - writeOutPrimitiveLengths = true; - break; - case (QUAD_STRIP): - fw.indent()<<"quadstrip "<< getNumPrims() << endl; - writeOutPrimitiveLengths = true; - break; - case (LINE_LOOP): - fw.indent()<<"lineloops "<< getNumPrims() << endl; - writeOutPrimitiveLengths = true; - break; - case (LINE_STRIP): - fw.indent()<<"linestrip "<< getNumPrims() << endl; - writeOutPrimitiveLengths = false; - break; - case (FLAT_LINE_STRIP): - fw.indent()<<"flat_linestrip "<< getNumPrims() << endl; - writeOutPrimitiveLengths = false; - break; - case (TRIANGLE_FAN): - fw.indent()<<"tfans "<< getNumPrims() << endl; - writeOutPrimitiveLengths = true; - case (FLAT_TRIANGLE_FAN): - fw.indent()<<"flat_tfans "<< getNumPrims() << endl; - writeOutPrimitiveLengths = true; - break; - case (LINES): - fw.indent()<<"lines "<< getNumPrims() << endl; - writeOutPrimitiveLengths = false; - break; - case (TRIANGLES): - fw.indent()<<"triangles "<< getNumPrims() << endl; - writeOutPrimitiveLengths = false; - break; - case (QUADS): - fw.indent()<<"quads "<< getNumPrims() << endl; - writeOutPrimitiveLengths = false; - break; - case (POINTS) : - fw.indent()<<"points "<< getNumPrims() << endl; - break; - default: - notify(WARN) << "GeoSet::writeLocalData() - unhandled primitive type = "<<(int)getPrimType()<apply(); - - _globj = glGenLists( 1 ); - glNewList( _globj, GL_COMPILE ); - drawImmediateMode(); - glEndList(); - + draw_alternate_path(); } void GeoSet::computeNumVerts() @@ -1354,22 +142,22 @@ void GeoSet::computeNumVerts() switch( _primtype ) { case POINTS : - _primlength = 1; + _primlength = 1; numverts = _numprims * _primlength; break; case LINES : - _primlength = 2; + _primlength = 2; numverts = _numprims * _primlength; break; case TRIANGLES : - _primlength = 3; + _primlength = 3; numverts = _numprims * _primlength; break; case QUADS : - _primlength = 4; + _primlength = 4; numverts = _numprims * _primlength; break; @@ -1382,7 +170,7 @@ void GeoSet::computeNumVerts() case TRIANGLE_STRIP : case FLAT_TRIANGLE_STRIP : case POLYGON : - _primlength = 0; + _primlength = 0; numverts = 0; for( i = 0; i < _numprims; i++ ) numverts += _primLengths[i]; @@ -1392,61 +180,46 @@ void GeoSet::computeNumVerts() break; } - - if( _cindex != (ushort *)0L ) + if( _cindex._ptr._ushort) { - int max = 0; - - _numindices = numverts; - for( i = 0; i < _numindices; i++ ) - if( _cindex[i] > max ) max = _cindex[i]; - - _numcoords = max + 1; + _cindex._size = numverts; + _numcoords = _cindex.maxIndex() + 1; } else { + _cindex._size = 0; _numcoords = numverts; - _numcindices = 0; } - - - if (_normals) { int nn; switch(_normal_binding) { - case (BIND_OFF) : nn = 0; break; - case (BIND_OVERALL) : nn = 1; break; - case (BIND_PERPRIM) : nn = getNumPrims(); break; - case (BIND_PERVERTEX) : nn = numverts-flat_shaded_offset; break; - default : nn = 0; break; + case (BIND_OFF) : nn = 0; break; + case (BIND_OVERALL) : nn = 1; break; + case (BIND_PERPRIM) : nn = getNumPrims(); break; + case (BIND_PERVERTEX) : nn = numverts-flat_shaded_offset; break; + default : nn = 0; break; } - // calc the maximum num of vertex from the index list. - int cc; - if (_nindex) + // calc the maximum num of normals from the index list. + if( _nindex._ptr._ushort) { - _numnindices = nn; - cc = 0; - for( i = 0; i < nn; i++ ) - if( _nindex[i] > cc ) cc = _nindex[i]; - cc++; + _nindex._size = nn; + _numnormals = _nindex.maxIndex() + 1; } else { - cc = nn; - _numnindices = 0; + _nindex._size = 0; + _numnormals = nn; } - - _numnormals = cc; } else { + _nindex._size = 0; _numnormals = 0; - _numnindices = 0; } if (_colors) @@ -1455,94 +228,83 @@ void GeoSet::computeNumVerts() int nn; switch(_color_binding) { - case (BIND_OFF) : nn = 0; break; - case (BIND_OVERALL) : nn = 1; break; - case (BIND_PERPRIM) : nn = getNumPrims(); break; - case (BIND_PERVERTEX) : nn = numverts-flat_shaded_offset; break; - default : nn = 0; break; + case (BIND_OFF) : nn = 0; break; + case (BIND_OVERALL) : nn = 1; break; + case (BIND_PERPRIM) : nn = getNumPrims(); break; + case (BIND_PERVERTEX) : nn = numverts-flat_shaded_offset; break; + default : nn = 0; break; } - // calc the maximum num of vertex from the index list. - int cc; - if (_colindex) + // calc the maximum num of colors from the index list. + if( _colindex._ptr._ushort) { - _numcindices = nn; - cc = 0; - for( i = 0; i < nn; i++ ) - if( _colindex[i] > cc ) cc = _colindex[i]; - cc++; + _colindex._size = nn; + _numcolors = _colindex.maxIndex() + 1; } else { - cc = nn; - _numcindices = 0; + _colindex._size = 0; + _numcolors = nn; } - _numcolors = cc; } else { + _colindex._size = 0; _numcolors = 0; - _numcindices = 0; } - if (_tcoords) { int nn; switch(_texture_binding) { - case (BIND_OFF) : nn = 0; break; - case (BIND_OVERALL) : nn = 1; break; - case (BIND_PERPRIM) : nn = getNumPrims(); break; - case (BIND_PERVERTEX) : nn = numverts; break; - default : nn = 0; break; + case (BIND_OFF) : nn = 0; break; + case (BIND_OVERALL) : nn = 1; break; + case (BIND_PERPRIM) : nn = getNumPrims(); break; + case (BIND_PERVERTEX) : nn = numverts; break; + default : nn = 0; break; } // calc the maximum num of vertex from the index list. - int cc; - if (_tindex) + if( _tindex._ptr._ushort) { - _numtindices = nn; - cc = 0; - for( i = 0; i < nn; i++ ) - if( _tindex[i] > cc ) cc = _tindex[i]; - cc++; + _tindex._size = nn; + _numtcoords = _tindex.maxIndex() + 1; } else { - cc = nn; - _numtindices = 0; + _tindex._size = 0; + _numtcoords = nn; } - - _numtcoords = cc; } else { + _tindex._size = 0; _numtcoords = 0; - _numtindices = 0; } } -void GeoSet::computeBound( void ) +const bool GeoSet::computeBound() const { + if( _coords == (Vec3 *)0 ) return false; + + if( _numcoords == 0 ) + { + // a dirty hack to cast away constness of this.. + GeoSet* gset = const_cast(this); + gset->computeNumVerts(); + } + + if( _numcoords == 0 ) + return false; + + Vec3 center(0.0f,0.0f,0.0f); + int i; - - Vec3 center; - - if( _coords == (Vec3 *)0 ) return; - - if( _numcoords == 0 ) - computeNumVerts(); - - if( _numcoords == 0 ) - return; - - center.set(0.0f,0.0f,0.0f); - for( i = 0; i < _numcoords; i++ ) { center += _coords[i]; @@ -1557,34 +319,28 @@ void GeoSet::computeBound( void ) _bbox.expandBy(_coords[i]); } - _bbox_computed++; + _bbox_computed=true; + + return true; } -const BoundingBox& GeoSet::getBound() -{ - if( _bbox_computed == 0 ) - computeBound(); - - return _bbox; -} - -bool GeoSet::check() +const bool GeoSet::check() const { if( _coords == (Vec3 *)0 ) return false; - if( _cindex != (ushort *)0 || - _nindex != (ushort *)0 || - _colindex != (ushort *)0 || - _tindex != (ushort *)0 ) + if( _cindex.valid() || + _nindex.valid() || + _colindex.valid() || + _tindex.valid() ) { - if( (_coords && _cindex == (ushort *)0) || - (_normals && _nindex == (ushort *)0) || - (_colors && _colindex == (ushort *)0) || - (_tcoords && _tindex == (ushort *)0) ) + if( (_coords && _cindex.null()) || + (_normals && _nindex.null()) || + (_colors && _colindex.null()) || + (_tcoords && _tindex.null()) ) { - notify(WARN) << "GeoState::check() : " + notify(WARN) << "GeoSet::check() : " "Cannot mix indexed and non-indexed attributes.\n"; return false; } @@ -1592,28 +348,28 @@ bool GeoSet::check() return true; } -void GeoSet::setPrimType( PrimitiveType type ) + +void GeoSet::setPrimType( const PrimitiveType type ) { switch( type ) { - case NO_TYPE: break; + case NO_TYPE: break; - case POINTS: _oglprimtype = GL_POINTS; _needprimlen = 0; break; - case LINES: _oglprimtype = GL_LINES; _needprimlen = 0; break; - case FLAT_LINE_STRIP: _oglprimtype = GL_LINE_STRIP; _needprimlen=1; break; - case LINE_STRIP: _oglprimtype = GL_LINE_STRIP; _needprimlen=1; break; - case LINE_LOOP: _oglprimtype = GL_LINE_LOOP; _needprimlen=1; break; - case TRIANGLES: _oglprimtype = GL_TRIANGLES; _needprimlen=0; break; - case FLAT_TRIANGLE_STRIP: _oglprimtype = GL_TRIANGLE_STRIP; _needprimlen=1; break; - case TRIANGLE_STRIP: _oglprimtype = GL_TRIANGLE_STRIP; _needprimlen=1; break; - case TRIANGLE_FAN: _oglprimtype = GL_TRIANGLE_FAN; _needprimlen=1; break; - case FLAT_TRIANGLE_FAN: _oglprimtype = GL_TRIANGLE_FAN; _needprimlen=1; break; - case QUADS: _oglprimtype = GL_QUADS; _needprimlen=0; break; - case QUAD_STRIP: _oglprimtype = GL_QUAD_STRIP; _needprimlen=1; break; - case POLYGON : _oglprimtype = GL_POLYGON; _needprimlen=1; break; + case POINTS: _oglprimtype = GL_POINTS; _needprimlen = 0; break; + case LINES: _oglprimtype = GL_LINES; _needprimlen = 0; break; + case FLAT_LINE_STRIP: _oglprimtype = GL_LINE_STRIP; _needprimlen=1; break; + case LINE_STRIP: _oglprimtype = GL_LINE_STRIP; _needprimlen=1; break; + case LINE_LOOP: _oglprimtype = GL_LINE_LOOP; _needprimlen=1; break; + case TRIANGLES: _oglprimtype = GL_TRIANGLES; _needprimlen=0; break; + case FLAT_TRIANGLE_STRIP: _oglprimtype = GL_TRIANGLE_STRIP; _needprimlen=1; break; + case TRIANGLE_STRIP: _oglprimtype = GL_TRIANGLE_STRIP; _needprimlen=1; break; + case TRIANGLE_FAN: _oglprimtype = GL_TRIANGLE_FAN; _needprimlen=1; break; + case FLAT_TRIANGLE_FAN: _oglprimtype = GL_TRIANGLE_FAN; _needprimlen=1; break; + case QUADS: _oglprimtype = GL_QUADS; _needprimlen=0; break; + case QUAD_STRIP: _oglprimtype = GL_QUAD_STRIP; _needprimlen=1; break; + case POLYGON : _oglprimtype = GL_POLYGON; _needprimlen=1; break; } - _primtype = type; if( _primtype == FLAT_LINE_STRIP ) _flat_shaded_skip = 1; @@ -1623,33 +379,48 @@ void GeoSet::setPrimType( PrimitiveType type ) } -void GeoSet::setCoords( Vec3 *cp ) -{ - _coords = cp; - _cindex = 0L; - set_fast_path(); -} -void GeoSet::setCoords( Vec3 *cp, ushort *ci ) -{ - _coords = cp; - _cindex = ci; +void GeoSet::setCoords( Vec3 *cp ) +{ + _coords = cp; + _cindex.setToNull(); + _bbox_computed = false; set_fast_path(); } -void GeoSet::setNormals( Vec3 *np ) -{ - _normals = np; - _nindex = 0L; - if( _normal_binding == BIND_OFF ) - setNormalBinding( BIND_DEFAULT ); - else - set_fast_path(); + +void GeoSet::setCoords( Vec3 *cp, ushort *ci ) +{ + _coords = cp; + // note the size of cindex defaults 0, but will be recalculated + // automatically by computeNumVerts(). + _cindex.set(0,ci); + _bbox_computed = false; + set_fast_path(); } -void GeoSet::setNormals( Vec3 *np, ushort *ni ) -{ - _normals = np; - _nindex = ni; + +void GeoSet::setCoords( Vec3 *cp, uint *ci ) +{ + _coords = cp; + // note the size of cindex defaults 0, but will be recalculated + // automatically by computeNumVerts(). + _cindex.set(0,ci); + _bbox_computed = false; + set_fast_path(); +} + +void GeoSet::setCoords( Vec3 *cp, IndexPointer& ip ) +{ + _coords = cp; + _cindex = ip; + _bbox_computed = false; + set_fast_path(); +} + +void GeoSet::setNormals( Vec3 *np ) +{ + _normals = np; + _nindex.setToNull(); if( _normal_binding == BIND_OFF ) setNormalBinding( BIND_DEFAULT ); else @@ -1657,40 +428,106 @@ void GeoSet::setNormals( Vec3 *np, ushort *ni ) } -void GeoSet::setColors( Vec4 *lp ) -{ - _colors = lp; - _colindex = 0L; +void GeoSet::setNormals( Vec3 *np, ushort *ni ) +{ + _normals = np; + // note the size of nindex defaults 0, but will be recalculated + // automatically by computeNumVerts(). + _nindex.set(0,ni); + if( _normal_binding == BIND_OFF ) + setNormalBinding( BIND_DEFAULT ); + else + set_fast_path(); +} + +void GeoSet::setNormals( Vec3 *np, uint *ni ) +{ + _normals = np; + // note the size of nindex defaults 0, but will be recalculated + // automatically by computeNumVerts(). + _nindex.set(0,ni); + if( _normal_binding == BIND_OFF ) + setNormalBinding( BIND_DEFAULT ); + else + set_fast_path(); +} + +void GeoSet::setNormals( Vec3 *cp, IndexPointer& ip ) +{ + _normals = cp; + _nindex = ip; + _bbox_computed = false; + if( _normal_binding == BIND_OFF ) + setNormalBinding( BIND_DEFAULT ); + else + set_fast_path(); +} + + +void GeoSet::setColors( Vec4 *lp ) +{ + _colors = lp; + _colindex.setToNull(); if( _color_binding == BIND_OFF ) setColorBinding( BIND_DEFAULT ); else set_fast_path(); } -void GeoSet::setColors( Vec4 *lp, ushort *li ) -{ - _colors = lp; - _colindex = li; + +void GeoSet::setColors( Vec4 *lp, ushort *coli ) +{ + _colors = lp; + // note the size of colindex defaults 0, but will be recalculated + // automatically by computeNumVerts(). + _colindex.set(0,coli); if( _color_binding == BIND_OFF ) setColorBinding( BIND_DEFAULT ); else set_fast_path(); } -void GeoSet::setTextureCoords( Vec2 *tc ) -{ - _tcoords = tc; - _tindex = 0L; +void GeoSet::setColors( Vec4 *lp, uint *coli ) +{ + _colors = lp; + // note the size of colindex defaults 0, but will be recalculated + // automatically by computeNumVerts(). + _colindex.set(0,coli); + if( _color_binding == BIND_OFF ) + setColorBinding( BIND_DEFAULT ); + else + set_fast_path(); +} + +void GeoSet::setColors( Vec4 *cp, IndexPointer& ip ) +{ + _colors = cp; + _colindex = ip; + _bbox_computed = false; + if( _color_binding == BIND_OFF ) + setColorBinding( BIND_DEFAULT ); + else + set_fast_path(); +} + + +void GeoSet::setTextureCoords( Vec2 *tc ) +{ + _tcoords = tc; + _tindex.setToNull(); if( _texture_binding == BIND_OFF ) setTextureBinding( BIND_DEFAULT ); else set_fast_path(); } -void GeoSet::setTextureCoords( Vec2 *tc, ushort *ti ) -{ - _tcoords = tc; - _tindex = ti; + +void GeoSet::setTextureCoords( Vec2 *tc, ushort *ti ) +{ + _tcoords = tc; + // note the size of tindex defaults 0, but will be recalculated + // automatically by computeNumVerts(). + _tindex.set(0,ti); if( _texture_binding == BIND_OFF ) setTextureBinding( BIND_DEFAULT ); else @@ -1698,81 +535,113 @@ void GeoSet::setTextureCoords( Vec2 *tc, ushort *ti ) } -void GeoSet::setInterleavedArray( InterleaveArrayType format, float *pointer ) +void GeoSet::setTextureCoords( Vec2 *tc, uint *ti ) +{ + _tcoords = tc; + // note the size of tindex defaults 0, but will be recalculated + // automatically by computeNumVerts(). + _tindex.set(0,ti); + if( _texture_binding == BIND_OFF ) + setTextureBinding( BIND_DEFAULT ); + else + set_fast_path(); + +} + +void GeoSet::setTextureCoords( Vec2 *cp, IndexPointer& ip ) +{ + _tcoords = cp; + _tindex = ip; + _bbox_computed = false; + if( _texture_binding == BIND_OFF ) + setTextureBinding( BIND_DEFAULT ); + else + set_fast_path(); +} + +void GeoSet::setInterleavedArray( const InterleaveArrayType format, float *pointer ) { _iaformat = format; - _ogliaformat = - (_iaformat == IA_OFF ) ? 0 : - (_iaformat == IA_V2F ) ? GL_V2F: - (_iaformat == IA_V3F ) ? GL_V3F: - (_iaformat == IA_C4UB_V2F) ? GL_C4UB_V2F: - (_iaformat == IA_C4UB_V3F) ? GL_C4UB_V3F: - (_iaformat == IA_C3F_V3F) ? GL_C3F_V3F: - (_iaformat == IA_N3F_V3F) ? GL_N3F_V3F: - (_iaformat == IA_C4F_N3F_V3F) ? GL_C4F_N3F_V3F: - (_iaformat == IA_T2F_V3F) ? GL_T2F_V3F: - (_iaformat == IA_T4F_V4F) ? GL_T4F_V4F: - (_iaformat == IA_T2F_C4UB_V3F) ? GL_T2F_C4UB_V3F: - (_iaformat == IA_T2F_C3F_V3F) ? GL_T2F_C3F_V3F: - (_iaformat == IA_T2F_N3F_V3F) ? GL_T2F_N3F_V3F: - (_iaformat == IA_T2F_C4F_N3F_V3F) ? GL_T2F_C4F_N3F_V3F: - (_iaformat == IA_T4F_C4F_N3F_V4F) ? GL_T4F_C4F_N3F_V4F: 0; + _ogliaformat = + (_iaformat == IA_OFF ) ? 0 : + (_iaformat == IA_V2F ) ? GL_V2F: + (_iaformat == IA_V3F ) ? GL_V3F: + (_iaformat == IA_C4UB_V2F) ? GL_C4UB_V2F: + (_iaformat == IA_C4UB_V3F) ? GL_C4UB_V3F: + (_iaformat == IA_C3F_V3F) ? GL_C3F_V3F: + (_iaformat == IA_N3F_V3F) ? GL_N3F_V3F: + (_iaformat == IA_C4F_N3F_V3F) ? GL_C4F_N3F_V3F: + (_iaformat == IA_T2F_V3F) ? GL_T2F_V3F: + (_iaformat == IA_T4F_V4F) ? GL_T4F_V4F: + (_iaformat == IA_T2F_C4UB_V3F) ? GL_T2F_C4UB_V3F: + (_iaformat == IA_T2F_C3F_V3F) ? GL_T2F_C3F_V3F: + (_iaformat == IA_T2F_N3F_V3F) ? GL_T2F_N3F_V3F: + (_iaformat == IA_T2F_C4F_N3F_V3F) ? GL_T2F_C4F_N3F_V3F: + (_iaformat == IA_T4F_C4F_N3F_V4F) ? GL_T4F_C4F_N3F_V4F: 0; _iarray = pointer; + _iaindex.setToNull(); set_fast_path(); } -void GeoSet::setInterleavedArray( InterleaveArrayType format, float *ia, ushort *iai ) + +void GeoSet::setInterleavedArray( const InterleaveArrayType format, float *ia, ushort *iai ) { _iaformat = format; - _ogliaformat = - (_iaformat == IA_OFF ) ? 0 : - (_iaformat == IA_V2F ) ? GL_V2F: - (_iaformat == IA_V3F ) ? GL_V3F: - (_iaformat == IA_C4UB_V2F) ? GL_C4UB_V2F: - (_iaformat == IA_C4UB_V3F) ? GL_C4UB_V3F: - (_iaformat == IA_C3F_V3F) ? GL_C3F_V3F: - (_iaformat == IA_N3F_V3F) ? GL_N3F_V3F: - (_iaformat == IA_C4F_N3F_V3F) ? GL_C4F_N3F_V3F: - (_iaformat == IA_T2F_V3F) ? GL_T2F_V3F: - (_iaformat == IA_T4F_V4F) ? GL_T4F_V4F: - (_iaformat == IA_T2F_C4UB_V3F) ? GL_T2F_C4UB_V3F: - (_iaformat == IA_T2F_C3F_V3F) ? GL_T2F_C3F_V3F: - (_iaformat == IA_T2F_N3F_V3F) ? GL_T2F_N3F_V3F: - (_iaformat == IA_T2F_C4F_N3F_V3F) ? GL_T2F_C4F_N3F_V3F: - (_iaformat == IA_T4F_C4F_N3F_V4F) ? GL_T4F_C4F_N3F_V4F: 0; + _ogliaformat = + (_iaformat == IA_OFF ) ? 0 : + (_iaformat == IA_V2F ) ? GL_V2F: + (_iaformat == IA_V3F ) ? GL_V3F: + (_iaformat == IA_C4UB_V2F) ? GL_C4UB_V2F: + (_iaformat == IA_C4UB_V3F) ? GL_C4UB_V3F: + (_iaformat == IA_C3F_V3F) ? GL_C3F_V3F: + (_iaformat == IA_N3F_V3F) ? GL_N3F_V3F: + (_iaformat == IA_C4F_N3F_V3F) ? GL_C4F_N3F_V3F: + (_iaformat == IA_T2F_V3F) ? GL_T2F_V3F: + (_iaformat == IA_T4F_V4F) ? GL_T4F_V4F: + (_iaformat == IA_T2F_C4UB_V3F) ? GL_T2F_C4UB_V3F: + (_iaformat == IA_T2F_C3F_V3F) ? GL_T2F_C3F_V3F: + (_iaformat == IA_T2F_N3F_V3F) ? GL_T2F_N3F_V3F: + (_iaformat == IA_T2F_C4F_N3F_V3F) ? GL_T2F_C4F_N3F_V3F: + (_iaformat == IA_T4F_C4F_N3F_V4F) ? GL_T4F_C4F_N3F_V4F: 0; _iarray = ia; - _iaindex = iai; + // note the size of _iaindex defaults 0, but will be recalculated + // automatically by computeNumVerts(). + _iaindex.set(0,iai); + set_fast_path(); } -void GeoSet::setUseDisplayList(bool flag) +void GeoSet::setInterleavedArray( const InterleaveArrayType format, float *ia, IndexPointer& iai ) { - // if value unchanged simply return. - if (_useDisplayList==flag) return; + _iaformat = format; - // if was previously set to true, remove display list. - if (_useDisplayList) - { - if( _globj != 0 ) - { - glDeleteLists( _globj, 1 ); - _globj = 0; - } - } - // set with new value. - _useDisplayList = flag; -} + _ogliaformat = + (_iaformat == IA_OFF ) ? 0 : + (_iaformat == IA_V2F ) ? GL_V2F: + (_iaformat == IA_V3F ) ? GL_V3F: + (_iaformat == IA_C4UB_V2F) ? GL_C4UB_V2F: + (_iaformat == IA_C4UB_V3F) ? GL_C4UB_V3F: + (_iaformat == IA_C3F_V3F) ? GL_C3F_V3F: + (_iaformat == IA_N3F_V3F) ? GL_N3F_V3F: + (_iaformat == IA_C4F_N3F_V3F) ? GL_C4F_N3F_V3F: + (_iaformat == IA_T2F_V3F) ? GL_T2F_V3F: + (_iaformat == IA_T4F_V4F) ? GL_T4F_V4F: + (_iaformat == IA_T2F_C4UB_V3F) ? GL_T2F_C4UB_V3F: + (_iaformat == IA_T2F_C3F_V3F) ? GL_T2F_C3F_V3F: + (_iaformat == IA_T2F_N3F_V3F) ? GL_T2F_N3F_V3F: + (_iaformat == IA_T2F_C4F_N3F_V3F) ? GL_T2F_C4F_N3F_V3F: + (_iaformat == IA_T4F_C4F_N3F_V4F) ? GL_T4F_C4F_N3F_V4F: 0; -void GeoSet::dirtyDisplayList() -{ - if( _globj != 0 ) - { - glDeleteLists( _globj, 1 ); - _globj = 0; - } + _iarray = ia; + // note the size of _iaindex defaults 0, but will be recalculated + // automatically by computeNumVerts(). + _iaindex = iai; + + set_fast_path(); } + diff --git a/src/osg/GeoSet_ogl.cpp b/src/osg/GeoSet_ogl.cpp index 363e5ffae..73dba0df3 100644 --- a/src/osg/GeoSet_ogl.cpp +++ b/src/osg/GeoSet_ogl.cpp @@ -1,3 +1,7 @@ +#if defined(_MSC_VER) + #pragma warning( disable : 4786 ) +#endif + #include #include "osg/GL" #include "osg/GeoSet" @@ -5,6 +9,7 @@ using namespace osg; +#define DEBUG #define DO_SHADING 1 #define I_ON (1<<4) @@ -21,53 +26,52 @@ void GeoSet::set_fast_path( void ) } else { - if( ( _normal_binding != BIND_PERPRIM) && - ( _nindex == 0L ) && - ( _color_binding != BIND_PERPRIM) && - ( _colindex == 0L ) && - ( _primtype != FLAT_LINE_STRIP ) && - ( _primtype != FLAT_TRIANGLE_STRIP ) && - ( _primtype != FLAT_TRIANGLE_FAN ) - ) - _fast_path = V_ON; + if( ( _normal_binding != BIND_PERPRIM) && + ( _nindex.null() || _nindex ==_cindex) && + ( _color_binding != BIND_PERPRIM) && + ( _colindex.null() || _colindex ==_cindex ) && + ( _primtype != FLAT_LINE_STRIP ) && + ( _primtype != FLAT_TRIANGLE_STRIP ) && + ( _primtype != FLAT_TRIANGLE_FAN ) + ) + _fast_path = V_ON; else - { - _fast_path = 0; + { + _fast_path = 0; - #ifdef DEBUG + #ifdef DEBUG - if( _normal_binding == BIND_PERPRIM ) - notify( DEBUG ) << "Geoset - Failed fast path because NORMALS are bound PER_PRIM\n"; + if( _normal_binding == BIND_PERPRIM ) + notify( DEBUG ) << "Geoset - Failed fast path because NORMALS are bound PER_PRIM\n"; - if( _nindex != 0L ) - notify( DEBUG ) << "Geoset - Failed fast path because NORMAL indeces are specified\n"; + if( _nindex.valid() ) + notify( DEBUG ) << "Geoset - Failed fast path because NORMAL indeces are specified\n"; - if( _color_binding == BIND_PERPRIM ) - notify( DEBUG ) << "Geoset - Failed fast path because COLORS are bound PER_PRIM\n"; + if( _color_binding == BIND_PERPRIM ) + notify( DEBUG ) << "Geoset - Failed fast path because COLORS are bound PER_PRIM\n"; - if( _cindex != 0L ) - notify( DEBUG ) << "Geoset - Failed fast path because COLOR indeces are specified\n"; + if( _cindex.valid() ) + notify( DEBUG ) << "Geoset - Failed fast path because COLOR indeces are specified\n"; - if( _primtype == FLAT_LINE_STRIP ) - notify( DEBUG ) << "Geoset - Failed fast path because primitive is FLAT_LINE_STRIP\n"; + if( _primtype == FLAT_LINE_STRIP ) + notify( DEBUG ) << "Geoset - Failed fast path because primitive is FLAT_LINE_STRIP\n"; - if ( _primtype == FLAT_TRIANGLE_STRIP ) - notify( DEBUG ) << "Geoset - Failed fast path because primitive is FLAT_TRIANGLE_STRIP\n"; + if ( _primtype == FLAT_TRIANGLE_STRIP ) + notify( DEBUG ) << "Geoset - Failed fast path because primitive is FLAT_TRIANGLE_STRIP\n"; - if ( _primtype == FLAT_TRIANGLE_FAN ) - notify( DEBUG ) << "Geoset - Failed fast path because primitive is FLAT_TRIANGLE_FAN\n"; - - #endif - } + if ( _primtype == FLAT_TRIANGLE_FAN ) + notify( DEBUG ) << "Geoset - Failed fast path because primitive is FLAT_TRIANGLE_FAN\n"; + #endif + } if( _fast_path ) { if( _color_binding == BIND_PERVERTEX ) - _fast_path |= C_ON; + _fast_path |= C_ON; if( _normal_binding == BIND_PERVERTEX ) - _fast_path |= N_ON; + _fast_path |= N_ON; if( _texture_binding == BIND_PERVERTEX ) - _fast_path |= T_ON; + _fast_path |= T_ON; } } @@ -76,113 +80,113 @@ void GeoSet::set_fast_path( void ) #endif } + void GeoSet::draw_fast_path( void ) { - ushort *ocindex = _cindex; + IndexPointer ocindex = _cindex; switch( _fast_path ) { case (I_ON) : _cindex = _iaindex; glInterleavedArrays( (GLenum)_ogliaformat, 0, _iarray ); - break; + break; case (V_ON) : - glDisableClientState( GL_COLOR_ARRAY ); - glDisableClientState( GL_NORMAL_ARRAY ); - glDisableClientState( GL_TEXTURE_COORD_ARRAY ); - glEnableClientState( GL_VERTEX_ARRAY ); - glVertexPointer( 3, GL_FLOAT, 0, (GLfloat *)_coords ); - break; + glDisableClientState( GL_COLOR_ARRAY ); + glDisableClientState( GL_NORMAL_ARRAY ); + glDisableClientState( GL_TEXTURE_COORD_ARRAY ); + glEnableClientState( GL_VERTEX_ARRAY ); + glVertexPointer( 3, GL_FLOAT, 0, (GLfloat *)_coords ); + break; - case (T_ON|V_ON) : - glDisableClientState( GL_COLOR_ARRAY ); - glDisableClientState( GL_NORMAL_ARRAY ); - glEnableClientState( GL_TEXTURE_COORD_ARRAY ); - glTexCoordPointer( 2, GL_FLOAT, 0, (GLfloat *)_tcoords ); - glEnableClientState( GL_VERTEX_ARRAY ); - glVertexPointer( 3, GL_FLOAT, 0, (GLfloat *)_coords ); - break; + case (T_ON|V_ON) : + glDisableClientState( GL_COLOR_ARRAY ); + glDisableClientState( GL_NORMAL_ARRAY ); + glEnableClientState( GL_TEXTURE_COORD_ARRAY ); + glTexCoordPointer( 2, GL_FLOAT, 0, (GLfloat *)_tcoords ); + glEnableClientState( GL_VERTEX_ARRAY ); + glVertexPointer( 3, GL_FLOAT, 0, (GLfloat *)_coords ); + break; - case (N_ON|V_ON) : - glDisableClientState( GL_COLOR_ARRAY ); - glEnableClientState( GL_NORMAL_ARRAY ); - glNormalPointer( GL_FLOAT, 0, (GLfloat *)_normals ); - glDisableClientState( GL_TEXTURE_COORD_ARRAY ); - glEnableClientState( GL_VERTEX_ARRAY ); - glVertexPointer( 3, GL_FLOAT, 0, (GLfloat *)_coords ); - break; + case (N_ON|V_ON) : + glDisableClientState( GL_COLOR_ARRAY ); + glEnableClientState( GL_NORMAL_ARRAY ); + glNormalPointer( GL_FLOAT, 0, (GLfloat *)_normals ); + glDisableClientState( GL_TEXTURE_COORD_ARRAY ); + glEnableClientState( GL_VERTEX_ARRAY ); + glVertexPointer( 3, GL_FLOAT, 0, (GLfloat *)_coords ); + break; case (N_ON|T_ON|V_ON) : - glDisableClientState( GL_COLOR_ARRAY ); - glEnableClientState( GL_NORMAL_ARRAY ); + glDisableClientState( GL_COLOR_ARRAY ); + glEnableClientState( GL_NORMAL_ARRAY ); glNormalPointer( GL_FLOAT, 0, (GLfloat *)_normals ); glEnableClientState( GL_TEXTURE_COORD_ARRAY ); glTexCoordPointer( 2, GL_FLOAT, 0, (GLfloat *)_tcoords ); - glEnableClientState( GL_VERTEX_ARRAY ); - glVertexPointer( 3, GL_FLOAT, 0, (GLfloat *)_coords ); - break; + glEnableClientState( GL_VERTEX_ARRAY ); + glVertexPointer( 3, GL_FLOAT, 0, (GLfloat *)_coords ); + break; - case (C_ON|V_ON) : - glEnableClientState( GL_COLOR_ARRAY ); + case (C_ON|V_ON) : + glEnableClientState( GL_COLOR_ARRAY ); glColorPointer( 4, GL_FLOAT, 0, (GLfloat *)_colors ); - glDisableClientState( GL_NORMAL_ARRAY ); - glDisableClientState( GL_TEXTURE_COORD_ARRAY ); - glEnableClientState( GL_VERTEX_ARRAY ); - glVertexPointer( 3, GL_FLOAT, 0, (GLfloat *)_coords ); - break; + glDisableClientState( GL_NORMAL_ARRAY ); + glDisableClientState( GL_TEXTURE_COORD_ARRAY ); + glEnableClientState( GL_VERTEX_ARRAY ); + glVertexPointer( 3, GL_FLOAT, 0, (GLfloat *)_coords ); + break; - - case (C_ON|T_ON|V_ON) : - glEnableClientState( GL_COLOR_ARRAY ); + case (C_ON|T_ON|V_ON) : + glEnableClientState( GL_COLOR_ARRAY ); glColorPointer( 4, GL_FLOAT, 0, (GLfloat *)_colors ); glDisableClientState( GL_NORMAL_ARRAY ); glEnableClientState( GL_TEXTURE_COORD_ARRAY ); glTexCoordPointer( 2, GL_FLOAT, 0, (GLfloat *)_tcoords ); glEnableClientState( GL_VERTEX_ARRAY ); glVertexPointer( 3, GL_FLOAT, 0, (GLfloat *)_coords ); - break; + break; - case (C_ON|N_ON|V_ON) : - glEnableClientState( GL_COLOR_ARRAY ); + case (C_ON|N_ON|V_ON) : + glEnableClientState( GL_COLOR_ARRAY ); glColorPointer( 4, GL_FLOAT, 0, (GLfloat *)_colors ); glEnableClientState( GL_NORMAL_ARRAY ); glNormalPointer( GL_FLOAT, 0, (GLfloat *)_normals ); glDisableClientState( GL_TEXTURE_COORD_ARRAY ); - glEnableClientState( GL_VERTEX_ARRAY ); - glVertexPointer( 3, GL_FLOAT, 0, (GLfloat *)_coords ); - break; + glEnableClientState( GL_VERTEX_ARRAY ); + glVertexPointer( 3, GL_FLOAT, 0, (GLfloat *)_coords ); + break; - case (C_ON|N_ON|T_ON|V_ON) : - glEnableClientState( GL_COLOR_ARRAY ); + case (C_ON|N_ON|T_ON|V_ON) : + glEnableClientState( GL_COLOR_ARRAY ); glColorPointer( 4, GL_FLOAT, 0, (GLfloat *)_colors ); glEnableClientState( GL_NORMAL_ARRAY ); glNormalPointer( GL_FLOAT, 0, (GLfloat *)_normals ); glEnableClientState( GL_TEXTURE_COORD_ARRAY ); glTexCoordPointer( 2, GL_FLOAT, 0, (GLfloat *)_tcoords ); glEnableClientState( GL_VERTEX_ARRAY ); - glVertexPointer( 3, GL_FLOAT, 0, (GLfloat *)_coords ); - break; + glVertexPointer( 3, GL_FLOAT, 0, (GLfloat *)_coords ); + break; } if( _color_binding == BIND_OVERALL ) { - if( _colindex != 0L ) - glColor4fv( (GLfloat * )&_colors[_colindex[0]] ); - else - glColor4fv( (GLfloat * )&_colors[0] ); + if( _colindex.valid() ) + glColor4fv( (GLfloat * )&_colors[_colindex[0]] ); + else + glColor4fv( (GLfloat * )&_colors[0] ); } if( _normal_binding == BIND_OVERALL ) { - if( _nindex != 0L ) - glNormal3fv( (GLfloat * )&_normals[_nindex[0]] ); - else - glNormal3fv( (GLfloat * )&_normals[0] ); + if( _nindex.valid() ) + glNormal3fv( (GLfloat * )&_normals[_nindex[0]] ); + else + glNormal3fv( (GLfloat * )&_normals[0] ); } - if( _needprimlen ) // LINE_STRIP, LINE_LOOP, TRIANGLE_STRIP, - // TRIANGLE_FAN, QUAD_STRIP, POLYGONS + if( _needprimlen ) // LINE_STRIP, LINE_LOOP, TRIANGLE_STRIP, + // TRIANGLE_FAN, QUAD_STRIP, POLYGONS { int index = 0; if( _primLengths == (int *)0 ) @@ -192,18 +196,29 @@ void GeoSet::draw_fast_path( void ) } for( int i = 0; i < _numprims; i++ ) - { - if( _cindex != (ushort *)0L ) - glDrawElements( (GLenum)_oglprimtype, _primLengths[i], GL_UNSIGNED_SHORT, &_cindex[index] ); - else - glDrawArrays( (GLenum)_oglprimtype, index, _primLengths[i] ); - index += _primLengths[i]; - } + { + if( _cindex.valid() ) + { + if (_cindex._is_ushort) + glDrawElements( (GLenum)_oglprimtype, _primLengths[i], GL_UNSIGNED_SHORT, &_cindex._ptr._ushort[index] ); + else + glDrawElements( (GLenum)_oglprimtype, _primLengths[i], GL_UNSIGNED_INT, &_cindex._ptr._uint[index] ); + } + else + glDrawArrays( (GLenum)_oglprimtype, index, _primLengths[i] ); + + index += _primLengths[i]; + } } - else // POINTS, LINES, TRIANGLES, QUADS + else // POINTS, LINES, TRIANGLES, QUADS { - if( _cindex != (ushort *)0L ) - glDrawElements( (GLenum)_oglprimtype, _numindices, GL_UNSIGNED_SHORT, _cindex ); + if( _cindex.valid()) + { + if (_cindex._is_ushort) + glDrawElements( (GLenum)_oglprimtype, _cindex._size, GL_UNSIGNED_SHORT, _cindex._ptr._ushort ); + else + glDrawElements( (GLenum)_oglprimtype, _cindex._size, GL_UNSIGNED_INT, _cindex._ptr._uint ); + } else glDrawArrays( (GLenum)_oglprimtype, 0, _numcoords ); } @@ -211,63 +226,64 @@ void GeoSet::draw_fast_path( void ) _cindex = ocindex; } + void GeoSet::draw_alternate_path( void ) { - if( (_color_binding == BIND_PERVERTEX) && (_cindex == 0L) && (_flat_shaded_skip == 0) ) + if( (_color_binding == BIND_PERVERTEX) && (_colindex.null() || _colindex ==_cindex) && (_flat_shaded_skip == 0) ) { - glEnableClientState( GL_COLOR_ARRAY ); + glEnableClientState( GL_COLOR_ARRAY ); glColorPointer( 4, GL_FLOAT, 0, (GLfloat *)_colors ); } else { glDisableClientState( GL_COLOR_ARRAY ); - if( _color_binding == BIND_OVERALL ) - { - if( _colindex ) - glColor4fv( (GLfloat *)&_colors[_colindex[0]] ); - else - glColor4fv( (GLfloat *)&_colors[0] ); - } - } + if( _color_binding == BIND_OVERALL ) + { + if( _colindex.valid() ) + glColor4fv( (GLfloat *)&_colors[_colindex[0]] ); + else + glColor4fv( (GLfloat *)&_colors[0] ); + } + } - if( (_normal_binding == BIND_PERVERTEX) && (_nindex == 0L) && (_flat_shaded_skip == 0) ) + if( (_normal_binding == BIND_PERVERTEX) && (_nindex.null() || _nindex ==_cindex) && (_flat_shaded_skip == 0) ) { glEnableClientState( GL_NORMAL_ARRAY ); - glNormalPointer( GL_FLOAT, 0, (GLfloat *)_normals ); + glNormalPointer( GL_FLOAT, 0, (GLfloat *)_normals ); } else { glDisableClientState( GL_NORMAL_ARRAY ); - if( _normal_binding == BIND_OVERALL ) - { - if( _nindex ) - glNormal3fv( (GLfloat *)&_normals[_nindex[0]] ); - else - glNormal3fv( (GLfloat *)&_normals[0] ); - } - } + if( _normal_binding == BIND_OVERALL ) + { + if( _nindex.valid() ) + glNormal3fv( (GLfloat *)&_normals[_nindex[0]] ); + else + glNormal3fv( (GLfloat *)&_normals[0] ); + } + } - if( (_texture_binding == BIND_PERVERTEX) && (_tindex == 0L) ) - { - glEnableClientState( GL_TEXTURE_COORD_ARRAY ); - glTexCoordPointer( 2, GL_FLOAT, 0, _tcoords ); - } - else - glDisableClientState( GL_TEXTURE_COORD_ARRAY ); + if( (_texture_binding == BIND_PERVERTEX) && (_tindex.null()) ) + { + glEnableClientState( GL_TEXTURE_COORD_ARRAY ); + glTexCoordPointer( 2, GL_FLOAT, 0, _tcoords ); + } + else + glDisableClientState( GL_TEXTURE_COORD_ARRAY ); glEnableClientState( GL_VERTEX_ARRAY ); glVertexPointer( 3, GL_FLOAT, 0, (GLfloat *)_coords ); - if( _needprimlen ) // LINE_STRIP, LINE_LOOP, TRIANGLE_STRIP, - // TRIANGLE_FAN, QUAD_STRIP, POLYGONS - // FLAT_LINE_STRIP, FLAT_TRIANGLE_STRIP, FLAT_TRIANGLE_FAN + if( _needprimlen ) // LINE_STRIP, LINE_LOOP, TRIANGLE_STRIP, + // TRIANGLE_FAN, QUAD_STRIP, POLYGONS + // FLAT_LINE_STRIP, FLAT_TRIANGLE_STRIP, FLAT_TRIANGLE_FAN { int i, j; int index = 0; - int ai = 0; - int ci = 0; - int ni = 0; - int ti = 0; + int ai = 0; + int ci = 0; + int ni = 0; + int ti = 0; if( _primLengths == (int *)0 ) { @@ -276,152 +292,166 @@ void GeoSet::draw_alternate_path( void ) } for( i = 0; i < _numprims; i++ ) - { - if( _color_binding == BIND_PERPRIM ) - { - if( _colindex ) - glColor4fv( (GLfloat *)&_colors[_colindex[ci++]] ); - else - glColor4fv( (GLfloat *)&_colors[ci++] ); - } - if( _normal_binding == BIND_PERPRIM ) - { - if( _nindex ) - glNormal3fv( (GLfloat *)&_normals[_nindex[ni++]] ); - else - glNormal3fv( (GLfloat *)&_normals[ni++] ); - } + { + if( _color_binding == BIND_PERPRIM ) + { + if( _colindex.valid() ) + glColor4fv( (GLfloat *)&_colors[_colindex[ci++]] ); + else + glColor4fv( (GLfloat *)&_colors[ci++] ); + } + if( _normal_binding == BIND_PERPRIM ) + { + if( _nindex.valid() ) + glNormal3fv( (GLfloat *)&_normals[_nindex[ni++]] ); + else + glNormal3fv( (GLfloat *)&_normals[ni++] ); + } - if( _flat_shaded_skip ) - { -#ifdef DO_SHADING -glShadeModel( GL_FLAT ); -#endif - glBegin( (GLenum)_oglprimtype ); - for( j = 0; j < _primLengths[i]; j++ ) - { - if( j >= _flat_shaded_skip ) - { - if( _color_binding == BIND_PERVERTEX ) - { - if( (_colindex != 0L) ) - glColor4fv( (GLfloat *)&_colors[_colindex[ci++]] ); - else - glColor4fv( (GLfloat *)&_colors[ci++] ); - } + if( _flat_shaded_skip ) + { + #ifdef DO_SHADING + glShadeModel( GL_FLAT ); + #endif + glBegin( (GLenum)_oglprimtype ); + for( j = 0; j < _primLengths[i]; j++ ) + { + if( j >= _flat_shaded_skip ) + { + if( _color_binding == BIND_PERVERTEX ) + { + if( (_colindex.valid()) ) + glColor4fv( (GLfloat *)&_colors[_colindex[ci++]] ); + else + glColor4fv( (GLfloat *)&_colors[ci++] ); + } - if( _normal_binding == BIND_PERVERTEX ) - { - if(_nindex != 0L) - glNormal3fv( (GLfloat *)&_normals[_nindex[ni++]] ); - else - glNormal3fv( (GLfloat *)&_normals[ni++] ); - } - } + if( _normal_binding == BIND_PERVERTEX ) + { + if(_nindex.valid()) + glNormal3fv( (GLfloat *)&_normals[_nindex[ni++]] ); + else + glNormal3fv( (GLfloat *)&_normals[ni++] ); + } + } - if( _texture_binding == BIND_PERVERTEX ) - { - if( _tindex != 0L ) - glTexCoord2fv( (GLfloat *)&_tcoords[_tindex[ti++]] ); - else - glTexCoord2fv( (GLfloat *)&_tcoords[ti++] ); - } + if( _texture_binding == BIND_PERVERTEX ) + { + if( _tindex.valid() ) + glTexCoord2fv( (GLfloat *)&_tcoords[_tindex[ti++]] ); + else + glTexCoord2fv( (GLfloat *)&_tcoords[ti++] ); + } - if( _cindex ) - glArrayElement( _cindex[ai++] ); - else - glArrayElement( ai++ ); - } - glEnd(); + if( _cindex.valid() ) + glArrayElement( _cindex[ai++] ); + else + glArrayElement( ai++ ); + } + glEnd(); -#ifdef DO_SHADING -glShadeModel( GL_SMOOTH ); -#endif - } + #ifdef DO_SHADING + glShadeModel( GL_SMOOTH ); + #endif + } - else - if( ((_color_binding == BIND_PERVERTEX ) && (_colindex != 0L) ) || - ((_normal_binding == BIND_PERVERTEX ) && (_nindex != 0L) ) || - ((_texture_binding == BIND_PERVERTEX ) && (_tindex != 0L) ) ) - { - glBegin( (GLenum)_oglprimtype ); - for( j = 0; j < _primLengths[i]; j++ ) - { - if( (_color_binding == BIND_PERVERTEX) && (_colindex != 0L) ) - glColor4fv( (GLfloat *)&_colors[_colindex[ci++]] ); + else + if( ((_color_binding == BIND_PERVERTEX ) && (_colindex.valid()) ) || + ((_normal_binding == BIND_PERVERTEX ) && (_nindex.valid()) ) || + ((_texture_binding == BIND_PERVERTEX ) && (_tindex.valid()) ) ) + { + glBegin( (GLenum)_oglprimtype ); + for( j = 0; j < _primLengths[i]; j++ ) + { + if( (_color_binding == BIND_PERVERTEX) && (_colindex.valid()) ) + glColor4fv( (GLfloat *)&_colors[_colindex[ci++]] ); - if( (_normal_binding == BIND_PERVERTEX) && (_nindex != 0L) ) - glNormal3fv( (GLfloat *)&_normals[_nindex[ci++]] ); + if( (_normal_binding == BIND_PERVERTEX) && (_nindex.valid()) ) + glNormal3fv( (GLfloat *)&_normals[_nindex[ni++]] ); - if( (_texture_binding == BIND_PERVERTEX) && (_tindex != 0L) ) - glTexCoord2fv( (GLfloat *)&_tcoords[_tindex[ti++]] ); + if( (_texture_binding == BIND_PERVERTEX) && (_tindex.valid()) ) + glTexCoord2fv( (GLfloat *)&_tcoords[_tindex[ti++]] ); - if( _cindex ) - glArrayElement( _cindex[ai++] ); - else - glArrayElement( ai++ ); - } - glEnd(); - } - else - { - if( _cindex != (ushort *)0L ) - glDrawElements( (GLenum)_oglprimtype, _primLengths[i], GL_UNSIGNED_SHORT, &_cindex[index] ); - else - glDrawArrays( (GLenum)_oglprimtype, index, _primLengths[i] ); - } - index += _primLengths[i]; - } + if( _cindex.valid() ) + glArrayElement( _cindex[ai++] ); + else + glArrayElement( ai++ ); + } + glEnd(); + } + else + { + + if( _cindex.valid() ) + { + if (_cindex._is_ushort) + glDrawElements( (GLenum)_oglprimtype, _primLengths[i], GL_UNSIGNED_SHORT, &_cindex._ptr._ushort[index] ); + else + glDrawElements( (GLenum)_oglprimtype, _primLengths[i], GL_UNSIGNED_INT, &_cindex._ptr._uint[index] ); + } + else + glDrawArrays( (GLenum)_oglprimtype, index, _primLengths[i] ); + } + index += _primLengths[i]; + } } - else // POINTS, LINES, TRIANGLES, QUADS + else // POINTS, LINES, TRIANGLES, QUADS { int i, j; if( _normal_binding == BIND_PERPRIM || _color_binding == BIND_PERPRIM || - ((_color_binding == BIND_PERVERTEX ) && (_colindex != 0L) ) || - ((_normal_binding == BIND_PERVERTEX ) && (_nindex != 0L) ) || - ((_texture_binding == BIND_PERVERTEX ) && (_tindex != 0L) ) ) - { - glBegin( (GLenum)_oglprimtype ); - for( i = 0; i < _numprims; i++ ) - { - if( _color_binding == BIND_PERPRIM ) - { - if( _colindex ) - glColor4fv( (GLfloat *)&_colors[_colindex[i]] ); - else - glColor4fv( (GLfloat *)&_colors[i] ); - } - if( _normal_binding == BIND_PERPRIM ) - { - if( _nindex ) - glNormal3fv( (GLfloat *)&_normals[_nindex[i]] ); - else - glNormal3fv( (GLfloat *)&_normals[i] ); - } + ((_color_binding == BIND_PERVERTEX ) && (_colindex.valid()) ) || + ((_normal_binding == BIND_PERVERTEX ) && (_nindex.valid()) ) || + ((_texture_binding == BIND_PERVERTEX ) && (_tindex.valid()) ) ) + { - for( j = 0; j < _primlength; j++ ) - { - if( (_color_binding == BIND_PERVERTEX) && (_colindex != 0L ) ) - glColor4fv( (GLfloat *)&_colors[_colindex[i*_primlength+j]] ); + glBegin( (GLenum)_oglprimtype ); + for( i = 0; i < _numprims; i++ ) + { + if( _color_binding == BIND_PERPRIM ) + { + if( _colindex.valid() ) + glColor4fv( (GLfloat *)&_colors[_colindex[i]] ); + else + glColor4fv( (GLfloat *)&_colors[i] ); + } + if( _normal_binding == BIND_PERPRIM ) + { + if( _nindex.valid() ) + glNormal3fv( (GLfloat *)&_normals[_nindex[i]] ); + else + glNormal3fv( (GLfloat *)&_normals[i] ); + } - if( (_normal_binding == BIND_PERVERTEX) && (_nindex != 0L ) ) - glNormal3fv( (GLfloat *)&_normals[_nindex[i*_primlength+j]] ); + for( j = 0; j < _primlength; j++ ) + { + if( (_color_binding == BIND_PERVERTEX) && (_colindex.valid() ) ) + glColor4fv( (GLfloat *)&_colors[_colindex[i*_primlength+j]] ); - if( (_texture_binding == BIND_PERVERTEX) && (_tindex != 0L ) ) - glTexCoord2fv( (GLfloat *)&_tcoords[_tindex[i*_primlength+j]] ); + if( (_normal_binding == BIND_PERVERTEX) && (_nindex.valid() ) ) + glNormal3fv( (GLfloat *)&_normals[_nindex[i*_primlength+j]] ); - glArrayElement( i*_primlength+j ); - } - } - glEnd(); - } - else - { - if( _cindex != (ushort *)0L ) - glDrawElements( (GLenum)_oglprimtype, _numindices, GL_UNSIGNED_SHORT, _cindex ); - else + if( (_texture_binding == BIND_PERVERTEX) && (_tindex.valid() ) ) + glTexCoord2fv( (GLfloat *)&_tcoords[_tindex[i*_primlength+j]] ); + + if( _cindex.valid()) + glArrayElement( _cindex[i*_primlength+j] ); + else + glArrayElement( i*_primlength+j ); + } + } + glEnd(); + } + else + { + if( _cindex.valid()) + { + if (_cindex._is_ushort) + glDrawElements( (GLenum)_oglprimtype, _cindex._size, GL_UNSIGNED_SHORT, _cindex._ptr._ushort ); + else + glDrawElements( (GLenum)_oglprimtype, _cindex._size, GL_UNSIGNED_INT, _cindex._ptr._uint ); + } + else glDrawArrays( (GLenum)_oglprimtype, 0, _numcoords ); - } + } } } - diff --git a/src/osg/Geode.cpp b/src/osg/Geode.cpp index 1b30bfb1c..1df0c17a5 100644 --- a/src/osg/Geode.cpp +++ b/src/osg/Geode.cpp @@ -1,8 +1,6 @@ #include #include #include "osg/Geode" -#include "osg/Input" -#include "osg/Output" #include @@ -13,101 +11,51 @@ using std::for_each; #define square(x) ((x)*(x)) -#include "osg/Registry" - using namespace osg; -RegisterObjectProxy g_GeodeProxy; - Geode::Geode() { - _bsphere_computed = false; } Geode::~Geode() { - // ref_ptr<> automactially decrements the reference count of all geosets. + // ref_ptr<> automactially decrements the reference count of all drawables. } - -bool Geode::readLocalData(Input& fr) +const bool Geode::addDrawable( Drawable *gset ) { - - bool iteratorAdvanced = false; - - if (Node::readLocalData(fr)) iteratorAdvanced = true; - - int num_geosets; - if (fr[0].matchWord("num_geosets") && - fr[1].getInt(num_geosets)) - { - // could allocate space for children here... - fr+=2; - iteratorAdvanced = true; - } - - GeoSet* gset_read = NULL; - do - { - if ((gset_read=static_cast(GeoSet::instance()->readClone(fr)))) - { - addGeoSet(gset_read); - iteratorAdvanced = true; - } - - } while(gset_read != NULL); - - return iteratorAdvanced; -} - - -bool Geode::writeLocalData(Output& fw) -{ - Node::writeLocalData(fw); - - fw.indent() << "num_geosets " << getNumGeosets() << endl; - for(GeoSetList::iterator itr = _geosets.begin(); - itr!=_geosets.end(); - ++itr) - { - (*itr)->write(fw); - } - return true; -} - - -bool Geode::addGeoSet( GeoSet *gset ) -{ - if (gset && !containsGeoSet(gset)) + if (gset && !containsDrawable(gset)) { // note ref_ptr<> automatically handles incrementing gset's reference count. - _geosets.push_back(gset); + _drawables.push_back(gset); dirtyBound(); return true; } else return false; } -bool Geode::removeGeoSet( GeoSet *gset ) + +const bool Geode::removeDrawable( Drawable *gset ) { - GeoSetList::iterator itr = findGeoSet(gset); - if (itr!=_geosets.end()) + DrawableList::iterator itr = findDrawable(gset); + if (itr!=_drawables.end()) { // note ref_ptr<> automatically handles decrementing gset's reference count. - _geosets.erase(itr); + _drawables.erase(itr); dirtyBound(); return true; } else return false; } -bool Geode::replaceGeoSet( GeoSet *origGset, GeoSet *newGset ) + +const bool Geode::replaceDrawable( Drawable *origGset, Drawable *newGset ) { if (newGset==NULL || origGset==newGset) return false; - GeoSetList::iterator itr = findGeoSet(origGset); - if (itr!=_geosets.end()) + DrawableList::iterator itr = findDrawable(origGset); + if (itr!=_drawables.end()) { // note ref_ptr<> automatically handles decrementing origGset's reference count, // and inccrementing newGset's reference count. @@ -116,46 +64,56 @@ bool Geode::replaceGeoSet( GeoSet *origGset, GeoSet *newGset ) return true; } else return false; - + } -bool Geode::computeBound( void ) -{ +const bool Geode::computeBound() const +{ BoundingBox bb; - GeoSetList::iterator itr; - for(itr=_geosets.begin(); - itr!=_geosets.end(); + + DrawableList::const_iterator itr; + for(itr=_drawables.begin(); + itr!=_drawables.end(); ++itr) { bb.expandBy((*itr)->getBound()); } - - _bsphere._center = bb.center(); - _bsphere._radius = 0.0f; - - for(itr=_geosets.begin(); - itr!=_geosets.end(); - ++itr) + + if (bb.isValid()) { - const BoundingBox& bbox = (*itr)->getBound(); - for(unsigned int c=0;c<8;++c) + + _bsphere._center = bb.center(); + _bsphere._radius = 0.0f; + + for(itr=_drawables.begin(); + itr!=_drawables.end(); + ++itr) { - _bsphere.expandRadiusBy(bbox.corner(c)); + const BoundingBox& bbox = (*itr)->getBound(); + for(unsigned int c=0;c<8;++c) + { + _bsphere.expandRadiusBy(bbox.corner(c)); + } } - } - _bsphere_computed=true; - return true; + _bsphere_computed=true; + return true; + } + else + { + _bsphere.init(); + _bsphere_computed=true; + return false; + } } - -void Geode::compileGeoSets( void ) +void Geode::compileDrawables(State& state) { - for(GeoSetList::iterator itr = _geosets.begin(); - itr!=_geosets.end(); + for(DrawableList::iterator itr = _drawables.begin(); + itr!=_drawables.end(); ++itr) { - (*itr)->compile(); + (*itr)->compile(state); } } diff --git a/src/osg/Group.cpp b/src/osg/Group.cpp index 0fa876d97..23e83f2ba 100644 --- a/src/osg/Group.cpp +++ b/src/osg/Group.cpp @@ -1,9 +1,6 @@ #include #include #include "osg/Group" -#include "osg/Input" -#include "osg/Output" -#include "osg/Registry" #include "osg/BoundingBox" #include @@ -18,8 +15,6 @@ using namespace osg; -RegisterObjectProxy g_GroupProxy; - Group::Group() { } @@ -29,8 +24,8 @@ Group::~Group() { for(ChildList::iterator itr=_children.begin(); - itr!=_children.end(); - ++itr) + itr!=_children.end(); + ++itr) { Node* child = itr->get(); ParentList::iterator pitr = std::find(child->_parents.begin(),child->_parents.end(),this); @@ -43,8 +38,8 @@ Group::~Group() void Group::traverse(NodeVisitor& nv) { for(ChildList::iterator itr=_children.begin(); - itr!=_children.end(); - ++itr) + itr!=_children.end(); + ++itr) { (*itr)->accept(nv); } @@ -68,23 +63,26 @@ bool Group::addChild( Node *child ) else return false; } + bool Group::removeChild( Node *child ) { ChildList::iterator itr = findNode(child); if (itr!=_children.end()) { + // remove this group from the child parent list. + ParentList::iterator pitr = std::find(child->_parents.begin(),child->_parents.end(),this); + if (pitr!=child->_parents.end()) child->_parents.erase(pitr); + // note ref_ptr<> automatically handles decrementing child's reference count. _children.erase(itr); dirtyBound(); - ParentList::iterator pitr = std::find(child->_parents.begin(),child->_parents.end(),child); - if (pitr!=child->_parents.end()) child->_parents.erase(pitr); - return true; } else return false; } + bool Group::replaceChild( Node *origNode, Node *newNode ) { if (newNode==NULL || origNode==newNode) return false; @@ -92,7 +90,7 @@ bool Group::replaceChild( Node *origNode, Node *newNode ) ChildList::iterator itr = findNode(origNode); if (itr!=_children.end()) { - ParentList::iterator pitr = std::find(origNode->_parents.begin(),origNode->_parents.end(),origNode); + ParentList::iterator pitr = std::find(origNode->_parents.begin(),origNode->_parents.end(),this); if (pitr!=origNode->_parents.end()) origNode->_parents.erase(pitr); // note ref_ptr<> automatically handles decrementing origNode's reference count, @@ -106,67 +104,29 @@ bool Group::replaceChild( Node *origNode, Node *newNode ) return true; } else return false; - + } -bool Group::readLocalData(Input& fr) -{ - bool iteratorAdvanced = false; - if (Node::readLocalData(fr)) iteratorAdvanced = true; - - int num_children; - if (fr[0].matchWord("num_children") && - fr[1].getInt(num_children)) - { - // could allocate space for children here... - fr+=2; - iteratorAdvanced = true; - } - - Node* node = NULL; - while((node=fr.readNode())!=NULL) - { - addChild(node); - iteratorAdvanced = true; - } - - return iteratorAdvanced; -} - - -bool Group::writeLocalData(Output& fw) -{ - Node::writeLocalData(fw); - - fw.indent() << "num_children " << getNumChildren() << endl; - for(int i=0;iwrite(fw); - } - return true; -} - - -bool Group::computeBound() +const bool Group::computeBound() const { _bsphere_computed = true; _bsphere.init(); if (_children.empty()) return false; - + BoundingBox bb; bb.init(); - ChildList::iterator itr; + ChildList::const_iterator itr; for(itr=_children.begin(); itr!=_children.end(); ++itr) { bb.expandBy((*itr)->getBound()); - } + } if (!bb.isValid()) return false; - + _bsphere._center = bb.center(); _bsphere._radius = 0.0f; for(itr=_children.begin(); @@ -174,7 +134,7 @@ bool Group::computeBound() ++itr) { _bsphere.expandRadiusBy((*itr)->getBound()); - } + } return true; } diff --git a/src/osg/Image.cpp b/src/osg/Image.cpp index 7884cca10..35011809b 100644 --- a/src/osg/Image.cpp +++ b/src/osg/Image.cpp @@ -1,19 +1,19 @@ #include "osg/Image" -#include "osg/Input" -#include "osg/Output" #include "osg/GL" #include "osg/Notify" #include #include -#include +#include #include +#include + using namespace osg; Image::Image() { - _fileName = NULL; + _fileName = ""; _s = _t = _r = 0; _internalFormat = 0; _pixelFormat = (unsigned int)0; @@ -26,26 +26,22 @@ Image::Image() Image::~Image() { - if (_fileName) ::free(_fileName); if (_data) ::free(_data); } -void Image::setFileName(const char* fileName) +void Image::setFileName(const std::string& fileName) { - if (_fileName) ::free(_fileName); - - if (fileName) _fileName = strdup(fileName); - else _fileName = NULL; + _fileName = fileName; } -void Image::setImage(int s,int t,int r, - int internalFormat, - unsigned int pixelFormat, - unsigned int dataType, +void Image::setImage(const int s,const int t,const int r, + const int internalFormat, + const unsigned int pixelFormat, + const unsigned int dataType, unsigned char *data, - int packing) + const int packing) { if (_data) ::free(_data); @@ -58,48 +54,23 @@ void Image::setImage(int s,int t,int r, _dataType = dataType; _data = data; - - + if (packing<0) { if (_s%4==0) _packing = 4; else - _packing = 1; + _packing = 1; } else _packing = packing; - -// scaleImageTo(16,16,_r); + + // test scaling... + // scaleImageTo(16,16,_r); } - -bool Image::readLocalData(Input& fr) -{ - bool iteratorAdvanced = false; - if (fr[0].matchWord("file") && fr[1].isString()) - { -//loadFile(fr[1].getStr()); - fr += 2; - iteratorAdvanced = true; - } - - return iteratorAdvanced; -} - - -bool Image::writeLocalData(Output& fw) -{ - if (_fileName) - { - fw.indent() << "file \""<<_fileName<<"\""<s(),image->t()); } -Geode* osg::createGeodeForImage(osg::Image* image,float s,float t) + +Geode* osg::createGeodeForImage(osg::Image* image,const float s,const float t) { if (image) { @@ -167,20 +144,19 @@ Geode* osg::createGeodeForImage(osg::Image* image,float s,float t) float y = 1.0; float x = y*(s/t); - // set up the texture. + // set up the texture. osg::Texture* texture = new osg::Texture; texture->setImage(image); - // set up the geostate. - osg::GeoState* gstate = new osg::GeoState; - gstate->setMode(osg::GeoState::FACE_CULL,osg::GeoState::OFF); - gstate->setMode(osg::GeoState::LIGHTING,osg::GeoState::OFF); - gstate->setMode(osg::GeoState::TEXTURE,osg::GeoState::ON); - gstate->setAttribute(osg::GeoState::TEXTURE,texture); + // set up the drawstate. + osg::StateSet* dstate = new osg::StateSet; + dstate->setMode(GL_CULL_FACE,osg::StateAttribute::OFF); + dstate->setMode(GL_LIGHTING,osg::StateAttribute::OFF); + dstate->setAttributeAndModes(texture,osg::StateAttribute::ON); // set up the geoset. osg::GeoSet* gset = new osg::GeoSet; - gset->setGeoState(gstate); + gset->setStateSet(dstate); osg::Vec3* coords = new Vec3 [4]; coords[0].set(-x,0.0f,y); @@ -198,7 +174,7 @@ Geode* osg::createGeodeForImage(osg::Image* image,float s,float t) gset->setTextureBinding(osg::GeoSet::BIND_PERVERTEX); osg::Vec4* colours = new Vec4; - colours->set(1.0f,1.0f,1.0,0.0f); + colours->set(1.0f,1.0f,1.0,1.0f); gset->setColors(colours); gset->setColorBinding(osg::GeoSet::BIND_OVERALL); @@ -207,7 +183,7 @@ Geode* osg::createGeodeForImage(osg::Image* image,float s,float t) // set up the geode. osg::Geode* geode = new osg::Geode; - geode->addGeoSet(gset); + geode->addDrawable(gset); return geode; diff --git a/src/osg/LOD.cpp b/src/osg/LOD.cpp index 69c0cee35..3dc1ec92c 100644 --- a/src/osg/LOD.cpp +++ b/src/osg/LOD.cpp @@ -1,30 +1,26 @@ #include "osg/LOD" -#include "osg/Input" -#include "osg/Output" -#include "osg/Registry" #include using namespace osg; -RegisterObjectProxy g_LODProxy; - void LOD::traverse(NodeVisitor& nv) { - switch(nv.getTraverseMode()) + switch(nv.getTraversalMode()) { - case(NodeVisitor::TRAVERSE_ALL_CHILDREN): - std::for_each(_children.begin(),_children.end(),NodeAcceptOp(nv)); - break; - case(NodeVisitor::TRAVERSE_ACTIVE_CHILDREN): - if (_children.size()!=0) _children.front()->accept(nv); - break; - default: - break; + case(NodeVisitor::TRAVERSE_ALL_CHILDREN): + std::for_each(_children.begin(),_children.end(),NodeAcceptOp(nv)); + break; + case(NodeVisitor::TRAVERSE_ACTIVE_CHILDREN): + if (_children.size()!=0) _children.front()->accept(nv); + break; + default: + break; } } -void LOD::setRange(unsigned int index, float range) + +void LOD::setRange(const unsigned int index, const float range) { if (index<_rangeList.size()) _rangeList[index] = range; else while (index>=_rangeList.size()) _rangeList.push_back(range); @@ -33,98 +29,23 @@ void LOD::setRange(unsigned int index, float range) else while (index>=_rangeList2.size()) _rangeList2.push_back(range*range); } -int LOD::evaluate(const Vec3& eye_local, float bias) + +const int LOD::evaluate(const Vec3& eye_local, const float bias) const { - // For cache coherency, use _rangeList2 exclusively + // For cache coherency, use _rangeList2 exclusively if (_rangeList2.size()==0) return -1; - // Test distance-squared against the stored array of squared ranges + // Test distance-squared against the stored array of squared ranges float LODRange = (eye_local-_center).length2()*bias; if (LODRange<_rangeList2[0]) return -1; - + for(unsigned int i=0;i<_rangeList2.size()-1;++i) { - if (_rangeList2[i]<=LODRange && LODRange<_rangeList2[i+1]) { + if (_rangeList2[i]<=LODRange && LODRange<_rangeList2[i+1]) + { return i; } } return -1; } -bool LOD::readLocalData(Input& fr) -{ - bool iteratorAdvanced = false; - - if (fr.matchSequence("Center %f %f %f")) - { - - fr[1].getFloat(_center[0]); - fr[2].getFloat(_center[1]); - fr[3].getFloat(_center[2]); - - iteratorAdvanced = true; - fr+=3; - } - - bool matchFirst = false; - if ((matchFirst=fr.matchSequence("Ranges {")) || fr.matchSequence("Ranges %i {")) - { - - // set up coordinates. - int entry = fr[0].getNoNestedBrackets(); - - if (matchFirst) - { - fr += 2; - } - else - { - //_rangeList.(capacity); - fr += 3; - } - - float range; - while (!fr.eof() && fr[0].getNoNestedBrackets()>entry) - { - if (fr[0].getFloat(range)) - { - ++fr; - _rangeList.push_back(range); - _rangeList2.push_back(range*range); - } - else - { - ++fr; - } - } - - iteratorAdvanced = true; - ++fr; - - } - - if (Group::readLocalData(fr)) iteratorAdvanced = true; - - return iteratorAdvanced; -} - - -bool LOD::writeLocalData(Output& fw) -{ - fw.indent() << "Center "<<_center[0] << " "<<_center[1] << " "<<_center[2] < s_Light(new Light); - return s_Light.get(); -} void Light::init( void ) { @@ -49,6 +44,7 @@ void Light::init( void ) _quadratic_attenuation = 0.0f; } + void Light::captureLightState() { glGetLightfv( (GLenum)((int)GL_LIGHT0 + _lightnum), GL_AMBIENT, _ambient.ptr() ); @@ -63,23 +59,11 @@ void Light::captureLightState() glGetLightfv( (GLenum)((int)GL_LIGHT0 + _lightnum), GL_QUADRATIC_ATTENUATION, &_quadratic_attenuation ); } - -void Light::enable( void ) -{ - glEnable( GL_LIGHTING ); -} - - -void Light::disable( void ) -{ - glDisable( GL_LIGHTING ); -} - - -void Light::apply( void ) +void Light::apply(State&) const { if( _on ) { + // note state should probably be handling the glEnable... glEnable ( (GLenum)((int)GL_LIGHT0 + _lightnum) ); glLightfv( (GLenum)((int)GL_LIGHT0 + _lightnum), GL_AMBIENT, _ambient.ptr() ); glLightfv( (GLenum)((int)GL_LIGHT0 + _lightnum), GL_DIFFUSE, _diffuse.ptr() ); diff --git a/src/osg/LightSource.cpp b/src/osg/LightSource.cpp index f750bcc56..5052ea4dd 100644 --- a/src/osg/LightSource.cpp +++ b/src/osg/LightSource.cpp @@ -1,13 +1,7 @@ #include "osg/LightSource" -#include "osg/Input" -#include "osg/Output" - -#include "osg/Registry" using namespace osg; -RegisterObjectProxy g_LightSourceProxy; - LightSource::LightSource() { _bsphere_computed = false; @@ -19,41 +13,13 @@ LightSource::~LightSource() // ref_ptr<> automactially decrements the reference count of attached lights. } - -bool LightSource::readLocalData(Input& fr) +const bool LightSource::computeBound() const { - - bool iteratorAdvanced = false; - - if (Node::readLocalData(fr)) iteratorAdvanced = true; - - Light* light = static_cast(Light::instance()->readClone(fr)); - if (light) - { - _light = light; - iteratorAdvanced = true; - } - - return iteratorAdvanced; -} - - -bool LightSource::writeLocalData(Output& fw) -{ - Node::writeLocalData(fw); - - if (_light.valid()) _light->write(fw); - - return true; -} - -bool LightSource::computeBound( void ) -{ // note, don't do anything right now as the light itself is not // visualised, just having an effect on the lighting of geodes. _bsphere.init(); - + _bsphere_computed = true; - return true; + return true; } diff --git a/src/osg/Makefile b/src/osg/Makefile index 2362a670f..965d3979b 100644 --- a/src/osg/Makefile +++ b/src/osg/Makefile @@ -2,55 +2,51 @@ include ../../Make/makedefs C++FILES = \ - Registry.cpp\ - OSG.cpp\ AlphaFunc.cpp\ - Group.cpp\ - Field.cpp\ - FieldReader.cpp\ - FieldReaderIterator.cpp\ + Billboard.cpp\ + BoundingBox.cpp\ + BoundingSphere.cpp\ + Camera.cpp\ + ClipPlane.cpp \ + ColorMask.cpp \ + CullFace.cpp\ + Depth.cpp \ + Drawable.cpp\ + Fog.cpp\ + FrontFace.cpp\ + Geode.cpp\ GeoSet.cpp\ GeoSet_ogl.cpp\ - GeoState.cpp\ - Geode.cpp\ - Input.cpp\ - FileNameUtils.cpp\ + GLExtensions.cpp\ + Group.cpp\ + Image.cpp\ + Impostor.cpp\ + ImpostorSprite.cpp\ Light.cpp\ LightSource.cpp\ - Lighting.cpp\ + LineSegment.cpp\ + LOD.cpp\ Material.cpp\ Matrix.cpp\ - Quat.cpp\ - Seg.cpp\ Node.cpp\ NodeVisitor.cpp\ + Notify.cpp\ Object.cpp\ - Output.cpp\ - DynamicLibrary.cpp\ + Point.cpp\ + PolygonMode.cpp\ + PolygonOffset.cpp\ + Quat.cpp\ + State.cpp\ + StateSet.cpp\ + Stencil.cpp \ + Switch.cpp\ TexEnv.cpp\ TexGen.cpp\ - Image.cpp\ - Texture.cpp\ - DCS.cpp\ - Scene.cpp\ - Switch.cpp\ - Sequence.cpp\ - LOD.cpp\ - Billboard.cpp\ - BoundingSphere.cpp\ - BoundingBox.cpp\ - Transparency.cpp\ - CullFace.cpp\ TexMat.cpp\ + Texture.cpp\ Timer.cpp\ - Fog.cpp\ - ReaderWriterOSG.cpp\ - ReaderWriterRGB.cpp\ - Camera.cpp\ - Notify.cpp\ - ExtensionSupported.cpp\ - Point.cpp\ - PolygonOffset.cpp\ + Transform.cpp\ + Transparency.cpp\ Version.cpp\ @@ -63,56 +59,61 @@ TARGET_INCLUDE_FILES = \ osg/Billboard\ osg/BoundingBox\ osg/BoundingSphere\ + osg/BoundsChecking\ osg/Camera\ + osg/ClipPlane\ + osg/ClippingVolume\ + osg/ColorMask\ osg/CullFace\ - osg/DCS\ - osg/DynamicLibrary\ + osg/Depth\ + osg/Drawable\ osg/Export\ - osg/Field\ - osg/FieldReader\ - osg/FieldReaderIterator\ - osg/FileNameUtils\ osg/Fog\ + osg/FrontFace\ + osg/GL\ + osg/GLExtensions\ osg/GeoSet\ - osg/GeoState\ osg/Geode\ osg/Group\ - osg/GL\ osg/Image\ - osg/Input\ + osg/Impostor\ + osg/ImpostorSprite\ osg/LOD\ osg/Light\ osg/LightSource\ - osg/Lighting\ + osg/LineSegment\ osg/Material\ osg/Matrix\ + osg/MemoryAdapter\ osg/Node\ - osg/Notify\ osg/NodeVisitor\ - osg/OSG\ + osg/Notify\ osg/Object\ - osg/Output\ osg/Point\ + osg/PolygonMode\ osg/PolygonOffset\ + osg/Plane\ osg/Quat\ osg/Referenced\ - osg/Registry\ - osg/Scene\ - osg/Seg\ - osg/Sequence\ osg/State\ + osg/StateAttribute\ + osg/StateSet\ + osg/Stencil\ osg/Switch\ osg/TexEnv\ osg/TexGen\ osg/TexMat\ osg/Texture\ - osg/Transparency\ osg/Timer\ + osg/Transform\ + osg/Transparency\ osg/Types\ osg/Vec2\ osg/Vec3\ osg/Vec4\ osg/Version\ + osg/mem_ptr\ + osg/ref_ptr\ TARGET_DATA_FILES = \ @@ -137,7 +138,7 @@ TARGET_DATA_FILES = \ Images/white.rgb\ -LIBS = -ldl +LIBS = -lGLU -lGL -lm LIB = ../../lib/lib$(TARGET_BASENAME).so #LIB = ../../lib/lib$(TARGET_BASENAME).a diff --git a/src/osg/Material.cpp b/src/osg/Material.cpp index b95199298..6b441aea4 100644 --- a/src/osg/Material.cpp +++ b/src/osg/Material.cpp @@ -1,11 +1,9 @@ #include "osg/Material" -#include "osg/Input" -#include "osg/Output" -#include "osg/Notify" +#include "osg/BoundsChecking" using namespace osg; -Material::Material( void ) +Material::Material() { _colorMode = OFF; @@ -31,467 +29,309 @@ Material::Material( void ) } -Material::~Material( void ) +Material::~Material() { } -Material* Material::instance() +void Material::setAmbient( const Face face, const Vec4& ambient ) { - static ref_ptr s_Material(new Material); - return s_Material.get(); -} - -void Material::setAmbient( MaterialFace face, const Vec4& ambient ) -{ - switch(face) { - case(FACE_FRONT): - _ambientFrontAndBack = false; - _ambientFront = ambient; - break; - case(FACE_BACK): - _ambientFrontAndBack = false; - _ambientBack = ambient; - break; - case(FACE_FRONT_AND_BACK): - _ambientFrontAndBack = true; - _ambientFront = ambient; - _ambientBack = ambient; - break; - default: - notify(NOTICE)<<"Notice: invalid MaterialFace passed to Material::setAmbient()."< -#include "osg/Matrix" -#include "osg/Input" -#include "osg/Output" -#include "osg/Notify" +#include + +#include +#include +#include +#include #define square(x) ((x)*(x)) #define DEG2RAD(x) ((x)*M_PI/180.0) +#define RAD2DEG(x) ((x)*180.0/M_PI) using namespace osg; @@ -51,7 +54,7 @@ typedef struct quaternion_ static void quaternion_matrix( quaternion *q, double mat[4][4] ) { -/* copied from Shoemake/ACM SIGGRAPH 89 */ + /* copied from Shoemake/ACM SIGGRAPH 89 */ double xs, ys, zs, wx, wy, wz, xx, xy, xz, yy, yz, zz ; xs = q->x + q->x; @@ -136,50 +139,6 @@ Matrix::~Matrix() } -Matrix* Matrix::instance() -{ - static ref_ptr s_matrix(new Matrix()); - return s_matrix.get(); -} - - -bool Matrix::readLocalData(Input& fr) -{ - bool iteratorAdvanced = false; - bool matched = true; - for(int k=0;k<16 && matched;++k) - { - matched = fr[k].isFloat(); - } - if (matched) - { - int k=0; - for(int i=0;i<4;++i) - { - for(int j=0;j<4;++j) - { - fr[k].getFloat(_mat[i][j]); - k++; - } - } - fr += 16; - iteratorAdvanced = true; - } - - return iteratorAdvanced; -} - - -bool Matrix::writeLocalData(Output& fw) -{ - fw.indent() << _mat[0][0] << " " << _mat[0][1] << " " << _mat[0][2] << " " << _mat[0][3] << endl; - fw.indent() << _mat[1][0] << " " << _mat[1][1] << " " << _mat[1][2] << " " << _mat[1][3] << endl; - fw.indent() << _mat[2][0] << " " << _mat[2][1] << " " << _mat[2][2] << " " << _mat[2][3] << endl; - fw.indent() << _mat[3][0] << " " << _mat[3][1] << " " << _mat[3][2] << " " << _mat[3][3] << endl; - return true; -} - - void Matrix::makeIdent() { _mat[0][0] = 1.0f; @@ -203,11 +162,63 @@ void Matrix::makeIdent() _mat[3][3] = 1.0f; } +void Matrix::set(const float* m) +{ + _mat[0][0] = m[0]; + _mat[0][1] = m[1]; + _mat[0][2] = m[2]; + _mat[0][3] = m[3]; + + _mat[1][0] = m[4]; + _mat[1][1] = m[5]; + _mat[1][2] = m[6]; + _mat[1][3] = m[7]; + + _mat[2][0] = m[8]; + _mat[2][1] = m[9]; + _mat[2][2] = m[10]; + _mat[2][3] = m[11]; + + _mat[3][0] = m[12]; + _mat[3][1] = m[13]; + _mat[3][2] = m[14]; + _mat[3][3] = m[15]; +} + + +void Matrix::set( + float a00, float a01, float a02, float a03, + float a10, float a11, float a12, float a13, + float a20, float a21, float a22, float a23, + float a30, float a31, float a32, float a33) +{ + _mat[0][0] = a00; + _mat[0][1] = a01; + _mat[0][2] = a02; + _mat[0][3] = a03; + + _mat[1][0] = a10; + _mat[1][1] = a11; + _mat[1][2] = a12; + _mat[1][3] = a13; + + _mat[2][0] = a20; + _mat[2][1] = a21; + _mat[2][2] = a22; + _mat[2][3] = a23; + + _mat[3][0] = a30; + _mat[3][1] = a31; + _mat[3][2] = a32; + _mat[3][3] = a33; +} + void Matrix::copy(const Matrix& matrix) { memcpy(_mat,matrix._mat,sizeof(_mat)); } + void Matrix::makeScale(float sx, float sy, float sz) { makeIdent(); @@ -224,6 +235,7 @@ void Matrix::preScale( float sx, float sy, float sz, const Matrix& m ) mult(transMat,m); } + void Matrix::postScale( const Matrix& m, float sx, float sy, float sz ) { Matrix transMat; @@ -231,6 +243,7 @@ void Matrix::postScale( const Matrix& m, float sx, float sy, float sz ) mult(m,transMat); } + void Matrix::preScale( float sx, float sy, float sz ) { Matrix transMat; @@ -238,6 +251,7 @@ void Matrix::preScale( float sx, float sy, float sz ) preMult(transMat); } + void Matrix::postScale( float sx, float sy, float sz ) { Matrix transMat; @@ -246,8 +260,6 @@ void Matrix::postScale( float sx, float sy, float sz ) } - - void Matrix::makeTrans( float tx, float ty, float tz ) { makeIdent(); @@ -256,6 +268,7 @@ void Matrix::makeTrans( float tx, float ty, float tz ) _mat[3][2] = tz; } + void Matrix::preTrans( float tx, float ty, float tz, const Matrix& m ) { Matrix transMat; @@ -263,6 +276,7 @@ void Matrix::preTrans( float tx, float ty, float tz, const Matrix& m ) mult(transMat,m); } + void Matrix::postTrans( const Matrix& m, float tx, float ty, float tz ) { Matrix transMat; @@ -270,6 +284,7 @@ void Matrix::postTrans( const Matrix& m, float tx, float ty, float tz ) mult(m,transMat); } + void Matrix::preTrans( float tx, float ty, float tz ) { _mat[3][0] = (tx * _mat[0][0]) + (ty * _mat[1][0]) + (tz * _mat[2][0]) + _mat[3][0]; @@ -278,6 +293,7 @@ void Matrix::preTrans( float tx, float ty, float tz ) _mat[3][3] = (tx * _mat[0][3]) + (ty * _mat[1][3]) + (tz * _mat[2][3]) + _mat[3][3]; } + void Matrix::postTrans( float tx, float ty, float tz ) { Matrix transMat; @@ -285,6 +301,21 @@ void Matrix::postTrans( float tx, float ty, float tz ) postMult(transMat); } +void Matrix::makeRot( const Vec3& old_vec, const Vec3& new_vec ) +{ + /* dot product == cos(angle old_vec<>new_vec). */ + double d = new_vec * old_vec; + if ( d < 0.9999 ) + { + double angle = acos( d ); + Vec3 rot_axis = new_vec ^ old_vec; + makeRot( RAD2DEG(angle), + rot_axis.x(), rot_axis.y(), rot_axis.z() ); + } + else + makeIdent(); +} + void Matrix::makeRot( float deg, float x, float y, float z ) { double __mat[4][4]; @@ -313,6 +344,7 @@ void Matrix::makeRot( float deg, float x, float y, float z ) } } + void Matrix::preRot( float deg, float x, float y, float z, const Matrix& m ) { Matrix rotMat; @@ -320,6 +352,7 @@ void Matrix::preRot( float deg, float x, float y, float z, const Matrix& m ) mult(rotMat,m); } + void Matrix::postRot( const Matrix& m, float deg, float x, float y, float z ) { Matrix rotMat; @@ -327,6 +360,7 @@ void Matrix::postRot( const Matrix& m, float deg, float x, float y, float z ) mult(m,rotMat); } + void Matrix::preRot( float deg, float x, float y, float z ) { quaternion q; @@ -351,6 +385,7 @@ void Matrix::preRot( float deg, float x, float y, float z ) memcpy( _mat, res_mat, sizeof( _mat ) ); } + void Matrix::postRot( float deg, float x, float y, float z ) { quaternion q; @@ -375,12 +410,15 @@ void Matrix::postRot( float deg, float x, float y, float z ) memcpy( _mat, res_mat, sizeof( _mat ) ); } + void Matrix::setTrans( float tx, float ty, float tz ) { _mat[3][0] = tx; - _mat[3][1] = ty; + _mat[3][1] = ty; _mat[3][2] = tz; } + + void Matrix::setTrans( const Vec3& v ) { _mat[3][0] = v[0]; @@ -388,6 +426,7 @@ void Matrix::setTrans( const Vec3& v ) _mat[3][2] = v[2]; } + void Matrix::preMult(const Matrix& m) { Matrix tm; @@ -395,6 +434,7 @@ void Matrix::preMult(const Matrix& m) *this = tm; } + void Matrix::postMult(const Matrix& m) { Matrix tm; @@ -402,25 +442,41 @@ void Matrix::postMult(const Matrix& m) *this = tm; } + void Matrix::mult(const Matrix& lhs,const Matrix& rhs) { - matrix_mult( lhs._mat, rhs._mat, _mat ); + if (&lhs==this || &rhs==this) + { + osg::Matrix tm; + matrix_mult( lhs._mat, rhs._mat, tm._mat ); + *this = tm; + } + else + { + matrix_mult( lhs._mat, rhs._mat, _mat ); + } } + Matrix Matrix::operator * (const Matrix& m) const { - Matrix nm; - matrix_mult( _mat,m._mat, nm._mat ); - return nm; + Matrix tm; + matrix_mult( _mat,m._mat, tm._mat ); + return tm; } -bool Matrix::invert(const Matrix& _m) +bool Matrix::invert(const Matrix& invm) { + if (&invm==this) { + Matrix tm(invm); + return invert(tm); + } + // code lifted from VR Juggler. // not cleanly added, but seems to work. RO. - const float* a = reinterpret_cast(_m._mat); + const float* a = reinterpret_cast(invm._mat); float* b = reinterpret_cast(_mat); int n = 4; @@ -428,14 +484,14 @@ bool Matrix::invert(const Matrix& _m) int r[ 4], c[ 4], row[ 4], col[ 4]; float m[ 4][ 4*2], pivot, max_m, tmp_m, fac; -/* Initialization */ + /* Initialization */ for ( i = 0; i < n; i ++ ) { r[ i] = c[ i] = 0; row[ i] = col[ i] = 0; } -/* Set working matrix */ + /* Set working matrix */ for ( i = 0; i < n; i++ ) { for ( j = 0; j < n; j++ ) @@ -445,10 +501,10 @@ bool Matrix::invert(const Matrix& _m) } } -/* Begin of loop */ + /* Begin of loop */ for ( k = 0; k < n; k++ ) { -/* Choosing the pivot */ + /* Choosing the pivot */ for ( i = 0, max_m = 0; i < n; i++ ) { if ( row[ i] ) continue; @@ -470,11 +526,11 @@ bool Matrix::invert(const Matrix& _m) if ( fabs( pivot) <= 1e-20) { notify(WARN) << "*** pivot = %f in mat_inv. ***\n"; -//exit( 0); + //exit( 0); return false; } -/* Normalization */ + /* Normalization */ for ( j = 0; j < 2*n; j++ ) { if ( j == c[ k] ) @@ -483,7 +539,7 @@ bool Matrix::invert(const Matrix& _m) m[ r[ k]][ j] /=pivot; } -/* Reduction */ + /* Reduction */ for ( i = 0; i < n; i++ ) { if ( i == r[ k] ) @@ -499,7 +555,7 @@ bool Matrix::invert(const Matrix& _m) } } -/* Assign invers to a matrix */ + /* Assign invers to a matrix */ for ( i = 0; i < n; i++ ) for ( j = 0; j < n; j++ ) row[ i] = ( c[ j] == i ) ? r[j] : row[ i]; @@ -508,5 +564,5 @@ bool Matrix::invert(const Matrix& _m) for ( j = 0; j < n; j++ ) b[ i * n + j] = m[ row[ i]][j + n]; - return true; // It worked + return true; // It worked } diff --git a/src/osg/Node.cpp b/src/osg/Node.cpp index d6a069cc1..01a0519d7 100644 --- a/src/osg/Node.cpp +++ b/src/osg/Node.cpp @@ -2,18 +2,12 @@ #include "osg/Group" #include "osg/NodeVisitor" -#include "osg/Input" -#include "osg/Output" - -#include "osg/Registry" #include "osg/Notify" #include using namespace osg; -RegisterObjectProxy g_NodeProxy; - Node::Node() { _bsphere_computed = false; @@ -24,7 +18,7 @@ Node::Node() Node::~Node() { - if (_userData && _memoryAdapter.valid()) _memoryAdapter->decrementReference(_userData); + if (_userData && _memoryAdapter.valid()) _memoryAdapter->unref_data(_userData); } @@ -33,122 +27,18 @@ void Node::accept(NodeVisitor& nv) nv.apply(*this); } + void Node::ascend(NodeVisitor& nv) { std::for_each(_parents.begin(),_parents.end(),NodeAcceptOp(nv)); } -bool Node::readLocalData(Input& fr) -{ - bool iteratorAdvanced = false; - - if (Object::readLocalData(fr)) iteratorAdvanced = true; - - if (fr.matchSequence("name %s")) - { - _name = fr[1].takeStr(); - fr+=2; - iteratorAdvanced = true; - } - -// if (fr.matchSequence("user_data {")) -// { -// notify(DEBUG) << "Matched user_data {"<entry) -// { -// Object* object = fr.readObject(); -// if (object) setUserData(object); -// notify(DEBUG) << "read "<entry) - { - _descriptions.push_back(fr[0].getStr()); - notify(DEBUG) << "read "<<_descriptions.back()<(_userData); -// if (object) -// { -// fw.indent() << "user_data {"<write(fw); -// fw.moveOut(); -// fw.indent() << "}"<dirtyBound(); } diff --git a/src/osg/NodeVisitor.cpp b/src/osg/NodeVisitor.cpp index 664d3de22..72b87a3ae 100644 --- a/src/osg/NodeVisitor.cpp +++ b/src/osg/NodeVisitor.cpp @@ -5,36 +5,37 @@ using namespace osg; NodeVisitor::NodeVisitor(TraversalMode tm) { - _traverseVisitor = NULL; - _traverseMode = tm; + _traversalVisitor = NULL; + _traversalMode = tm; } + NodeVisitor::~NodeVisitor() { - // if (_traverseVisitor) detach from _traverseVisitor; + // if (_traversalVisitor) detach from _traversalVisitor; } -void NodeVisitor::setTraverseMode(TraversalMode mode) + +void NodeVisitor::setTraversalMode(const TraversalMode mode) { - if (_traverseMode==mode) return; + if (_traversalMode==mode) return; if (mode==TRAVERSE_VISITOR) { - if (_traverseVisitor==NULL) _traverseMode = TRAVERSE_NONE; - else _traverseMode = TRAVERSE_VISITOR; + if (_traversalVisitor==NULL) _traversalMode = TRAVERSE_NONE; + else _traversalMode = TRAVERSE_VISITOR; } else { - if (_traverseVisitor) _traverseVisitor=NULL; - _traverseMode = mode; + if (_traversalVisitor.valid()) _traversalVisitor=NULL; + _traversalMode = mode; } } -void NodeVisitor::setTraverseVisitor(NodeVisitor* nv) + +void NodeVisitor::setTraversalVisitor(NodeVisitor* nv) { - if (_traverseVisitor==nv) return; - // if (_traverseVisitor) detach from _traverseVisitor; - _traverseVisitor = nv; - if (_traverseVisitor) _traverseMode = TRAVERSE_VISITOR; - else _traverseMode = TRAVERSE_NONE; - // attach to _traverseVisitor; + if (_traversalVisitor==nv) return; + _traversalVisitor = nv; + if (_traversalVisitor.valid()) _traversalMode = TRAVERSE_VISITOR; + else _traversalMode = TRAVERSE_NONE; } diff --git a/src/osg/Notify.cpp b/src/osg/Notify.cpp index d30ddad4e..c0ec13144 100644 --- a/src/osg/Notify.cpp +++ b/src/osg/Notify.cpp @@ -1,87 +1,60 @@ #include "osg/Notify" #include -using namespace osg; +osg::NotifySeverity osg::g_NotifyLevel = osg::NOTICE; -int osg::NotifyInit::count_ = 0; -NotifySeverity osg::g_NotifyLevel = osg::NOTICE; -ofstream *osg::g_absorbStreamPtr = NULL; - -void osg::setNotifyLevel(NotifySeverity severity) +void osg::setNotifyLevel(osg::NotifySeverity severity) { - g_NotifyLevel = severity; + osg::initNotifyLevel(); + g_NotifyLevel = severity; } -int osg::getNotifyLevel() + +osg::NotifySeverity osg::getNotifyLevel() { + osg::initNotifyLevel(); return g_NotifyLevel; } -#ifndef WIN32 -ostream& osg::notify(NotifySeverity severity) + +bool osg::initNotifyLevel() { - if (severity<=g_NotifyLevel || g_absorbStreamPtr==NULL) + static bool s_local_intialized = false; + + if (s_local_intialized) return true; + + s_local_intialized = true; + + // g_NotifyLevel + // ============= + + g_NotifyLevel = osg::NOTICE; // Default value + + char *OSGNOTIFYLEVEL=getenv("OSGNOTIFYLEVEL"); + if(OSGNOTIFYLEVEL) { - if (severity<=osg::WARN) return cerr; - else return cout; - } - return *g_absorbStreamPtr; -} -#endif -NotifyInit::NotifyInit() -{ - if (count_++ == 0) { + std::string stringOSGNOTIFYLEVEL(OSGNOTIFYLEVEL); - // g_NotifyLevel - // ============= - - g_NotifyLevel = osg::NOTICE; // Default value - - char *OSGNOTIFYLEVEL=getenv("OSGNOTIFYLEVEL"); - if(OSGNOTIFYLEVEL){ - - std::string stringOSGNOTIFYLEVEL(OSGNOTIFYLEVEL); - - // Convert to upper case - for(std::string::iterator i=stringOSGNOTIFYLEVEL.begin(); - i!=stringOSGNOTIFYLEVEL.end(); - ++i) *i=toupper(*i); - - if(stringOSGNOTIFYLEVEL.find("ALWAYS")!=std::string::npos) g_NotifyLevel=osg::ALWAYS; - else if(stringOSGNOTIFYLEVEL.find("FATAL")!=std::string::npos) g_NotifyLevel=osg::FATAL; - else if(stringOSGNOTIFYLEVEL.find("WARN")!=std::string::npos) g_NotifyLevel=osg::WARN; - else if(stringOSGNOTIFYLEVEL.find("NOTICE")!=std::string::npos) g_NotifyLevel=osg::NOTICE; - else if(stringOSGNOTIFYLEVEL.find("INFO")!=std::string::npos) g_NotifyLevel=osg::INFO; - else if(stringOSGNOTIFYLEVEL.find("DEBUG")!=std::string::npos) g_NotifyLevel=osg::DEBUG; - else if(stringOSGNOTIFYLEVEL.find("FP_DEBUG")!=std::string::npos) g_NotifyLevel=osg::FP_DEBUG; - - } - - // g_absorbStreamPtr - // ================= - - char *OSGNOTIFYABSORBFILE=getenv("OSGNOTIFYABSORBFILE"); - if (OSGNOTIFYABSORBFILE) + // Convert to upper case + for(std::string::iterator i=stringOSGNOTIFYLEVEL.begin(); + i!=stringOSGNOTIFYLEVEL.end(); + ++i) { - g_absorbStreamPtr=new ofstream(OSGNOTIFYABSORBFILE); + *i=toupper(*i); } - else - { -#ifdef WIN32 - // What's the Windows equivalent of /dev/null? - g_absorbStreamPtr=new ofstream("C:/Windows/Tmp/osg.log"); -#else - g_absorbStreamPtr=new ofstream("/dev/null"); -#endif - } - } -} -NotifyInit::~NotifyInit() -{ - if(--count_ == 0) { - delete g_absorbStreamPtr; - g_absorbStreamPtr=NULL; + if(stringOSGNOTIFYLEVEL.find("ALWAYS")!=std::string::npos) g_NotifyLevel=osg::ALWAYS; + else if(stringOSGNOTIFYLEVEL.find("FATAL")!=std::string::npos) g_NotifyLevel=osg::FATAL; + else if(stringOSGNOTIFYLEVEL.find("WARN")!=std::string::npos) g_NotifyLevel=osg::WARN; + else if(stringOSGNOTIFYLEVEL.find("NOTICE")!=std::string::npos) g_NotifyLevel=osg::NOTICE; + else if(stringOSGNOTIFYLEVEL.find("INFO")!=std::string::npos) g_NotifyLevel=osg::INFO; + else if(stringOSGNOTIFYLEVEL.find("DEBUG_INFO")!=std::string::npos) g_NotifyLevel=osg::DEBUG_INFO; + else if(stringOSGNOTIFYLEVEL.find("DEBUG_FP")!=std::string::npos) g_NotifyLevel=osg::DEBUG_FP; + else if(stringOSGNOTIFYLEVEL.find("DEBUG")!=std::string::npos) g_NotifyLevel=osg::DEBUG_INFO; + } + + return true; + } diff --git a/src/osg/Object.cpp b/src/osg/Object.cpp index 9c1498284..1b5d2dd28 100644 --- a/src/osg/Object.cpp +++ b/src/osg/Object.cpp @@ -1,78 +1,5 @@ #include "osg/Object" -#include "osg/Registry" -#include "osg/Input" -#include "osg/Output" using namespace osg; -Object* Object::readClone(Input& fr) -{ - if (fr[0].matchWord("Use")) - { - if (fr[1].isString()) - { - Object* obj = fr.getObjectForUniqueID(fr[1].getStr()); - if (obj && isSameKindAs(obj)) - { - fr+=2; - return obj; - } - } - return NULL; - - } - - if (!fr[0].matchWord(className()) || - !fr[1].isOpenBracket()) return NULL; - - int entry = fr[0].getNoNestedBrackets(); - - Object* obj = clone(); - - fr+=2; - - while(!fr.eof() && fr[0].getNoNestedBrackets()>entry) - { - bool iteratorAdvanced = false; - if (fr[0].matchWord("UniqueID") && fr[1].isString()) { - fr.regisiterUniqueIDForObject(fr[1].getStr(),obj); - fr += 2; - } - if (obj->readLocalData(fr)) iteratorAdvanced = true; - if (!iteratorAdvanced) ++fr; - } - ++fr; // step over trailing '}' - - return obj; -} - - -bool Object::write(Output& fw) -{ - if (_refCount>1) { - std::string uniqueID; - if (fw.getUniqueIDForObject(this,uniqueID)) { - fw.indent() << "Use " << uniqueID << endl; - return true; - } - } - - fw.indent() << className() << " {"<1) { - std::string uniqueID; - fw.createUniqueIDForObject(this,uniqueID); - fw.registerUniqueIDForObject(this,uniqueID); - fw.indent() << "UniqueID " << uniqueID << endl; - } - - writeLocalData(fw); - - fw.moveOut(); - - fw.indent() << "}"< #endif #include "osg/GL" +#include "osg/GLExtensions" #include "osg/Point" -#include "osg/ExtensionSupported" -#include "osg/Input" -#include "osg/Output" - +#include "osg/Notify" using namespace osg; +// if extensions not defined by gl.h (or via glext.h) define them +// ourselves and allow the extensions to detectd at runtine using +// osg::isGLExtensionSupported(). #if defined(GL_SGIS_point_parameters) && !defined(GL_EXT_point_parameters) /* Use the EXT point parameters interface for the SGIS implementation. */ # define GL_POINT_SIZE_MIN_EXT GL_POINT_SIZE_MIN_SGIS # define GL_POINT_SIZE_MAX_EXT GL_POINT_SIZE_MAX_SGIS # define GL_POINT_FADE_THRESHOLD_SIZE_EXT GL_POINT_FADE_THRESHOLD_SIZE_SGIS # define GL_DISTANCE_ATTENUATION_EXT GL_DISTANCE_ATTENUATION_SGIS -# define glPointParameterfEXT glPointParameterfSGIS -# define glPointParameterfvEXT glPointParameterfvSGIS # define GL_EXT_point_parameters 1 #endif @@ -30,91 +29,73 @@ using namespace osg; # define GL_POINT_SIZE_MAX_EXT 0x8127 # define GL_POINT_FADE_THRESHOLD_SIZE_EXT 0x8128 # define GL_DISTANCE_ATTENUATION_EXT 0x8129 -# ifdef _WIN32 - // Curse Microsoft for the insanity of wglGetProcAddress. - typedef void (APIENTRY * PFNGLPOINTPARAMETERFEXTPROC) (GLenum pname, GLfloat param); - typedef void (APIENTRY * PFNGLPOINTPARAMETERFVEXTPROC) (GLenum pname, const GLfloat *params); -# define GL_EXT_point_parameters 1 -# endif +# define GL_EXT_point_parameters 1 #endif -#ifdef _WIN32 - PFNGLPOINTPARAMETERFEXTPROC glPointParameterfEXT; - PFNGLPOINTPARAMETERFVEXTPROC glPointParameterfvEXT; +#ifndef PFNGLPOINTPARAMETERFEXTPROC +typedef void (APIENTRY * PFNGLPOINTPARAMETERFEXTPROC) (GLenum pname, GLfloat param); +#endif +#ifndef PFNGLPOINTPARAMETERFVEXTPROC +typedef void (APIENTRY * PFNGLPOINTPARAMETERFVEXTPROC) (GLenum pname, const GLfloat *params); #endif -static int s_hasPointParameters; +PFNGLPOINTPARAMETERFEXTPROC s_PointParameterfEXT = NULL; +PFNGLPOINTPARAMETERFVEXTPROC s_PointParameterfvEXT = NULL; - -Point::Point( void ) +Point::Point() { - _size = 1.0f; // TODO find proper default - _fadeThresholdSize = 1.0f; // TODO find proper default - _distanceAttenuation = Vec3(0.0f, 1.0f/5.f, 0.0f); // TODO find proper default + _size = 1.0f; // TODO find proper default + _fadeThresholdSize = 1.0f; // TODO find proper default + // TODO find proper default + _distanceAttenuation = Vec3(0.0f, 1.0f/5.f, 0.0f); } -Point::~Point( void ) +Point::~Point() { } - -Point* Point::instance() -{ - static ref_ptr s_point(new Point); - return s_point.get(); -} - - void Point::init_GL_EXT() { - s_hasPointParameters = - ExtensionSupported("GL_SGIS_point_parameters") || - ExtensionSupported("GL_EXT_point_parameters"); -#ifdef _WIN32 - if (s_hasPointParameters) + if (isGLExtensionSupported("GL_EXT_point_parameters")) { - glPointParameterfEXT = (PFNGLPOINTPARAMETERFEXTPROC) - wglGetProcAddress("glPointParameterfEXT"); - glPointParameterfvEXT = (PFNGLPOINTPARAMETERFVEXTPROC) - wglGetProcAddress("glPointParameterfvEXT"); + s_PointParameterfEXT = (PFNGLPOINTPARAMETERFEXTPROC) + getGLExtensionFuncPtr("glPointParameterfEXT"); + s_PointParameterfvEXT = (PFNGLPOINTPARAMETERFVEXTPROC) + getGLExtensionFuncPtr("glPointParameterfvEXT"); } -#endif + else if (isGLExtensionSupported("GL_SGIS_point_parameters")) + { + s_PointParameterfEXT = (PFNGLPOINTPARAMETERFEXTPROC) + getGLExtensionFuncPtr("glPointParameterfSGIS"); + s_PointParameterfvEXT = (PFNGLPOINTPARAMETERFVEXTPROC) + getGLExtensionFuncPtr("glPointParameterfvSGIS"); + } + } - -void Point::enableSmooth( void ) -{ - glEnable( GL_POINT_SMOOTH ); -} - - -void Point::disableSmooth( void ) -{ - glDisable( GL_POINT_SMOOTH ); -} - - -void Point::setSize( float size ) +void Point::setSize( const float size ) { _size = size; } -void Point::setFadeThresholdSize(float fadeThresholdSize) + +void Point::setFadeThresholdSize(const float fadeThresholdSize) { _fadeThresholdSize = fadeThresholdSize; } + void Point::setDistanceAttenuation(const Vec3& distanceAttenuation) { _distanceAttenuation = distanceAttenuation; } -void Point::apply( void ) + +void Point::apply(State&) const { glPointSize(_size); -#if GL_EXT_point_parameters static bool s_gl_ext_init=false; if (!s_gl_ext_init) @@ -123,56 +104,8 @@ void Point::apply( void ) init_GL_EXT(); } - if (s_hasPointParameters) - { - glPointParameterfvEXT(GL_DISTANCE_ATTENUATION_EXT, (const GLfloat*)&_distanceAttenuation); - glPointParameterfEXT(GL_POINT_FADE_THRESHOLD_SIZE_EXT, _fadeThresholdSize); - } -#endif + if (s_PointParameterfvEXT) s_PointParameterfvEXT(GL_DISTANCE_ATTENUATION_EXT, (const GLfloat*)&_distanceAttenuation); + if (s_PointParameterfEXT) s_PointParameterfEXT(GL_POINT_FADE_THRESHOLD_SIZE_EXT, _fadeThresholdSize); + } - -bool Point::readLocalData(Input& fr) -{ - bool iteratorAdvanced = false; - - float data; - if (fr[0].matchWord("size") && fr[1].getFloat(data)) - { - - _size = data; - fr+=2; - iteratorAdvanced = true; - } - - if (fr[0].matchWord("fade_threshold_size") && fr[1].getFloat(data)) - { - - _fadeThresholdSize = data; - fr+=2; - iteratorAdvanced = true; - } - - Vec3 distAtten; - if (fr[0].matchWord("distance_attenuation") && - fr[1].getFloat(distAtten[0]) && fr[2].getFloat(distAtten[1]) && fr[3].getFloat(distAtten[2])) - { - - _distanceAttenuation = distAtten; - fr+=4; - iteratorAdvanced = true; - } - - return iteratorAdvanced; -} - - -bool Point::writeLocalData(Output& fw) -{ - fw.indent() << "size " << _size << endl; - fw.indent() << "fade_threshold_size " << _fadeThresholdSize << endl; - fw.indent() << "distance_attenuation " << _distanceAttenuation << endl; - return true; -} - - diff --git a/src/osg/PolygonOffset.cpp b/src/osg/PolygonOffset.cpp index 01a19b0fc..740d47437 100644 --- a/src/osg/PolygonOffset.cpp +++ b/src/osg/PolygonOffset.cpp @@ -1,85 +1,20 @@ #include "osg/GL" #include "osg/PolygonOffset" -#include "osg/Input" -#include "osg/Output" using namespace osg; - -PolygonOffset::PolygonOffset( void ) +PolygonOffset::PolygonOffset() { - _factor = 0.0f; // are these sensible defaut values? + _factor = 0.0f; // are these sensible defaut values? _units = 0.0f; } -PolygonOffset::~PolygonOffset( void ) +PolygonOffset::~PolygonOffset() { } - -PolygonOffset* PolygonOffset::instance() -{ - static ref_ptr s_PolygonOffset(new PolygonOffset); - return s_PolygonOffset.get(); -} - -void PolygonOffset::setOffset(float factor,float units) -{ - _factor = factor; - _units = units; -} - -void PolygonOffset::enable( void ) -{ - glEnable( GL_POLYGON_OFFSET_FILL); - glEnable( GL_POLYGON_OFFSET_LINE); - glEnable( GL_POLYGON_OFFSET_POINT); -} - - -void PolygonOffset::disable( void ) -{ - glDisable( GL_POLYGON_OFFSET_FILL); - glDisable( GL_POLYGON_OFFSET_LINE); - glDisable( GL_POLYGON_OFFSET_POINT); -} - -void PolygonOffset::apply( void ) +void PolygonOffset::apply(State&) const { glPolygonOffset(_factor,_units); } - -bool PolygonOffset::readLocalData(Input& fr) -{ - bool iteratorAdvanced = false; - - float data; - if (fr[0].matchWord("factor") && fr[1].getFloat(data)) - { - - _factor = data; - fr+=2; - iteratorAdvanced = true; - } - - if (fr[0].matchWord("units") && fr[1].getFloat(data)) - { - - _units = data; - fr+=2; - iteratorAdvanced = true; - } - - return iteratorAdvanced; -} - - -bool PolygonOffset::writeLocalData(Output& fw) -{ - fw.indent() << "factor " << _factor << endl; - fw.indent() << "units " << _units << endl; - return true; -} - - diff --git a/src/osg/Quat.cpp b/src/osg/Quat.cpp index 395f57392..930f909ad 100644 --- a/src/osg/Quat.cpp +++ b/src/osg/Quat.cpp @@ -11,29 +11,13 @@ using namespace osg; -/// Default constructor is empty -Quat::Quat( void ) -{ -} - -/// Constructor with four floats - just call the constructor for the Vec4 -Quat::Quat( const float x, const float y, const float z, const float w ) -{ - _fv = Vec4( x, y, z, w ); -} - -/// Constructor with a Vec4 -Quat::Quat( const Vec4& vec ) -{ - _fv = vec; -} /// Set the elements of the Quat to represent a rotation of angle /// (radians) around the axis (x,y,z) void Quat::makeRot( const float angle, - const float x, - const float y, - const float z ) +const float x, +const float y, +const float z ) { float inversenorm = 1.0/sqrt( x*x + y*y + z*z ); float coshalfangle = cos( 0.5*angle ); @@ -45,11 +29,13 @@ void Quat::makeRot( const float angle, _fv[3] = coshalfangle; } + void Quat::makeRot( const float angle, const Vec3& vec ) { makeRot( angle, vec[0], vec[1], vec[2] ); } + // Make a rotation Quat which will rotate vec1 to vec2 // Generally take adot product to get the angle between these // and then use a cross product to get the rotation axis @@ -61,39 +47,41 @@ void Quat::makeRot( const Vec3& vec1, const Vec3& vec2 ) float length1 = vec1.length(); float length2 = vec2.length(); - float cosangle = vec1*vec2/(2*length1*length2); // dot product vec1*vec2 + + // dot product vec1*vec2 + float cosangle = vec1*vec2/(length1*length2); if ( fabs(cosangle - 1) < epsilon ) { - // cosangle is close to 1, so the vectors are close to being coincident - // Need to generate an angle of zero with any vector we like - // We'll choose (1,0,0) - makeRot( 0.0, 1.0, 0.0, 0.0 ); + // cosangle is close to 1, so the vectors are close to being coincident + // Need to generate an angle of zero with any vector we like + // We'll choose (1,0,0) + makeRot( 0.0, 1.0, 0.0, 0.0 ); } else if ( fabs(cosangle + 1) < epsilon ) { - // cosangle is close to -1, so the vectors are close to being opposite - // The angle of rotation is going to be Pi, but around which axis? - // Basically, any one perpendicular to vec1 = (x,y,z) is going to work. - // Choose a vector to cross product vec1 with. Find the biggest - // in magnitude of x, y and z and then put a zero in that position. - float biggest = fabs(vec1[0]); int bigposn = 0; - if ( fabs(vec1[1]) > biggest ) { biggest=fabs(vec1[1]); bigposn = 1; } - if ( fabs(vec1[2]) > biggest ) { biggest=fabs(vec1[2]); bigposn = 2; } - Vec3 temp = Vec3( 1.0, 1.0, 1.0 ); - temp[bigposn] = 0.0; - Vec3 axis = vec1^temp; // this is a cross-product to generate the - // axis around which to rotate - makeRot( (float)M_PI, axis ); + // cosangle is close to -1, so the vectors are close to being opposite + // The angle of rotation is going to be Pi, but around which axis? + // Basically, any one perpendicular to vec1 = (x,y,z) is going to work. + // Choose a vector to cross product vec1 with. Find the biggest + // in magnitude of x, y and z and then put a zero in that position. + float biggest = fabs(vec1[0]); int bigposn = 0; + if ( fabs(vec1[1]) > biggest ) { biggest=fabs(vec1[1]); bigposn = 1; } + if ( fabs(vec1[2]) > biggest ) { biggest=fabs(vec1[2]); bigposn = 2; } + Vec3 temp = Vec3( 1.0, 1.0, 1.0 ); + temp[bigposn] = 0.0; + Vec3 axis = vec1^temp; // this is a cross-product to generate the + // axis around which to rotate + makeRot( (float)M_PI, axis ); } else { - // This is the usual situation - take a cross-product of vec1 and vec2 - // and that is the axis around which to rotate. - Vec3 axis = vec1^vec2; - float angle = acos( cosangle ); - makeRot( angle, axis ); + // This is the usual situation - take a cross-product of vec1 and vec2 + // and that is the axis around which to rotate. + Vec3 axis = vec1^vec2; + float angle = acos( cosangle ); + makeRot( angle, axis ); } } @@ -112,10 +100,12 @@ void Quat::getRot( float& angle, Vec3& vec ) const /// if ( abs(coshalfangle) > 1.0 ) { error }; // *angle = atan2( sinhalfangle, coshalfangle ); // see man atan2 - angle = 2 * atan2( sinhalfangle, _fv[3] ); // -pi < angle < pi + // -pi < angle < pi + angle = 2 * atan2( sinhalfangle, _fv[3] ); vec = Vec3(_fv[0], _fv[1], _fv[2]) / sinhalfangle; } + void Quat::getRot( float& angle, float& x, float& y, float& z ) const { float sinhalfangle = sqrt( _fv[0]*_fv[0] + _fv[1]*_fv[1] + _fv[2]*_fv[2] ); @@ -137,34 +127,34 @@ void Quat::slerp( const float t, const Quat& from, const Quat& to ) const double epsilon = 0.00001; double omega, cosomega, sinomega, scale_from, scale_to ; - cosomega = from.asVec4() * to.asVec4() ; // this is a dot product + // this is a dot product + cosomega = from.asVec4() * to.asVec4() ; if( (1.0 - cosomega) > epsilon ) { - omega= acos(cosomega) ; // 0 <= omega <= Pi (see man acos) - sinomega = sin(omega) ; // this sinomega should always be +ve so - // could try sinomega=sqrt(1-cosomega*cosomega) to avoid a sin()? - scale_from = sin((1.0-t)*omega)/sinomega ; - scale_to = sin(t*omega)/sinomega ; + omega= acos(cosomega) ; // 0 <= omega <= Pi (see man acos) + sinomega = sin(omega) ; // this sinomega should always be +ve so + // could try sinomega=sqrt(1-cosomega*cosomega) to avoid a sin()? + scale_from = sin((1.0-t)*omega)/sinomega ; + scale_to = sin(t*omega)/sinomega ; } else { - /* -------------------------------------------------- - The ends of the vectors are very close - we can use simple linear interpolation - no need - to worry about the "spherical" interpolation - -------------------------------------------------- */ - scale_from = 1.0 - t ; - scale_to = t ; + /* -------------------------------------------------- + The ends of the vectors are very close + we can use simple linear interpolation - no need + to worry about the "spherical" interpolation + -------------------------------------------------- */ + scale_from = 1.0 - t ; + scale_to = t ; } - _fv = (from._fv*scale_from) + (to._fv*scale_to); // use Vec4 arithmetic - // so that we get a Vec4 + // use Vec4 arithmetic + _fv = (from._fv*scale_from) + (to._fv*scale_to); + // so that we get a Vec4 } - - #define QX _fv[0] #define QY _fv[1] #define QZ _fv[2] @@ -173,7 +163,7 @@ void Quat::slerp( const float t, const Quat& from, const Quat& to ) void Quat::set( const Matrix& m ) { // Source: Gamasutra, Rotating Objects Using Quaternions - // + // //http://www.gamasutra.com/features/programming/19980703/quaternions_01.htm float tr, s; @@ -196,7 +186,7 @@ void Quat::set( const Matrix& m ) } else { - // diagonal is negative + // diagonal is negative i = 0; if (m._mat[1][1] > m._mat[0][0]) i = 1; @@ -224,11 +214,10 @@ void Quat::set( const Matrix& m ) } - void Quat::get( Matrix& m ) const { // Source: Gamasutra, Rotating Objects Using Quaternions - // + // //http://www.gamasutra.com/features/programming/19980703/quaternions_01.htm float wx, wy, wz, xx, yy, yz, xy, xz, zz, x2, y2, z2; diff --git a/src/osg/Switch.cpp b/src/osg/Switch.cpp index 367dc6f43..bf5f39403 100644 --- a/src/osg/Switch.cpp +++ b/src/osg/Switch.cpp @@ -1,87 +1,41 @@ #include "osg/Switch" -#include "osg/Registry" -#include "osg/Input" -#include "osg/Output" #include using namespace osg; -RegisterObjectProxy g_SwitchProxy; - +/** + * Switch constructor. The default setting of _value is + * ALL_CHILDREN_OFF. + */ Switch::Switch() { _value = ALL_CHILDREN_OFF; } + void Switch::traverse(NodeVisitor& nv) { - switch(nv.getTraverseMode()) + switch(nv.getTraversalMode()) { - case(NodeVisitor::TRAVERSE_ALL_CHILDREN): - std::for_each(_children.begin(),_children.end(),NodeAcceptOp(nv)); - break; - case(NodeVisitor::TRAVERSE_ACTIVE_CHILDREN): - switch(_value) - { - case(ALL_CHILDREN_ON): + case(NodeVisitor::TRAVERSE_ALL_CHILDREN): std::for_each(_children.begin(),_children.end(),NodeAcceptOp(nv)); break; - case(ALL_CHILDREN_OFF): - return; - default: - if (_value>=0 && (unsigned int)_value<_children.size()) _children[_value]->accept(nv); + case(NodeVisitor::TRAVERSE_ACTIVE_CHILDREN): + switch(_value) + { + case(ALL_CHILDREN_ON): + std::for_each(_children.begin(),_children.end(),NodeAcceptOp(nv)); + break; + case(ALL_CHILDREN_OFF): + return; + default: + if (_value>=0 && (unsigned int)_value<_children.size()) _children[_value]->accept(nv); + break; + } + break; + default: break; - } - break; - default: - break; } } -bool Switch::readLocalData(Input& fr) -{ - bool iteratorAdvanced = false; - - if (fr.matchSequence("value")) - { - if (fr[1].matchWord("ALL_CHILDREN_ON")) - { - _value = ALL_CHILDREN_ON; - iteratorAdvanced = true; - fr+=2; - } - else if (fr[1].matchWord("ALL_CHILDREN_ON")) - { - _value = ALL_CHILDREN_OFF; - iteratorAdvanced = true; - fr+=2; - } - else if (fr[1].isInt()) - { - fr[1].getInt(_value); - iteratorAdvanced = true; - fr+=2; - } - } - - if (Group::readLocalData(fr)) iteratorAdvanced = true; - - return iteratorAdvanced; -} - -bool Switch::writeLocalData(Output& fw) -{ - fw.indent() << "value "; - switch(_value) - { - case(ALL_CHILDREN_ON): fw<<"ALL_CHILDREN_ON"< s_TexEnv(new TexEnv); - return s_TexEnv.get(); -} - - -void TexEnv::setMode( TexEnvMode mode ) +void TexEnv::setMode( const Mode mode ) { _mode = (mode == DECAL || - mode == MODULATE || - mode == BLEND ) ? - mode : MODULATE; + mode == MODULATE || + mode == BLEND || + mode == REPLACE ) ? + mode : MODULATE; } -void TexEnv::apply( void ) + +void TexEnv::apply(State&) const { glTexEnvi( GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, _mode); } - -bool TexEnv::readLocalData(Input& fr) -{ - bool iteratorAdvanced = false; - TexEnvMode mode; - if (fr[0].matchWord("mode") && matchModeStr(fr[1].getStr(),mode)) - { - _mode = mode; - fr+=2; - iteratorAdvanced = true; - } - - return iteratorAdvanced; -} - - -bool TexEnv::matchModeStr(const char* str,TexEnvMode& mode) -{ - if (strcmp(str,"DECAL")==0) mode = DECAL; - else if (strcmp(str,"MODULATE")==0) mode = MODULATE; - else if (strcmp(str,"BLEND")==0) mode = BLEND; - else return false; - return true; -} - - -const char* TexEnv::getModeStr(TexEnvMode mode) -{ - switch(mode) - { - case(DECAL): return "DECAL"; - case(MODULATE): return "MODULATE"; - case(BLEND): return "BLEND"; - } - return ""; -} - - -bool TexEnv::writeLocalData(Output& fw) -{ - fw.indent() << "mode " << getModeStr(_mode) << endl; - - return true; -} diff --git a/src/osg/TexGen.cpp b/src/osg/TexGen.cpp index 921f270d8..3b72d917e 100644 --- a/src/osg/TexGen.cpp +++ b/src/osg/TexGen.cpp @@ -1,89 +1,92 @@ - #include "osg/TexGen" -#include "osg/Input" -#include "osg/Output" +#include "osg/Notify" using namespace osg; -TexGen::TexGen( void ) +TexGen::TexGen() { _mode = OBJECT_LINEAR; + _plane_s.set(1.0f, 0.0f, 0.0f, 0.0f); + _plane_t.set(0.0f, 1.0f, 0.0f, 0.0f); + _plane_r.set(0.0f, 0.0f, 1.0f, 0.0f); + _plane_q.set(0.0f, 0.0f, 0.0f, 1.0f); } -TexGen::~TexGen( void ) +TexGen::~TexGen() { } -TexGen* TexGen::instance() +void TexGen::setPlane(const Coord which, const Vec4& plane) { - static ref_ptr s_texgen(new TexGen); - return s_texgen.get(); -} - - -bool TexGen::readLocalData(Input& fr) -{ - bool iteratorAdvanced = false; - TexGenMode mode; - if (fr[0].matchWord("mode") && matchModeStr(fr[1].getStr(),mode)) + switch( which ) { - _mode = mode; - fr+=2; - iteratorAdvanced = true; + case S : _plane_s = plane; break; + case T : _plane_t = plane; break; + case R : _plane_r = plane; break; + case Q : _plane_q = plane; break; + default : notify(WARN)<<"Error: invalid 'which' passed TexGen::setPlane("<<(unsigned int)which<<","< s_texmat(new TexMat); - return s_texmat.get(); -} - -void TexMat::apply( void ) +void TexMat::apply(State&) const { glMatrixMode( GL_TEXTURE ); - glLoadMatrixf( (GLfloat *)_mat ); + glLoadMatrixf( (GLfloat *)_matrix._mat ); } diff --git a/src/osg/Texture.cpp b/src/osg/Texture.cpp index 579b9595c..137c9cdd1 100644 --- a/src/osg/Texture.cpp +++ b/src/osg/Texture.cpp @@ -1,161 +1,72 @@ -#include "osg/Texture" -#include "osg/Input" -#include "osg/Output" -#include "osg/Registry" -#include "osg/Image" -#include "osg/Referenced" -#include "osg/Notify" +#if defined(_MSC_VER) + #pragma warning( disable : 4786 ) +#endif + +#include +#include +#include +#include +#include +#include + +#include using namespace osg; + +Texture::DeletedTextureObjectCache Texture::s_deletedTextureObjectCache; + Texture::Texture() { - _handle = 0; + _textureUnit = 0; _wrap_s = CLAMP; _wrap_t = CLAMP; _wrap_r = CLAMP; - _min_filter = NEAREST_MIPMAP_LINEAR; - _mag_filter = LINEAR; + //_min_filter = LINEAR_MIPMAP_LINEAR; // trilinear + //_min_filter = LINEAR_MIPMAP_NEAREST; // bilinear + _min_filter = NEAREST_MIPMAP_LINEAR; // OpenGL default + _mag_filter = LINEAR; + + _internalFormatMode = USE_IMAGE_DATA_FORMAT; + _internalFormatValue = 0; + + _textureWidth = _textureHeight = 0; + + _textureObjectSize = 0; + + _subloadMode = OFF; + _subloadOffsX = _subloadOffsY = 0; } Texture::~Texture() { - if (_handle!=0) glDeleteTextures( 1, &_handle ); -} - - -Texture* Texture::instance() -{ - static ref_ptr s_texture(new Texture); - return s_texture.get(); -} - - -bool Texture::readLocalData(Input& fr) -{ - bool iteratorAdvanced = false; - if (fr[0].matchWord("file") && fr[1].isString()) - { - _image = fr.readImage(fr[1].getStr()); - fr += 2; - iteratorAdvanced = true; - } - WrapMode wrap; - if (fr[0].matchWord("wrap_s") && matchWrapStr(fr[1].getStr(),wrap)) - { - _wrap_s = wrap; - fr+=2; - iteratorAdvanced = true; - } - - if (fr[0].matchWord("wrap_t") && matchWrapStr(fr[1].getStr(),wrap)) - { - _wrap_t = wrap; - fr+=2; - iteratorAdvanced = true; - } - - if (fr[0].matchWord("wrap_r") && matchWrapStr(fr[1].getStr(),wrap)) - { - _wrap_r = wrap; - fr+=2; - iteratorAdvanced = true; - } - - FilterMode filter; - if (fr[0].matchWord("min_filter") && matchFilterStr(fr[1].getStr(),filter)) - { - _min_filter = filter; - fr+=2; - iteratorAdvanced = true; - } - - if (fr[0].matchWord("mag_filter") && matchFilterStr(fr[1].getStr(),filter)) - { - _mag_filter = filter; - fr+=2; - iteratorAdvanced = true; - } - - return iteratorAdvanced; -} - - -bool Texture::writeLocalData(Output& fw) -{ - if (_image.valid()) - { - fw.indent() << "file \""<<_image->getFileName()<<"\""<data()) + { + // pad out the modified tag list, if required. + while (_modifiedTag.size() <= contextID) + _modifiedTag.push_back(0); + + if (_subloadMode == AUTO || + (_subloadMode == IF_DIRTY && _modifiedTag[contextID] != _image->getModifiedTag())) + { + glBindTexture( GL_TEXTURE_2D, handle ); + glTexSubImage2D(GL_TEXTURE_2D, 0, + _subloadOffsX, _subloadOffsY, + _image->s(), _image->t(), + (GLenum) _image->pixelFormat(), (GLenum) _image->dataType(), + _image->data()); + // update the modified flag to show that the image has been loaded. + _modifiedTag[contextID] = _image->getModifiedTag(); + } + } + } + else { + glGenTextures( 1L, (GLuint *)&handle ); + glBindTexture( GL_TEXTURE_2D, handle ); + + applyImmediateMode(state); + + // in theory the following line is redundent, but in practice + // have found that the first frame drawn doesn't apply the textures + // unless a second bind is called?!! + // perhaps it is the first glBind which is not required... + glBindTexture( GL_TEXTURE_2D, handle ); + + } +} + +void Texture::compile(State& state) const +{ + apply(state); +} + + +void Texture::applyImmediateMode(State& state) const +{ + // if we don't have a valid image we can't create a texture! + if (!_image.valid() || !_image->data()) + return; + + // get the contextID (user defined ID of 0 upwards) for the + // current OpenGL context. + const uint contextID = state.getContextID(); + + // pad out the modified tag list, if required. + while (_modifiedTag.size() <= contextID) + _modifiedTag.push_back(0); + + // update the modified tag to show that it is upto date. + _modifiedTag[contextID] = _image->getModifiedTag(); + + + if (_subloadMode == OFF) _image->ensureDimensionsArePowerOfTwo(); - - glPixelStorei(GL_UNPACK_ALIGNMENT,_image->packing()); + glPixelStorei(GL_UNPACK_ALIGNMENT,_image->packing()); - glGenTextures( 1, &_handle ); - glBindTexture( GL_TEXTURE_2D, _handle ); + if (_wrap_s == MIRROR || _wrap_t == MIRROR) + { + static bool s_mirroredSupported = isGLExtensionSupported("GL_IBM_texture_mirrored_repeat"); + // check for support of mirror-repeated textures + // if not supported fall back to repeated textures + WrapMode ws = _wrap_s, wt = _wrap_t; + if (!s_mirroredSupported) + { + if (ws == MIRROR) + ws = REPEAT; + if (wt == MIRROR) + wt = REPEAT; + } + glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, ws ); + glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, wt ); + } + else + { glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, _wrap_s ); glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, _wrap_t ); - glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, _min_filter); + } + + glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, _min_filter); + + if (_mag_filter == ANISOTROPIC) + { + // check for support for anisotropic filter, + // note since this is static varible it is intialised + // only on the first time entering this code block, + // is then never reevaluated on subsequent calls. + static bool s_anisotropicSupported = + isGLExtensionSupported("GL_EXT_texture_filter_anisotropic"); + + if (s_anisotropicSupported) + { + // note, GL_TEXTURE_MAX_ANISOTROPY_EXT will either be defined + // by gl.h (or via glext.h) or by include/osg/Texture. + glTexParameterf(GL_TEXTURE_2D, GL_TEXTURE_MAX_ANISOTROPY_EXT, 2.f); + } + else + { + glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, LINEAR); + } + } + else + { glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, _mag_filter); + } + + + static bool s_ARB_Compression = isGLExtensionSupported("GL_ARB_texture_compression"); + static bool s_S3TC_Compression = isGLExtensionSupported("GL_EXT_texture_compression_s3tc"); + + // select the internalFormat required for the texture. + int internalFormat = _image->internalFormat(); + switch(_internalFormatMode) + { + case(USE_IMAGE_DATA_FORMAT): + internalFormat = _image->internalFormat(); + break; + + case(USE_ARB_COMPRESSION): + if (s_ARB_Compression) + { + switch(_image->pixelFormat()) + { + case(1): internalFormat = GL_COMPRESSED_ALPHA_ARB; break; + case(2): internalFormat = GL_COMPRESSED_LUMINANCE_ALPHA_ARB; break; + case(3): internalFormat = GL_COMPRESSED_RGB_ARB; break; + case(4): internalFormat = GL_COMPRESSED_RGBA_ARB; break; + case(GL_RGB): internalFormat = GL_COMPRESSED_RGB_ARB; break; + case(GL_RGBA): internalFormat = GL_COMPRESSED_RGBA_ARB; break; + case(GL_ALPHA): internalFormat = GL_COMPRESSED_ALPHA_ARB; break; + case(GL_LUMINANCE): internalFormat = GL_COMPRESSED_LUMINANCE_ARB; break; + case(GL_LUMINANCE_ALPHA): internalFormat = GL_COMPRESSED_LUMINANCE_ALPHA_ARB; break; + case(GL_INTENSITY): internalFormat = GL_COMPRESSED_INTENSITY_ARB; break; + } + } + else internalFormat = _image->internalFormat(); + break; + + case(USE_S3TC_DXT1_COMPRESSION): + if (s_S3TC_Compression) + { + switch(_image->pixelFormat()) + { + case(3): internalFormat = GL_COMPRESSED_RGB_S3TC_DXT1_EXT; break; + case(4): internalFormat = GL_COMPRESSED_RGBA_S3TC_DXT1_EXT; break; + case(GL_RGB): internalFormat = GL_COMPRESSED_RGB_S3TC_DXT1_EXT; break; + case(GL_RGBA): internalFormat = GL_COMPRESSED_RGBA_S3TC_DXT1_EXT; break; + default: internalFormat = _image->internalFormat(); break; + } + } + else internalFormat = _image->internalFormat(); + break; + + case(USE_S3TC_DXT3_COMPRESSION): + if (s_S3TC_Compression) + { + switch(_image->pixelFormat()) + { + case(3): + case(GL_RGB): internalFormat = GL_COMPRESSED_RGB_S3TC_DXT1_EXT; break; + case(4): + case(GL_RGBA): internalFormat = GL_COMPRESSED_RGBA_S3TC_DXT3_EXT; break; + default: internalFormat = _image->internalFormat(); break; + } + } + else internalFormat = _image->internalFormat(); + break; + + case(USE_S3TC_DXT5_COMPRESSION): + if (s_S3TC_Compression) + { + switch(_image->pixelFormat()) + { + case(3): + case(GL_RGB): internalFormat = GL_COMPRESSED_RGB_S3TC_DXT1_EXT; break; + case(4): + case(GL_RGBA): internalFormat = GL_COMPRESSED_RGBA_S3TC_DXT5_EXT; break; + default: internalFormat = _image->internalFormat(); break; + } + } + else internalFormat = _image->internalFormat(); + break; + + case(USE_USER_DEFINED_FORMAT): + internalFormat = _internalFormatValue; + break; + + } + + if (_subloadMode == OFF) { if( _min_filter == LINEAR || _min_filter == NEAREST ) { + glTexImage2D( GL_TEXTURE_2D, 0, internalFormat, + _image->s(), _image->t(), 0, + (GLenum)_image->pixelFormat(), + (GLenum)_image->dataType(), + _image->data() ); + // just estimate estimate it right now.. + // note, ignores texture compression.. + _textureObjectSize = _image->s()*_image->t()*4; - glTexImage2D( GL_TEXTURE_2D, 0, _image->internalFormat(), - _image->s(), _image->t(), 0, - (GLenum)_image->pixelFormat(), - (GLenum)_image->dataType(), - _image->data() ); } else { - gluBuild2DMipmaps( GL_TEXTURE_2D, _image->internalFormat(), + gluBuild2DMipmaps( GL_TEXTURE_2D, internalFormat, _image->s(),_image->t(), (GLenum)_image->pixelFormat(), (GLenum)_image->dataType(), _image->data() ); + + // just estimate size it right now.. + // crude x2 multiplier to account for minmap storage. + // note, ignores texture compression.. + _textureObjectSize = _image->s()*_image->t()*4; + } - glBindTexture( GL_TEXTURE_2D, _handle ); + _textureWidth = _image->s(); + _textureHeight = _image->t(); + } + else + { + static bool s_SGIS_GenMipmap = isGLExtensionSupported("GL_SGIS_generate_mipmap"); + if (s_SGIS_GenMipmap && (_min_filter != LINEAR && _min_filter != NEAREST)) { + glTexParameteri(GL_TEXTURE_2D, GL_GENERATE_MIPMAP_SGIS, GL_TRUE); + } + + // calculate texture dimension + _textureWidth = 1; + for (; _textureWidth < (_subloadOffsX + _image->s()); _textureWidth <<= 1) + ; + + _textureHeight = 1; + for (; _textureHeight < (_subloadOffsY + _image->t()); _textureHeight <<= 1) + ; + + // reserve appropriate texture memory + glTexImage2D(GL_TEXTURE_2D, 0, internalFormat, + _textureWidth, _textureHeight, 0, + (GLenum) _image->pixelFormat(), (GLenum) _image->dataType(), + NULL); + + glTexSubImage2D(GL_TEXTURE_2D, 0, + _subloadOffsX, _subloadOffsY, + _image->s(), _image->t(), + (GLenum) _image->pixelFormat(), (GLenum) _image->dataType(), + _image->data()); + } + +} + +/** use deleteTextureObject instead of glDeleteTextures to allow + * OpenGL texture objects to cached until they can be deleted + * by the OpenGL context in which they were created, specified + * by contextID.*/ +void Texture::deleteTextureObject(uint contextID,uint handle) +{ + if (handle!=0) + { + // insert the handle into the cache for the appropriate context. + s_deletedTextureObjectCache[contextID].insert(handle); + } +} + + +/** flush all the cached display list which need to be deleted + * in the OpenGL context related to contextID.*/ +void Texture::flushDeletedTextureObjects(uint contextID) +{ + DeletedTextureObjectCache::iterator citr = s_deletedTextureObjectCache.find(contextID); + if (citr!=s_deletedTextureObjectCache.end()) + { + std::set& textureObjectSet = citr->second; + for(std::set::iterator titr=textureObjectSet.begin(); + titr!=textureObjectSet.end(); + ++titr) + { + glDeleteTextures( 1L, (const GLuint *)&(*titr )); + } + s_deletedTextureObjectCache.erase(citr); + } +} + +void Texture::copyTexImage2D(State& state, int x, int y, int width, int height ) +{ + const uint contextID = state.getContextID(); + + // get the globj for the current contextID. + uint& handle = getHandle(contextID); + + if (handle) + { + if (width==(int)_textureWidth && height==(int)_textureHeight) + { + // we have a valid texture object which is the right size + // so lets play clever and use copyTexSubImage2D instead. + // this allows use to reuse the texture object and avoid + // expensive memory allocations. + copyTexSubImage2D(state,0 ,0, x, y, width, height); + return; + } + // the relevent texture object is not of the right size so + // needs to been deleted + // remove previously bound textures. + dirtyTextureObject(); + // note, dirtyTextureObject() dirties all the texture objects for + // this texture, is this right? Perhaps we should dirty just the + // one for this context. Note sure yet will leave till later. + // RO July 2001. + } + + // For multi-texturing will need something like... + // glActiveTextureARB((GLenum)(GL_TEXTURE0_ARB+_textureUnit)); + + // remove any previously assigned images as these are nolonger valid. + _image = NULL; + + // switch off mip-mapping. + _min_filter = LINEAR; + _mag_filter = LINEAR; + + // Get a new 2d texture handle. + glGenTextures( 1, &handle ); + + glBindTexture( GL_TEXTURE_2D, handle ); + glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_WRAP_S, _wrap_s ); + glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_WRAP_T, _wrap_t ); + glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MIN_FILTER, _min_filter ); + glTexParameteri( GL_TEXTURE_2D, GL_TEXTURE_MAG_FILTER, _mag_filter ); +// glTexEnvi( GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_REPLACE); + glCopyTexImage2D( GL_TEXTURE_2D, 0, GL_RGBA, x, y, width, height, 0 ); + + + /* Redundant, delete later */ +// glBindTexture( GL_TEXTURE_2D, handle ); + + _textureWidth = width; + _textureHeight = height; + +// cout<<"copyTexImage2D x="< #include @@ -132,7 +162,6 @@ Timer_t Timer::delta_n( Timer_t t0, Timer_t t1 ) unsigned long Timer::dummy = 0; - Timer::Timer( void ) { __psunsigned_t phys_addr, raddr; @@ -154,26 +183,66 @@ Timer::Timer( void ) return; } - iotimer_addr = (volatile unsigned long *)mmap( - (void *)0L, - (size_t)poffmask, - (int)PROT_READ, - (int)MAP_PRIVATE, fd, (off_t)raddr); + (void *)0L, + (size_t)poffmask, + (int)PROT_READ, + (int)MAP_PRIVATE, fd, (off_t)raddr); iotimer_addr = (unsigned long *)( - (__psunsigned_t)iotimer_addr + (phys_addr & poffmask) - ); - + (__psunsigned_t)iotimer_addr + (phys_addr & poffmask) + ); cycleCntrSize = syssgi( SGI_CYCLECNTR_SIZE ); - if( cycleCntrSize > 32 ) + if( cycleCntrSize > 32 ) ++iotimer_addr; clk = (unsigned long *)iotimer_addr; } + +Timer::~Timer( void ) +{ +} + + +double Timer::delta_s( Timer_t t1, Timer_t t2 ) +{ + Timer_t delta = t2 - t1; + return ((double)delta * microseconds_per_click*1e-6); +} + + +double Timer::delta_m( Timer_t t1, Timer_t t2 ) +{ + Timer_t delta = t2 - t1; + return ((double)delta * microseconds_per_click*1e-3); +} + + +Timer_t Timer::delta_u( Timer_t t1, Timer_t t2 ) +{ + Timer_t delta = t2 - t1; + return (Timer_t)((double)delta * microseconds_per_click); +} + +Timer_t Timer::delta_n( Timer_t t1, Timer_t t2 ) +{ + unsigned long delta = t2 - t1; + return (Timer_t )((double)delta * nanoseconds_per_click); +} + +#endif // ] + +#ifdef macintosh // [ + +Timer::Timer( void ) +{ + microseconds_per_click = (1.0 / (double) CLOCKS_PER_SEC) * 1e6; + nanoseconds_per_click = (1.0 / (double) CLOCKS_PER_SEC) * 1e9; +} + Timer::~Timer( void ) { } @@ -201,5 +270,4 @@ Timer_t Timer::delta_n( Timer_t t1, Timer_t t2 ) unsigned long delta = t2 - t1; return (Timer_t )((double)delta * nanoseconds_per_click); } - -#endif // ] +#endif // ] diff --git a/src/osg/Transparency.cpp b/src/osg/Transparency.cpp index 882474fcf..a241e576d 100644 --- a/src/osg/Transparency.cpp +++ b/src/osg/Transparency.cpp @@ -1,46 +1,19 @@ -#include "osg/OSG" #include "osg/Transparency" using namespace osg; -Transparency::Transparency( void ) +Transparency::Transparency() { _source_factor = SRC_ALPHA; _destination_factor = ONE_MINUS_SRC_ALPHA; } -Transparency::~Transparency( void ) +Transparency::~Transparency() { } - -Transparency* Transparency::instance() -{ - static ref_ptr s_transparency(new Transparency); - return s_transparency.get(); -} - -void Transparency::enable( void ) -{ - glEnable( GL_BLEND ); -} - - -void Transparency::disable( void ) -{ - glDisable( GL_BLEND ); -} - - -void Transparency::apply( void ) +void Transparency::apply(State&) const { glBlendFunc( (GLenum)_source_factor, (GLenum)_destination_factor ); } - - -void Transparency::setFunction( int source, int destination ) -{ - _source_factor = source; - _destination_factor = destination; -} diff --git a/src/osg/Version.cpp b/src/osg/Version.cpp index cab061079..885473c29 100644 --- a/src/osg/Version.cpp +++ b/src/osg/Version.cpp @@ -2,9 +2,10 @@ const char* osgGetVersion() { - return "0.8.34"; + return "0.8.42"; } + const char* osgGetLibraryName() { return "Open Scene Graph Library"; diff --git a/src/osgDB/DotOsgWrapper.cpp b/src/osgDB/DotOsgWrapper.cpp new file mode 100644 index 000000000..addf1b76e --- /dev/null +++ b/src/osgDB/DotOsgWrapper.cpp @@ -0,0 +1,38 @@ +#include + +using namespace osgDB; + +DotOsgWrapper::DotOsgWrapper(osg::Object* proto, + const std::string& name, + const std::string& associates, + ReadFunc readFunc, + WriteFunc writeFunc, + ReadWriteMode readWriteMode) +{ + _prototype = proto; + _name = name; + + + // copy the names in the space deliminated associates input into + // a vector of seperated names. + std::string::size_type start_of_name = associates.find_first_not_of(' '); + while (start_of_name!=std::string::npos) + { + std::string::size_type end_of_name = associates.find_first_of(' ',start_of_name); + if (end_of_name!=std::string::npos) + { + _associates.push_back(std::string(associates,start_of_name,end_of_name-start_of_name)); + start_of_name = associates.find_first_not_of(' ',end_of_name); + } + else + { + _associates.push_back(std::string(associates,start_of_name,associates.size()-start_of_name)); + start_of_name = end_of_name; + } + } + + _readFunc = readFunc; + _writeFunc = writeFunc; + + _readWriteMode = readWriteMode; +} diff --git a/src/osgDB/DynamicLibrary.cpp b/src/osgDB/DynamicLibrary.cpp new file mode 100644 index 000000000..4fb0e81bb --- /dev/null +++ b/src/osgDB/DynamicLibrary.cpp @@ -0,0 +1,69 @@ +#ifdef WIN32 +#include +#include +#include +#elif !defined(macintosh) +#include +#include +#endif + +#ifndef OSG_USE_IO_DOT_H +#include +using namespace std; +#endif + +#include "osg/Notify" + +#include "osgDB/DynamicLibrary" +#include "osgDB/FileUtils" + +using namespace osg; +using namespace osgDB; + +DynamicLibrary::DynamicLibrary(const std::string& name,HANDLE handle) +{ + _name = name; + _handle = handle; +} + +DynamicLibrary::~DynamicLibrary() +{ + if (_handle) + { +#ifdef WIN32 + FreeLibrary((HMODULE)_handle); +#elif !defined(macintosh) + dlclose(_handle); +#endif + } +} + +DynamicLibrary* DynamicLibrary::loadLibrary(const std::string& libraryName) +{ + + char* fullLibraryName = osgDB::findDSO( libraryName.c_str() ); + if (fullLibraryName==NULL) return NULL; + +#ifdef WIN32 + HANDLE handle = LoadLibrary( fullLibraryName ); + if (handle) return new DynamicLibrary(libraryName,handle); + notify(WARN) << "DynamicLibrary::failed loading "< + +using namespace osgDB; + +Field::Field() +{ + _init(); +} + + +Field::Field(const Field& ic) +{ + _copy(ic); +} + + +Field::~Field() +{ + _free(); +} + + +Field& Field::operator = (const Field& ic) +{ + if (this==&ic) return *this; + _free(); + _copy(ic); + return *this; +} + + +void Field::_free() +{ + // free all data + if (_fieldCache) delete [] _fieldCache; + + _init(); + +} + + +void Field::_init() +{ + + _fieldCacheCapacity = 256; + _fieldCacheSize = 0; + _fieldCache = NULL; + + _fieldType = UNINTIALISED; + + _withinQuotes = false; + + _noNestedBrackets = 0; + +} + + +void Field::_copy(const Field& ic) +{ + + // copy string cache. + if (ic._fieldCache) + { + _fieldCacheCapacity = ic._fieldCacheCapacity; + _fieldCacheSize = ic._fieldCacheSize; + _fieldCache = new char [_fieldCacheCapacity]; + strncpy(_fieldCache,ic._fieldCache,_fieldCacheCapacity); + } + else + { + _fieldCacheCapacity = 0; + _fieldCacheSize = 0; + _fieldCache = NULL; + } + + _fieldType = ic._fieldType; + + _withinQuotes = ic._withinQuotes; + + _noNestedBrackets = ic._noNestedBrackets; +} + + +void Field::setWithinQuotes(bool withinQuotes) +{ + _withinQuotes=withinQuotes; + _fieldType = UNINTIALISED; +} + + +bool Field::getWithinQuotes() +{ + return _withinQuotes; +} + + +void Field::setNoNestedBrackets(int no) +{ + _noNestedBrackets=no; +} + + +int Field::getNoNestedBrackets() +{ + return _noNestedBrackets; +} + + +const char* Field::getStr() const +{ + if (_fieldCacheSize!=0) return _fieldCache; + else return NULL; +} + + +char* Field::takeStr() +{ + char* field = _fieldCache; + + _fieldCache = NULL; + _fieldCacheSize = 0; + + _fieldType = UNINTIALISED; + _withinQuotes = false; + + return field; +} + + +void Field::reset() +{ + _fieldCacheSize = 0; + if (_fieldCache) + { + _fieldCache[_fieldCacheSize] = 0; + } + + _withinQuotes = false; + _noNestedBrackets = 0; +} + + +void Field::addChar(char c) +{ + if (_fieldCache==NULL) + { + if (_fieldCacheCapacity=_fieldCacheCapacity-1) + { + if (_fieldCacheCapacity=_fieldCacheCapacity-1) _fieldCacheCapacity *= 2; + char* tmp_str = _fieldCache; + _fieldCache = new char[_fieldCacheCapacity]; + strncpy(_fieldCache,tmp_str,_fieldCacheSize); + delete [] tmp_str; + + } + _fieldCache[_fieldCacheSize++] = c; + _fieldCache[_fieldCacheSize] = 0; + _fieldType = UNINTIALISED; +} + + +Field::FieldType Field::getFieldType() const +{ + if (_fieldType==UNINTIALISED && _fieldCache) + { + _fieldType = calculateFieldType(_fieldCache,_withinQuotes); + } + return _fieldType; +} + + +bool Field::isValid() const +{ + if (_fieldCacheSize>0 && !_withinQuotes) return true; + else return false; +} + + +bool Field::isOpenBracket() const +{ + if (_fieldCacheSize==1) return _fieldCache[0]=='{'; + else return false; +} + + +bool Field::isCloseBracket() const +{ + if (_fieldCacheSize==1) return _fieldCache[0]=='}'; + else return false; +} + + +bool Field::isWord() const +{ + getFieldType(); + return (_fieldType==WORD); +} + + +bool Field::matchWord(const char* str) const +{ + getFieldType(); + return _fieldType==WORD && strcmp(_fieldCache,str)==0; +} + + +bool Field::matchWord(const char* str,int noCharacters) const +{ + getFieldType(); + return _fieldType==WORD && strncmp(_fieldCache,str,noCharacters)==0; +} + + +bool Field::isString() const +{ + return getNoCharacters()!=0; +} + + +bool Field::matchString(const char* str) const +{ + return strcmp(_fieldCache,str)==0; +} + + +bool Field::matchString(const char* str,int noCharacters) const +{ + return strncmp(_fieldCache,str,noCharacters)==0; +} + + +bool Field::isQuotedString() const +{ + return _withinQuotes; +} + + +bool Field::isInt() const +{ + getFieldType(); + return _fieldType==INTEGER; +} + + +bool Field::matchInt(int i) const +{ + getFieldType(); + if (_fieldType==INTEGER) + { + return strtol(_fieldCache,NULL,0)==i; + } + else + { + return false; + } +} + + +bool Field::getInt(int& i) const +{ + getFieldType(); + if (_fieldType==INTEGER) + { + i = strtol(_fieldCache,NULL,0); + return true; + } + else + { + return false; + } +} + +bool Field::isUInt() const +{ + getFieldType(); + return _fieldType==INTEGER; +} + + +bool Field::matchUInt(osg::uint i) const +{ + getFieldType(); + if (_fieldType==INTEGER) + { + return (osg::uint) strtoul(_fieldCache,NULL,0)==i; + } + else + { + return false; + } +} + + +bool Field::getUInt(osg::uint& i) const +{ + getFieldType(); + if (_fieldType==INTEGER) + { + i = strtoul(_fieldCache,NULL,0); + return true; + } + else + { + return false; + } +} + +bool Field::isFloat() const +{ + getFieldType(); + return _fieldType==REAL || _fieldType==INTEGER; +} + + +bool Field::matchFloat(float f) const +{ + getFieldType(); + if (_fieldType==REAL || _fieldType==INTEGER) + { + return (float)atof(_fieldCache)==f; + } + else + { + return false; + } +} + + +bool Field::getFloat(float& f) const +{ + getFieldType(); + if (_fieldType==REAL || _fieldType==INTEGER) + { + f = (float)atof(_fieldCache); + return true; + } + else + { + return false; + } +} + + +bool Field::isDouble() const +{ + getFieldType(); + return _fieldType==REAL || _fieldType==INTEGER; +} + + +bool Field::matchDouble(double d) const +{ + getFieldType(); + if (_fieldType==REAL || _fieldType==INTEGER) + { + return atof(_fieldCache)==d; + } + else + { + return false; + } +} + + +bool Field::getDouble(double& d) const +{ + getFieldType(); + if (_fieldType==REAL || _fieldType==INTEGER) + { + d = atof(_fieldCache); + return true; + } + else + { + return false; + } +} + + +Field::FieldType Field::calculateFieldType(const char* str,bool withinQuotes) +{ + if (str==NULL) return BLANK; + if (*str==0) return BLANK; + + if (withinQuotes) return STRING; + + bool hadPlusMinus = false; + bool hadDecimalPlace = false; + bool hadExponent = false; + bool couldBeInt = true; + bool couldBeFloat = true; + int noZeroToNine = 0; + + const char* ptr = str; + + // check if could be a hex number. + if (strncmp(ptr,"0x",2)==0) + { + // skip over leading 0x, and then go through rest of string + // checking to make sure all values are 0...9 or a..f. + ptr+=2; + while ( + *ptr!=0 && + ((*ptr>='0' && *ptr<='9') || + (*ptr>='a' && *ptr<='f') || + (*ptr>='A' && *ptr<='F')) + ) + { + ++ptr; + } + + // got to end of string without failure, therefore must be a hex integer. + if (*ptr==0) return INTEGER; + } + + ptr = str; + // check if a float or an int. + while (*ptr!=0 && couldBeFloat) + { + if (*ptr=='+' || *ptr=='-') + { + if (hadPlusMinus) + { + couldBeInt = false; + couldBeFloat = false; + } else hadPlusMinus = true; + } + else if (*ptr>='0' && *ptr<='9') + { + noZeroToNine++; + } + else if (*ptr=='.') + { + if (hadDecimalPlace) + { + couldBeInt = false; + couldBeFloat = false; + } + else + { + hadDecimalPlace = true; + couldBeInt = false; + } + } + else if (*ptr=='e' || *ptr=='E') + { + if (hadExponent || noZeroToNine==0) + { + couldBeInt = false; + couldBeFloat = false; + } + else + { + hadExponent = true; + couldBeInt = false; + hadDecimalPlace = false; + hadPlusMinus = false; + noZeroToNine=0; + } + } + else + { + couldBeInt = false; + couldBeFloat = false; + } + ++ptr; + } + + if (couldBeInt && noZeroToNine>0) return INTEGER; + if (couldBeFloat && noZeroToNine>0) return REAL; + if (str[0]=='{') return OPEN_BRACKET; + if (str[0]=='}') return CLOSE_BRACKET; + return WORD; +} diff --git a/src/osgDB/FieldReader.cpp b/src/osgDB/FieldReader.cpp new file mode 100644 index 000000000..31575a5d8 --- /dev/null +++ b/src/osgDB/FieldReader.cpp @@ -0,0 +1,269 @@ +#include "osgDB/Field" +#include "osgDB/FieldReader" + +using namespace osgDB; + +FieldReader::FieldReader() +{ + _init(); +} + + +FieldReader::FieldReader(const FieldReader& ic) +{ + _copy(ic); +} + + +FieldReader::~FieldReader() +{ + _free(); +} + + +FieldReader& FieldReader::operator = (const FieldReader& ic) +{ + if (this==&ic) return *this; + _free(); + _copy(ic); + return *this; +} + + +void FieldReader::_free() +{ + // free all data + + _init(); + +} + + +void FieldReader::_init() +{ + _fin = NULL; + _eof = true; + + _noNestedBrackets = 0; + + int i; + for(i=0;i<256;++i) _delimiterEatLookUp[i]=false; + _delimiterEatLookUp[' '] = true; + _delimiterEatLookUp['\t'] = true; + _delimiterEatLookUp['\n'] = true; + _delimiterEatLookUp['\r'] = true; + + for(i=0;i<256;++i) _delimiterKeepLookUp[i]=false; + _delimiterKeepLookUp['{'] = true; + _delimiterKeepLookUp['}'] = true; + _delimiterKeepLookUp['"'] = true; + _delimiterKeepLookUp['\''] = true; + +} + + +void FieldReader::_copy(const FieldReader& ic) +{ + + _fin = ic._fin; + _eof = ic._eof; + + _noNestedBrackets = ic._noNestedBrackets; + + int i; + for(i=0;i<256;++i) _delimiterEatLookUp[i]=ic._delimiterEatLookUp[i]; + for(i=0;i<256;++i) _delimiterKeepLookUp[i]=ic._delimiterKeepLookUp[i]; +} + + +void FieldReader::attach(istream* input) +{ + _fin = input; + + if (_fin) + { + _eof = _fin->eof()!=0; + } + else + { + _eof = true; + } +} + + +void FieldReader::detach() +{ + _fin = NULL; + _eof = true; +} + + +bool FieldReader::eof() const +{ + return _eof; +} + + +bool FieldReader::findStartOfNextField() +{ + int ch = 0; + while (true) + { + ch = _fin->peek(); + if (ch==EOF) + { + _eof = true; + return false; + } + else if (_delimiterEatLookUp[ch]) + { + _fin->ignore(1); + } + else + { + return true; + } + } +} + + +bool FieldReader::readField(Field& fieldPtr) +{ + return _readField(&fieldPtr); +} + + +void FieldReader::ignoreField() +{ + _readField(NULL); +} + + +bool FieldReader::_readField(Field* fieldPtr) +{ + if (fieldPtr) fieldPtr->reset(); + + if (!eof() && findStartOfNextField()) + { + + int ch = _fin->peek(); + if (ch==EOF) + { + _eof = true; + if (fieldPtr) fieldPtr->setNoNestedBrackets(getNoNestedBrackets()); + return fieldPtr && fieldPtr->getNoCharacters()!=0; + } + else if (ch=='"') + { + if (fieldPtr) + { + fieldPtr->setWithinQuotes(true); + fieldPtr->setNoNestedBrackets(getNoNestedBrackets()); + } + _fin->ignore(1); + char c; + while (true) + { + ch = _fin->peek(); + if (ch==EOF) + { + _eof = true; + return fieldPtr && fieldPtr->getNoCharacters()!=0; + } + c = ch; + if (ch=='"') + { + _fin->ignore(1); + //return fieldPtr && fieldPtr->getNoCharacters()!=0; + return fieldPtr!=NULL; + } + else + { + _fin->get(c); + if (fieldPtr) fieldPtr->addChar(c); + } + } + } + else if (ch=='\'') + { + if (fieldPtr) + { + fieldPtr->setWithinQuotes(true); + fieldPtr->setNoNestedBrackets(getNoNestedBrackets()); + } + _fin->ignore(1); + char c; + while (true) + { + ch = _fin->peek(); + if (ch==EOF) + { + _eof = true; + return fieldPtr && fieldPtr->getNoCharacters()!=0; + } + c = ch; + if (ch=='\'') + { + _fin->ignore(1); + //return fieldPtr && fieldPtr->getNoCharacters()!=0; + return fieldPtr!=NULL; + } + else + { + _fin->get(c); + if (fieldPtr) fieldPtr->addChar(c); + } + } + } + else if (_delimiterKeepLookUp[ch]) + { + char c; + _fin->get(c); + if (fieldPtr) fieldPtr->addChar(c); + if (c=='{') ++_noNestedBrackets; + else if (c=='}') --_noNestedBrackets; + if (fieldPtr) fieldPtr->setNoNestedBrackets(getNoNestedBrackets()); + return fieldPtr && fieldPtr->getNoCharacters()!=0; + } + else + { + if (fieldPtr) fieldPtr->setNoNestedBrackets(getNoNestedBrackets()); + char c; + while (true) + { + ch = _fin->peek(); + if (ch==EOF) + { + _eof = true; + return fieldPtr && fieldPtr->getNoCharacters()!=0; + } + c = ch; + if (_delimiterEatLookUp[c]) + { + _fin->ignore(1); + return fieldPtr && fieldPtr->getNoCharacters()!=0; + } + if (_delimiterKeepLookUp[c]) + { + return fieldPtr && fieldPtr->getNoCharacters()!=0; + } + else + { + _fin->get(c); + if (fieldPtr) fieldPtr->addChar(c); + } + } + } + + } + else + { + return false; + } +} + + +int FieldReader::getNoNestedBrackets() const +{ + return _noNestedBrackets; +} diff --git a/src/osgDB/FieldReaderIterator.cpp b/src/osgDB/FieldReaderIterator.cpp new file mode 100644 index 000000000..de39cd4cd --- /dev/null +++ b/src/osgDB/FieldReaderIterator.cpp @@ -0,0 +1,366 @@ +#include + +using namespace osgDB; + +FieldReaderIterator::FieldReaderIterator() +{ + _init(); +} + + +FieldReaderIterator::FieldReaderIterator(const FieldReaderIterator& ic) +{ + _copy(ic); +} + + +FieldReaderIterator::~FieldReaderIterator() +{ + _free(); +} + + +FieldReaderIterator& FieldReaderIterator::operator = (const FieldReaderIterator& ic) +{ + if (this==&ic) return *this; + _free(); + _copy(ic); + return *this; +} + + +void FieldReaderIterator::_free() +{ + // free all data + if (_previousField) + { + delete _previousField; + } + if (_fieldQueue) + { + for(int i=0;i<_fieldQueueCapacity;++i) + { + if (_fieldQueue[i]) delete _fieldQueue[i]; + _fieldQueue[i] = NULL; + } + delete [] _fieldQueue; + } + _init(); + +} + + +void FieldReaderIterator::_init() +{ + _previousField = NULL; + _fieldQueue = NULL; + _fieldQueueSize = 0; + _fieldQueueCapacity = 0; + +} + + +void FieldReaderIterator::_copy(const FieldReaderIterator& ic) +{ + _reader = ic._reader; + + if (ic._previousField) + { + _previousField = new Field(*ic._previousField); + } + + if (ic._fieldQueue && ic._fieldQueueCapacity>0) + { + _fieldQueue = new Field* [ic._fieldQueueCapacity]; + for(int i=0;i_fieldQueueSize) pos=_fieldQueueSize; + + int i; + // need to reallocate the stack + if (_fieldQueueSize>=_fieldQueueCapacity) + { + int newCapacity = _fieldQueueCapacity*2; + if (newCapacity=newCapacity) newCapacity*=2; + Field** newFieldStack = new Field* [newCapacity]; + for(i=0;i<_fieldQueueCapacity;++i) + { + newFieldStack[i] = _fieldQueue[i]; + } + for(;i=pos;++i) + { + _fieldQueue[i+1]=_fieldQueue[i]; + } + _fieldQueue[pos] = field; + ++_fieldQueueSize; +} + + +void FieldReaderIterator::insert(int pos,const char* str) +{ + if (str) + { + Field* field = new Field; + while(*str!=0) + { + field->addChar(*str); + ++str; + } + insert(pos,field); + } +} + + +Field& FieldReaderIterator::operator [] (int pos) +{ + return field(pos); +} + + +Field& FieldReaderIterator::field (int pos) +{ + if (pos<0) + { + _blank.setNoNestedBrackets(_reader.getNoNestedBrackets()); + return _blank; + } // can directly access field + else if (pos<_fieldQueueSize) + { + return *_fieldQueue[pos]; + } // need to read the new fields. + else + { + // need to reallocate the stack + if (pos>=_fieldQueueCapacity) + { + int newCapacity = _fieldQueueCapacity*2; + if (newCapacity=newCapacity) newCapacity*=2; + Field** newFieldStack = new Field* [newCapacity]; + int i; + for(i=0;i<_fieldQueueCapacity;++i) + { + newFieldStack[i] = _fieldQueue[i]; + } + for(;i=_fieldQueueSize) + { + if (_fieldQueue[_fieldQueueSize]==NULL) _fieldQueue[_fieldQueueSize] = new Field; + if (_reader.readField(*_fieldQueue[_fieldQueueSize])) + { + ++_fieldQueueSize; + } + } + if (pos<_fieldQueueSize) + { + return *_fieldQueue[pos]; + } + else + { + _blank.setNoNestedBrackets(_reader.getNoNestedBrackets()); + return _blank; + } + } +} + + +FieldReaderIterator& FieldReaderIterator::operator ++ () +{ + return (*this)+=1; +} + + +FieldReaderIterator& FieldReaderIterator::operator += (int no) +{ + if (no>_fieldQueueSize) + { + while (!_reader.eof() && no>_fieldQueueSize) + { + _reader.ignoreField(); + --no; + } + _fieldQueueSize=0; + } + else if (no>0) + { + Field** tmpFields = new Field* [no]; + int i; + for(i=0;i=entry) + { + ++(*this); + } +} + + +void FieldReaderIterator::advanceToEndOfBlock(int noNestedBrackets) +{ + while(!eof() && field(0).getNoNestedBrackets()>=noNestedBrackets) + { + ++(*this); + } +} + + +bool FieldReaderIterator::matchSequence(const char* str) +{ + if (str==NULL) return false; + if (*str==0) return false; + int fieldCount = 0; + const char* end = str; + while((*end)!=0 && (*end)==' ') ++end; + const char* start = end; + while((*start)!=0) + { + if (*end!=' ' && *end!=0) + { + ++end; + } + else + { + if (start!=end) + { + if (end-start>1 && *start=='%') + { + const char type = *(start+1); + switch(type) + { + // expecting an integer + case('i') : + { + if (!field(fieldCount).isInt()) return false; + break; + } + // expecting an floating point number + case('f') : + { + if (!field(fieldCount).isFloat()) return false; + break; + } + // expecting an quoted string + case('s') : + { + if (!field(fieldCount).isQuotedString()) return false; + break; + } + default :// expecting an word + { + if (!field(fieldCount).isWord()) return false; + break; + } + } + + } + else + { + if (*start=='{') + { + if (!field(fieldCount).isOpenBracket()) return false; + } + else if (*start=='}') + { + if (!field(fieldCount).isCloseBracket()) return false; + } + else + { + if (!field(fieldCount).matchWord(start,end-start)) return false; + } + } + fieldCount++; + } + while((*end)==' ') ++end; + start = end; + } + } + return true; +} diff --git a/src/osgDB/FileNameUtils.cpp b/src/osgDB/FileNameUtils.cpp new file mode 100644 index 000000000..abe9d3904 --- /dev/null +++ b/src/osgDB/FileNameUtils.cpp @@ -0,0 +1,91 @@ +#include "osgDB/FileNameUtils" + + +// mac requires std::tolower, but IRIX MipsPro doesn't like it, +// so use this preprocessor to allow mac and mipspro to work. +#ifdef macintosh +using std::tolower; +using std::strlen; +#endif + +std::string osgDB::getFilePath(const std::string& fileName) +{ + std::string::size_type slash = fileName.find_last_of('/'); + if (slash==std::string::npos) return std::string(""); + return std::string(fileName.begin(),fileName.begin()+slash+1); +} + + +std::string osgDB::getSimpleFileName(const std::string& fileName) +{ + std::string::size_type slash = fileName.find_last_of('/'); + if (slash==std::string::npos) return fileName; + return std::string(fileName.begin()+slash+1,fileName.end()); +} + + +std::string osgDB::getFileExtension(const std::string& fileName) +{ + std::string::size_type dot = fileName.find_last_of('.'); + if (dot==std::string::npos) return std::string(""); + return std::string(fileName.begin()+dot+1,fileName.end()); +} + + +std::string osgDB::getLowerCaseFileExtension(const std::string& filename) +{ + std::string ext = osgDB::getFileExtension(filename); + for(std::string::iterator itr=ext.begin(); + itr!=ext.end(); + ++itr) + { + *itr = tolower(*itr); + } + return ext; +} + + +std::string osgDB::getStrippedName(const std::string& fileName) +{ + std::string::size_type slash = fileName.find_last_of('/'); + std::string::size_type dot = fileName.find_last_of('.'); + if (slash==std::string::npos) + { + if (dot==std::string::npos) return fileName; + else return std::string(fileName.begin(),fileName.begin()+dot); + } + else + { + if (dot==std::string::npos) return std::string(fileName.begin()+slash+1,fileName.end()); + else return std::string(fileName.begin()+slash+1,fileName.begin()+dot); + } +} + + +bool osgDB::equalCaseInsensitive(const std::string& lhs,const std::string& rhs) +{ + if (lhs.size()!=rhs.size()) return false; + std::string::const_iterator litr = lhs.begin(); + std::string::const_iterator ritr = rhs.begin(); + while (litr!=lhs.end()) + { + if (tolower(*litr)!=tolower(*ritr)) return false; + ++litr; + ++ritr; + } + return true; +} + +bool osgDB::equalCaseInsensitive(const std::string& lhs,const char* rhs) +{ + if (rhs==NULL || lhs.size()!=strlen(rhs)) return false; + std::string::const_iterator litr = lhs.begin(); + const char* cptr = rhs; + while (litr!=lhs.end()) + { + if (tolower(*litr)!=tolower(*cptr)) return false; + ++litr; + ++cptr; + } + return true; +} diff --git a/src/osgDB/FileUtils.cpp b/src/osgDB/FileUtils.cpp new file mode 100644 index 000000000..13a57db0a --- /dev/null +++ b/src/osgDB/FileUtils.cpp @@ -0,0 +1,355 @@ +#ifdef WIN32 +#include +#include +#include +#elif !defined(macintosh) // UNIX +#include +#include +#endif + +#include +#include + +#include "osg/Notify" +#include "osg/Node" +#include "osg/Geode" +#include "osg/Group" + +#include "osgDB/FileUtils" +#include "osgDB/FileNameUtils" +#include "osgDB/Registry" + +using namespace osg; +using namespace osgDB; + +// follows is definition of strdup for compatibility under mac, +// However, I'd prefer to migrate all the findFindInPath tools to use +// std::string's and then be able to remove the following definition. +// My objective is to minimize the number of platform #ifdef's as they +// are source of potential bugs and developer confusion. +#ifdef macintosh +#ifndef strdup +inline static char* strdup(const char *src); + +inline static char* strdup(const char *src) +{ + char *ret = (char *) std::malloc(std::strlen(src) +1); + if(!ret) return NULL; + + return std::strcpy(ret, src); +} +#endif +#endif + +#ifdef WIN32 +char *PathDelimitor = ";"; +static const char *s_default_file_path = ".;"; +static const char *s_default_dso_path = "C:/Windows/System/"; +static char *s_filePath = ".;"; +#elif macintosh +char *PathDelimitor = " "; +static const char *s_default_file_path = ":"; +static const char *s_default_dso_path = ":"; +static char *s_filePath = ":"; +#elif __sgi +char *PathDelimitor = ":"; +static const char *s_default_file_path = ".:"; +static const char *s_default_dso_path = "/usr/lib32/osgPlugins/"; +static char *s_filePath = ".:"; +#else +char *PathDelimitor = ":"; +static const char *s_default_file_path = ".:"; +static const char *s_default_dso_path = "/usr/lib/osgPlugins/"; +static char *s_filePath = ".:"; +#endif + + +void osgDB::initFilePath( void ) +{ + char *ptr; + if( (ptr = getenv( "OSGFILEPATH" )) ) + { + notify(DEBUG_INFO) << "osgDB::Init("< + +osgDB::DirectoryContents osgDB::getDirectoryContents(const std::string& dirName) +{ + osgDB::DirectoryContents contents; + + DIR *handle = opendir(dirName.c_str()); + if (handle) + { + dirent *rc; + while((rc = readdir(handle))!=NULL) + { + contents.push_back(rc->d_name); + } + closedir(handle); + } + + return contents; +} +#endif diff --git a/src/osgDB/Input.cpp b/src/osgDB/Input.cpp new file mode 100644 index 000000000..82db0d2b1 --- /dev/null +++ b/src/osgDB/Input.cpp @@ -0,0 +1,76 @@ +#include + +#include +#include + +using namespace osgDB; + +Input::Input() +{ +} + + +Input::~Input() +{ +} + + +osg::Object* Input::getObjectForUniqueID(const std::string& uniqueID) +{ + UniqueIDToObjectMapping::iterator fitr = _uniqueIDToObjectMap.find(uniqueID); + if (fitr != _uniqueIDToObjectMap.end()) return (*fitr).second; + else return NULL; +} + + +void Input::regisiterUniqueIDForObject(const std::string& uniqueID,osg::Object* obj) +{ + _uniqueIDToObjectMap[uniqueID] = obj; +} + + +osg::Object* Input::readObjectOfType(const osg::Object& compObj) +{ + return Registry::instance()->readObjectOfType(compObj,*this); +} + +osg::Object* Input::readObject() +{ + return Registry::instance()->readObject(*this); +} + + +osg::Image* Input::readImage() +{ + return Registry::instance()->readImage(*this); +} + +osg::Drawable* Input::readDrawable() +{ + return Registry::instance()->readDrawable(*this); +} + +osg::StateAttribute* Input::readStateAttribute() +{ + return Registry::instance()->readStateAttribute(*this); +} + +osg::Node* Input::readNode() +{ + return Registry::instance()->readNode(*this); +} + +osg::Object* Input::readObject(const std::string& fileName) +{ + return Registry::instance()->readObject(fileName); +} + +osg::Image* Input::readImage(const std::string& fileName) +{ + return Registry::instance()->readImage(fileName); +} + +osg::Node* Input::readNode(const std::string& fileName) +{ + return Registry::instance()->readNode(fileName); +} diff --git a/src/osgDB/Makedepend b/src/osgDB/Makedepend new file mode 100644 index 000000000..e69de29bb diff --git a/src/osgDB/Makefile b/src/osgDB/Makefile new file mode 100644 index 000000000..2f36b5ee8 --- /dev/null +++ b/src/osgDB/Makefile @@ -0,0 +1,51 @@ +#!smake +include ../../Make/makedefs + +C++FILES = \ + DynamicLibrary.cpp\ + FileNameUtils.cpp\ + FileUtils.cpp\ + ReadFile.cpp\ + Registry.cpp\ + Version.cpp\ + WriteFile.cpp\ + Input.cpp\ + Output.cpp\ + Field.cpp\ + FieldReader.cpp\ + FieldReaderIterator.cpp\ + DotOsgWrapper.cpp\ + + +TARGET_BASENAME = osgDB + +TARGET_LIB_FILES = lib$(TARGET_BASENAME).so + +TARGET_INCLUDE_FILES = \ + osgDB/DynamicLibrary\ + osgDB/Export\ + osgDB/FileNameUtils\ + osgDB/FileUtils\ + osgDB/ReaderWriter\ + osgDB/ReadFile\ + osgDB/Registry\ + osgDB/Version\ + osgDB/WriteFile\ + osgDB/Input\ + osgDB/Output\ + osgDB/Field\ + osgDB/FieldReader\ + osgDB/FieldReaderIterator\ + osgDB/DotOsgWrapper\ + + +#LIBS = -L../../lib -losg -lGLU -lGL -lm -ldl +LIBS = -L../../lib -losg -lGLU -lGL -lm $(DYNAMICLIBRARYLIB) + +LIB = ../../lib/lib$(TARGET_BASENAME).so +#LIB = ../../lib/lib$(TARGET_BASENAME).a + +C++FLAGS += -I ../../include + +include ../../Make/makerules + diff --git a/src/osgDB/Output.cpp b/src/osgDB/Output.cpp new file mode 100644 index 000000000..436ef04f2 --- /dev/null +++ b/src/osgDB/Output.cpp @@ -0,0 +1,124 @@ +#include +#include +#include + +#include + +#include + +using namespace osgDB; + +Output::Output() +{ + init(); +} + +Output::Output(const char* name) : ofstream(name) +{ + init(); + _filename = name; +} + +Output::~Output() +{ +} + + +void Output::init() +{ + _indent = 0; + _indentStep = 2; + _numIndicesPerLine = 10; + _pathNameHint = AS_IS; +} + +void Output::open(const char *name) +{ + init(); + ofstream::open(name); + _filename = name; +} + +void Output::open(const char *name,int mode) +{ + init(); + ofstream::open(name,mode); + _filename = name; +} + +Output& Output::indent() +{ + for(int i=0;i<_indent;++i) *this<<' '; + return *this; +} + + +void Output::moveIn() +{ + _indent += _indentStep; +} + + +void Output::moveOut() +{ + _indent -= _indentStep; + if (_indent<0) _indent=0; +} + +bool Output::writeObject(const osg::Object& obj) +{ + return Registry::instance()->writeObject(obj,*this); +} + +bool Output::getUniqueIDForObject(const osg::Object* obj,std::string& uniqueID) +{ + UniqueIDToLabelMapping::iterator fitr = _objectToUniqueIDMap.find(obj); + if (fitr != _objectToUniqueIDMap.end()) + { + uniqueID = (*fitr).second; + return true; + } + else return false; +} + + +bool Output::createUniqueIDForObject(const osg::Object* obj,std::string& uniqueID) +{ + char str[256]; + sprintf(str,"%s_%i",obj->className(),_objectToUniqueIDMap.size()); + uniqueID = str; + return true; +} + + +bool Output::registerUniqueIDForObject(const osg::Object* obj,std::string& uniqueID) +{ + _objectToUniqueIDMap[obj] = uniqueID; + return true; +} + +const std::string Output::getFileNameForOutput(const std::string& filename) const +{ + switch(_pathNameHint) + { + case(FULL_PATH): + { + // need to think about how best to implement this first... + osg::notify(osg::WARN)<<"Warning: Output::getFileNameForOutput() does not support FULL_PATH yet."<readObject(filename); +} + + +Image* osgDB::readImageFile(const std::string& filename) +{ + return Registry::instance()->readImage(filename); +} + + +Node* osgDB::readNodeFile(const std::string& filename) +{ + return Registry::instance()->readNode(filename); +} diff --git a/src/osgDB/Registry.cpp b/src/osgDB/Registry.cpp new file mode 100644 index 000000000..93d02da30 --- /dev/null +++ b/src/osgDB/Registry.cpp @@ -0,0 +1,822 @@ + +#include "osg/Notify" +#include "osg/Object" +#include "osg/Image" +#include "osg/Node" +#include "osg/Group" +#include "osg/Geode" + +#include "osgDB/Registry" +#include "osgDB/FileUtils" +#include "osgDB/FileNameUtils" + +#include + +#include +#include + +using namespace osg; +using namespace osgDB; + + +class RegistryPtr +{ + public: + RegistryPtr() : _ptr(0L) {} + RegistryPtr(Registry* t): _ptr(t) {} + RegistryPtr(const RegistryPtr& rp):_ptr(rp._ptr) { } + ~RegistryPtr() { if (_ptr) delete _ptr; _ptr=0L; } + + inline Registry* get() { return _ptr; } + + Registry* _ptr; +}; + +// definition of the Registry +Registry::Registry() +{ + notify(INFO) << "Constructing osg::Registry"<getName()<<")"<getAssociates(); + + for(DotOsgWrapper::Associates::const_iterator itr=assoc.begin(); + itr!=assoc.end(); + ++itr) + { + notify(INFO) << " ("<<*itr<<")"<getName(); + const osg::Object* proto = wrapper->getPrototype(); + + _objectWrapperMap[name] = wrapper; + + if (proto) + { + if (wrapper->getReadWriteMode()==DotOsgWrapper::READ_AND_WRITE) _classNameWrapperMap[proto->className()] = wrapper; + + if (dynamic_cast(proto)) _imageWrapperMap[name] = wrapper; + if (dynamic_cast(proto)) _drawableWrapperMap[name] = wrapper; + if (dynamic_cast(proto)) _stateAttrWrapperMap[name] = wrapper; + if (dynamic_cast(proto)) _nodeWrapperMap[name] = wrapper; + } +} + +#define EraseMacro(WL,W) \ +{ \ + DotOsgWrapperMap::iterator itr = WL.find(W->getName()); \ + if (itr!=WL.end() && itr->second.get()==W) WL.erase(itr); \ +} + +void Registry::removeDotOsgWrapper(DotOsgWrapper* wrapper) +{ + if (wrapper==0L) return; + +//// notify(INFO) << "osg::Registry::removeReaderWriter();"<className()<<")"<second); + +#ifdef WIN32 +# ifdef _DEBUG + return "osgdb_"+ext+"d.dll"; +# else + return "osgdb_"+ext+".dll"; +# endif +#elif macintosh + return "osgdb_"+ext; +#else + return "osgdb_"+ext+".so"; +#endif + +} + + +bool Registry::loadLibrary(const std::string& fileName) +{ + DynamicLibrary* dl = getLibrary(fileName); + if (dl) return false; + + _openingLibrary=true; + + dl = DynamicLibrary::loadLibrary(fileName); + _openingLibrary=false; + + if (dl) + { + dl->ref(); + _dlList.push_back(dl); + return true; + } + return false; +} + + +bool Registry::closeLibrary(const std::string& fileName) +{ + DynamicLibraryList::iterator ditr = getLibraryItr(fileName); + if (ditr!=_dlList.end()) + { + _dlList.erase(ditr); + return true; + } + return false; +} + + +Registry::DynamicLibraryList::iterator Registry::getLibraryItr(const std::string& fileName) +{ + DynamicLibraryList::iterator ditr = _dlList.begin(); + for(;ditr!=_dlList.end();++ditr) + { + if ((*ditr)->getName()==fileName) return ditr; + } + return _dlList.end(); +} + + +DynamicLibrary* Registry::getLibrary(const std::string& fileName) +{ + DynamicLibraryList::iterator ditr = getLibraryItr(fileName); + if (ditr!=_dlList.end()) return ditr->get(); + else return NULL; +} + +osg::Object* Registry::readObjectOfType(const osg::Object& compObj,Input& fr) +{ + const char *str = fr[0].getStr(); + if (str==NULL) return NULL; + + if (fr[0].matchWord("Use")) + { + if (fr[1].isString()) + { + Object* obj = fr.getObjectForUniqueID(fr[1].getStr()); + if (compObj.isSameKindAs(obj)) fr+=2; + return obj; + } + else return NULL; + + } + + std::string name = str; + DotOsgWrapperMap::iterator itr = _objectWrapperMap.find(name); + if (itr!=_objectWrapperMap.end() && fr[1].isOpenBracket()) + { + + DotOsgWrapper* wrapper = itr->second.get(); + const osg::Object* proto = wrapper->getPrototype(); + if (proto==NULL) + { + osg::notify(osg::WARN)<<"Token "<getAssociates(); + osg::Object* obj = proto->clone(); + + while(!fr.eof() && fr[0].getNoNestedBrackets()>entry) + { + bool iteratorAdvanced = false; + if (fr[0].matchWord("UniqueID") && fr[1].isString()) + { + fr.regisiterUniqueIDForObject(fr[1].getStr(),obj); + fr += 2; + iteratorAdvanced = true; + } + + // read the local data by iterating through the associate + // list, mapping the associate names to DotOsgWrapper's which + // in turn have the appropriate functions. + for(DotOsgWrapper::Associates::const_iterator aitr=assoc.begin(); + aitr!=assoc.end(); + ++aitr) + { + DotOsgWrapperMap::iterator mitr = _objectWrapperMap.find(*aitr); + if (mitr!=_objectWrapperMap.end()) + { + // get the function to read the data... + DotOsgWrapper::ReadFunc rf = mitr->second->getReadFunc(); + if (rf && (*rf)(*obj,fr)) iteratorAdvanced = true; + } + + } + + if (!iteratorAdvanced) ++fr; + } + ++fr; // step over trailing '}' + + return obj; + + } + + return 0L; + +} + +// +// read object from input iterator. +// +osg::Object* Registry::readObject(DotOsgWrapperMap& dowMap,Input& fr) +{ + const char *str = fr[0].getStr(); + if (str==NULL) return NULL; + + std::string name = str; + DotOsgWrapperMap::iterator itr = dowMap.find(name); + if (itr!=dowMap.end() && fr[1].isOpenBracket()) + { + + DotOsgWrapper* wrapper = itr->second.get(); + const osg::Object* proto = wrapper->getPrototype(); + if (proto==NULL) + { + osg::notify(osg::WARN)<<"Token "<getAssociates(); + osg::Object* obj = proto->clone(); + + while(!fr.eof() && fr[0].getNoNestedBrackets()>entry) + { + bool iteratorAdvanced = false; + if (fr[0].matchWord("UniqueID") && fr[1].isString()) + { + fr.regisiterUniqueIDForObject(fr[1].getStr(),obj); + fr += 2; + iteratorAdvanced = true; + } + + // read the local data by iterating through the associate + // list, mapping the associate names to DotOsgWrapper's which + // in turn have the appropriate functions. + for(DotOsgWrapper::Associates::const_iterator aitr=assoc.begin(); + aitr!=assoc.end(); + ++aitr) + { + DotOsgWrapperMap::iterator mitr = _objectWrapperMap.find(*aitr); + if (mitr!=_objectWrapperMap.end()) + { + // get the function to read the data... + DotOsgWrapper::ReadFunc rf = mitr->second->getReadFunc(); + if (rf && (*rf)(*obj,fr)) iteratorAdvanced = true; + } + + } + + if (!iteratorAdvanced) ++fr; + } + ++fr; // step over trailing '}' + + return obj; + + } + + return 0L; +} + +// +// read object from input iterator. +// +Object* Registry::readObject(Input& fr) +{ + if (fr[0].matchWord("Use")) + { + if (fr[1].isString()) + { + Object* obj = fr.getObjectForUniqueID(fr[1].getStr()); + if (obj) fr+=2; + return obj; + } + else return NULL; + + } + + return readObject(_objectWrapperMap,fr); +} + + +// +// read image from input iterator. +// +Image* Registry::readImage(Input& fr) +{ + if (fr[0].matchWord("Use")) + { + if (fr[1].isString()) + { + Image* image = dynamic_cast(fr.getObjectForUniqueID(fr[1].getStr())); + if (image) fr+=2; + return image; + } + else return NULL; + + } + + return dynamic_cast(readObject(_imageWrapperMap,fr)); +} + + +// +// read drawable from input iterator. +// +Drawable* Registry::readDrawable(Input& fr) +{ + if (fr[0].matchWord("Use")) + { + if (fr[1].isString()) + { + Drawable* drawable = dynamic_cast(fr.getObjectForUniqueID(fr[1].getStr())); + if (drawable) fr+=2; + return drawable; + } + else return NULL; + + } + + return dynamic_cast(readObject(_drawableWrapperMap,fr)); +} + +// +// read drawable from input iterator. +// +StateAttribute* Registry::readStateAttribute(Input& fr) +{ + + if (fr[0].matchWord("Use")) + { + if (fr[1].isString()) + { + StateAttribute* attribute = dynamic_cast(fr.getObjectForUniqueID(fr[1].getStr())); + if (attribute) fr+=2; + return attribute; + } + else return NULL; + + } + + return dynamic_cast(readObject(_stateAttrWrapperMap,fr)); +} + +// +// read node from input iterator. +// +Node* Registry::readNode(Input& fr) +{ + if (fr[0].matchWord("Use")) + { + if (fr[1].isString()) + { + Node* node = dynamic_cast(fr.getObjectForUniqueID(fr[1].getStr())); + if (node) fr+=2; + return node; + } + else return NULL; + + } + + return dynamic_cast(readObject(_nodeWrapperMap,fr)); +} + +// +// Write object to output +// +bool Registry::writeObject(const osg::Object& obj,Output& fw) +{ + + if (obj.referenceCount()>1) + { + std::string uniqueID; + if (fw.getUniqueIDForObject(&obj,uniqueID)) + { + fw.indent() << "Use " << uniqueID << endl; + return true; + } + } + + std::string classname = obj.className(); + DotOsgWrapperMap::iterator itr = _classNameWrapperMap.find(classname); + if (itr!=_classNameWrapperMap.end()) + { + + + DotOsgWrapper* wrapper = itr->second.get(); + const DotOsgWrapper::Associates& assoc = wrapper->getAssociates(); + + fw.indent() << wrapper->getName() << " {"<1) + { + std::string uniqueID; + fw.createUniqueIDForObject(&obj,uniqueID); + fw.registerUniqueIDForObject(&obj,uniqueID); + fw.indent() << "UniqueID " << uniqueID << endl; + } + + // read the local data by iterating through the associate + // list, mapping the associate names to DotOsgWrapper's which + // in turn have the appropriate functions. + for(DotOsgWrapper::Associates::const_iterator aitr=assoc.begin(); + aitr!=assoc.end(); + ++aitr) + { + DotOsgWrapperMap::iterator mitr = _objectWrapperMap.find(*aitr); + if (mitr!=_objectWrapperMap.end()) + { + // get the function to read the data... + DotOsgWrapper::WriteFunc wf = mitr->second->getWriteFunc(); + if (wf) (*wf)(obj,fw); + } + + } + + fw.moveOut(); + fw.indent() << "}"< rwOriginal; + + // first attempt to load the file from existing ReaderWriter's + for(ReaderWriterList::iterator itr=_rwList.begin(); + itr!=_rwList.end(); + ++itr) + { + rwOriginal.insert(itr->get()); + Object* obj = (*itr)->readObject(file); + if (obj) return obj; + } + + // now look for a plug-in to load the file. + std::string libraryName = createLibraryNameForFile(fileName); + if (Registry::instance()->loadLibrary(libraryName)) + { + for(ReaderWriterList::iterator itr=_rwList.begin(); + itr!=_rwList.end(); + ++itr) + { + if (rwOriginal.find(itr->get())==rwOriginal.end()) + { + Object* obj = (*itr)->readObject(file); + if (obj) return obj; + } + } + } + else + { + notify(NOTICE)<<"Warning: Could not find plugin to read file with extension ." + < rwOriginal; + + // first attempt to load the file from existing ReaderWriter's + for(ReaderWriterList::iterator itr=_rwList.begin(); + itr!=_rwList.end(); + ++itr) + { + rwOriginal.insert(itr->get()); + if ((*itr)->writeObject(obj,fileName)) return true; + } + + // now look for a plug-in to save the file. + std::string libraryName = createLibraryNameForFile(fileName); + if (loadLibrary(libraryName)) + { + for(ReaderWriterList::iterator itr=_rwList.begin(); + itr!=_rwList.end(); + ++itr) + { + if (rwOriginal.find(itr->get())==rwOriginal.end()) + { + if ((*itr)->writeObject(obj,fileName)) return true; + } + } + } + else + { + notify(NOTICE)<<"Warning: Could not find plugin to write file with extension ." + < rwOriginal; + + // first attempt to load the file from existing ReaderWriter's + for(ReaderWriterList::iterator itr=_rwList.begin(); + itr!=_rwList.end(); + ++itr) + { + rwOriginal.insert(itr->get()); + Image* image = (*itr)->readImage(file); + if (image) return image; + } + + // now look for a plug-in to load the file. + std::string libraryName = createLibraryNameForFile(fileName); + if (loadLibrary(libraryName)) + { + for(ReaderWriterList::iterator itr=_rwList.begin(); + itr!=_rwList.end(); + ++itr) + { + if (rwOriginal.find(itr->get())==rwOriginal.end()) + { + Image* image = (*itr)->readImage(file); + if (image) return image; + } + } + } + else + { + notify(NOTICE)<<"Warning: Could not find plugin to read file with extension ." + < rwOriginal; + + // first attempt to load the file from existing ReaderWriter's + for(ReaderWriterList::iterator itr=_rwList.begin(); + itr!=_rwList.end(); + ++itr) + { + rwOriginal.insert(itr->get()); + if ((*itr)->writeImage(image,fileName)) return true; + } + + // now look for a plug-in to save the file. + std::string libraryName = createLibraryNameForFile(fileName); + if (loadLibrary(libraryName)) + { + for(ReaderWriterList::iterator itr=_rwList.begin(); + itr!=_rwList.end(); + ++itr) + { + if (rwOriginal.find(itr->get())==rwOriginal.end()) + { + if ((*itr)->writeImage(image,fileName)) return true; + } + } + } + else + { + notify(NOTICE)<<"Warning: Could not find plugin to write file with extension ." + < rwOriginal; + + // first attempt to load the file from existing ReaderWriter's + for(ReaderWriterList::iterator itr=_rwList.begin(); + itr!=_rwList.end(); + ++itr) + { + rwOriginal.insert(itr->get()); + Node* node = (*itr)->readNode(file); + if (node) return node; + } + + bool couldNotFindPlugin = false; + + // now look for a plug-in to load the file. + std::string libraryName = createLibraryNameForFile(fileName); + notify(INFO) << "Now checking for plug-in "<get())==rwOriginal.end()) + { + Node* node = (*itr)->readNode(file); + if (node) return node; + } + } + } + else + { + couldNotFindPlugin = true; + } + + if (_createNodeFromImage) + { + ref_ptr image = readImage(fileName); + if (image.valid()) + { + return createGeodeForImage(image.get()); + } + } + + if (couldNotFindPlugin) + { + notify(NOTICE)<<"Warning: Could not find plugin to read file with extension ." + < rwOriginal; + + // first attempt to write the file from existing ReaderWriter's + for(ReaderWriterList::iterator itr=_rwList.begin(); + itr!=_rwList.end(); + ++itr) + { + rwOriginal.insert(itr->get()); + if ((*itr)->writeNode(node,fileName)) return true; + } + + // now look for a plug-in to save the file. + std::string libraryName = createLibraryNameForFile(fileName); + if (Registry::instance()->loadLibrary(libraryName)) + { + for(ReaderWriterList::iterator itr=_rwList.begin(); + itr!=_rwList.end(); + ++itr) + { + if (rwOriginal.find(itr->get())==rwOriginal.end()) + { + if ((*itr)->writeNode(node,fileName)) return true; + } + } + } + else + { + notify(NOTICE)<<"Warning: Could not find plugin to write file with extension ." + <writeObject(object,filename); +} + + +bool osgDB::writeImageFile(const Image& image,const std::string& filename) +{ + return Registry::instance()->writeImage(image,filename); +} + + +bool osgDB::writeNodeFile(const Node& node,const std::string& filename) +{ + return Registry::instance()->writeNode(node,filename); +} diff --git a/src/osgGLUT/GLUTEventAdapter.cpp b/src/osgGLUT/GLUTEventAdapter.cpp index d718f5ae4..92ebd1301 100644 --- a/src/osgGLUT/GLUTEventAdapter.cpp +++ b/src/osgGLUT/GLUTEventAdapter.cpp @@ -15,18 +15,19 @@ int GLUTEventAdapter::_s_my = 0; GLUTEventAdapter::GLUTEventAdapter() { - _eventType = NONE; // adaptor does not encapsulate any events. - _key = -1; // set to 'invalid' key value. - _button = -1; // set to 'invalid' button value. - _mx = -1; // set to 'invalid' position value. - _my = -1; // set to 'invalid' position value. - _buttonMask = 0; // default to no mouse buttons being pressed. - _time = 0.0f; // default to no time has been set. + _eventType = NONE; // adaptor does not encapsulate any events. + _key = -1; // set to 'invalid' key value. + _button = -1; // set to 'invalid' button value. + _mx = -1; // set to 'invalid' position value. + _my = -1; // set to 'invalid' position value. + _buttonMask = 0; // default to no mouse buttons being pressed. + _time = 0.0f; // default to no time has been set. copyStaticVariables(); } + void GLUTEventAdapter::copyStaticVariables() { _buttonMask = _s_accumulatedButtonMask; @@ -38,6 +39,7 @@ void GLUTEventAdapter::copyStaticVariables() _my = _s_my; } + void GLUTEventAdapter::setWindowSize(int Xmin, int Ymin, int Xmax, int Ymax) { _s_Xmin = Xmin; @@ -46,6 +48,7 @@ void GLUTEventAdapter::setWindowSize(int Xmin, int Ymin, int Xmax, int Ymax) _s_Ymax = Ymax; } + void GLUTEventAdapter::setButtonMask(unsigned int buttonMask) { _s_accumulatedButtonMask = buttonMask; @@ -60,6 +63,7 @@ void GLUTEventAdapter::adaptResize(float time, int Xmin, int Ymin, int Xmax, int copyStaticVariables(); } + /** method for adapting mouse motion events whilst mouse buttons are pressed.*/ void GLUTEventAdapter::adaptMouseMotion(float time, int x, int y) { @@ -70,6 +74,7 @@ void GLUTEventAdapter::adaptMouseMotion(float time, int x, int y) copyStaticVariables(); } + /** method for adapting mouse motion events whilst no mouse button are pressed.*/ void GLUTEventAdapter::adaptMousePassiveMotion(float time, int x, int y) { @@ -80,12 +85,12 @@ void GLUTEventAdapter::adaptMousePassiveMotion(float time, int x, int y) copyStaticVariables(); } + /** method for adapting mouse button pressed/released events.*/ void GLUTEventAdapter::adaptMouse(float time, int button, int state, int x, int y) { _time = time; - if( state == GLUT_DOWN ) { @@ -94,9 +99,9 @@ void GLUTEventAdapter::adaptMouse(float time, int button, int state, int x, int switch(button) { - case(GLUT_LEFT_BUTTON): _s_accumulatedButtonMask = _s_accumulatedButtonMask | LEFT_BUTTON; break; - case(GLUT_MIDDLE_BUTTON): _s_accumulatedButtonMask = _s_accumulatedButtonMask | MIDDLE_BUTTON; break; - case(GLUT_RIGHT_BUTTON): _s_accumulatedButtonMask = _s_accumulatedButtonMask | RIGHT_BUTTON; break; + case(GLUT_LEFT_BUTTON): _s_accumulatedButtonMask = _s_accumulatedButtonMask | LEFT_BUTTON; break; + case(GLUT_MIDDLE_BUTTON): _s_accumulatedButtonMask = _s_accumulatedButtonMask | MIDDLE_BUTTON; break; + case(GLUT_RIGHT_BUTTON): _s_accumulatedButtonMask = _s_accumulatedButtonMask | RIGHT_BUTTON; break; } } @@ -108,19 +113,20 @@ void GLUTEventAdapter::adaptMouse(float time, int button, int state, int x, int switch(button) { - case(GLUT_LEFT_BUTTON): _s_accumulatedButtonMask = _s_accumulatedButtonMask & ~LEFT_BUTTON; break; - case(GLUT_MIDDLE_BUTTON): _s_accumulatedButtonMask = _s_accumulatedButtonMask & ~MIDDLE_BUTTON; break; - case(GLUT_RIGHT_BUTTON): _s_accumulatedButtonMask = _s_accumulatedButtonMask & ~RIGHT_BUTTON; break; + case(GLUT_LEFT_BUTTON): _s_accumulatedButtonMask = _s_accumulatedButtonMask & ~LEFT_BUTTON; break; + case(GLUT_MIDDLE_BUTTON): _s_accumulatedButtonMask = _s_accumulatedButtonMask & ~MIDDLE_BUTTON; break; + case(GLUT_RIGHT_BUTTON): _s_accumulatedButtonMask = _s_accumulatedButtonMask & ~RIGHT_BUTTON; break; } } - + _s_mx = x; _s_my = y; copyStaticVariables(); } + /** method for adapting keyboard events.*/ void GLUTEventAdapter::adaptKeyboard(float time, unsigned char key, int x, int y ) { @@ -129,16 +135,16 @@ void GLUTEventAdapter::adaptKeyboard(float time, unsigned char key, int x, int y _key = key; _s_mx = x; _s_my = y; - + copyStaticVariables(); } + /** method for adapting frame events, i.e. iddle/display callback.*/ void GLUTEventAdapter::adaptFrame(float time) { _eventType = FRAME; _time = time; - + copyStaticVariables(); } - diff --git a/src/osgGLUT/Makefile b/src/osgGLUT/Makefile index 7e2936e7e..20fb492a0 100644 --- a/src/osgGLUT/Makefile +++ b/src/osgGLUT/Makefile @@ -9,7 +9,7 @@ C++FILES = \ TARGET_BASENAME = osgGLUT -LIBS = -ldl +LIBS = -L../../lib -losgDB -losgUtil -losg $(GLUTLIB) -lGLU -lGL -lm LIB = ../../lib/lib$(TARGET_BASENAME).so #LIB = ../../lib/lib$(TARGET_BASENAME).a @@ -17,8 +17,9 @@ LIB = ../../lib/lib$(TARGET_BASENAME).so TARGET_LIB_FILES = lib$(TARGET_BASENAME).so TARGET_INCLUDE_FILES = \ osgGLUT/Export\ - osgGLUT/Viewer\ osgGLUT/GLUTEventAdapter\ + osgGLUT/Version\ + osgGLUT/Viewer\ C++FLAGS += -I ../../include diff --git a/src/osgGLUT/Version.cpp b/src/osgGLUT/Version.cpp index 311dae185..cb53aa913 100755 --- a/src/osgGLUT/Version.cpp +++ b/src/osgGLUT/Version.cpp @@ -1,11 +1,11 @@ #include "osgGLUT/Version" - const char* osgGLUTGetVersion() { - return "0.8.34"; + return "0.8.42"; } + const char* osgGLUTGetLibraryName() { return "Open Scene Graph GLUT Library"; diff --git a/src/osgGLUT/Viewer.cpp b/src/osgGLUT/Viewer.cpp index b14d31ef4..1835dfa09 100644 --- a/src/osgGLUT/Viewer.cpp +++ b/src/osgGLUT/Viewer.cpp @@ -1,35 +1,40 @@ +#if defined(_MSC_VER) + #pragma warning( disable : 4786 ) +#endif + #include -#ifndef WIN32 +#if !defined(WIN32) && !defined(macintosh) #include #include #endif #include #include +#include + #include "osgGLUT/Viewer" #include "osgGLUT/GLUTEventAdapter" -#include -#include -#include #include #include #include -#include #include #include #include #include -#include -#include -#include #include -#include +#include +#include +#include #include -#include +#include + #include #include +#include +#include +#include #include #include @@ -38,7 +43,6 @@ #include #include - #ifdef WIN32 #define USE_FLTK #define USE_GLUT @@ -55,8 +59,11 @@ osg::Timer g_timer; osg::Timer_t g_initTime; -static GLenum polymodes [] = { GL_FILL, GL_LINE, GL_POINT }; +//static GLenum polymodes [] = { GL_FILL, GL_LINE, GL_POINT }; +static osg::PolygonMode::Mode polymodes [] = { osg::PolygonMode::FILL, osg::PolygonMode::LINE, osg::PolygonMode::POINT }; +using namespace osg; +using namespace osgUtil; using namespace osgGLUT; Viewer* Viewer::s_theViewer = 0; @@ -65,23 +72,25 @@ Viewer::Viewer() { s_theViewer = this; - - fullscreen = false; + fullscreen = false; + _is_open = 0; + _saved_wx = wx = _saved_wy = wy = 0; _saved_ww = ww = 1024, _saved_wh = wh = 768; + _title = "OSG Viewer"; + mx = ww/2, my = wh/2; mbutton = 0; - polymode = 0; texture = 1; backface = 1; lighting = 1; flat_shade = 0; - _printStats = false; + _printStats = 0; // gwm change from bool was : false; #ifdef SGV_USE_RTFS fs = new RTfs( RTFS_MODE_RTC_SPIN ); @@ -98,21 +107,18 @@ Viewer::Viewer() _saveFileName = "saved_model.osg"; - - _sceneView = new osgUtil::SceneView; - _sceneView->setDefaults(); - - registerCameraManipulator(new osgUtil::TrackballManipulator); - registerCameraManipulator(new osgUtil::FlightManipulator); - registerCameraManipulator(new osgUtil::DriveManipulator); - osg::notify(osg::INFO)<<"Scene Graph Viewer (sgv)"<_cameraManipList.empty()) + { + osg::notify(osg::NOTICE)<<"osgGLUT::Viewer::open() called without any camara manipulators registered for a viewport,"<_cameraManipulator.valid()) + selectCameraManipulator(0,index); + } + + GLUTEventAdapter::setWindowSize( wx, wy, ww, wh ); GLUTEventAdapter::setButtonMask(0); - _sceneView->setViewport(0,0,ww,wh); + // Set the absolute viewport for each SceneView based on the + // relative viewport coordinates given to us + for(itr=_viewportList.begin(); + itr!=_viewportList.end(); + ++itr) + { + osgUtil::SceneView* sceneView = itr->sceneView.get(); + int view[4] = { int(itr->viewport[0]*ww), int(itr->viewport[1]*wh), + int(itr->viewport[2]*ww), int(itr->viewport[3]*wh) }; + + sceneView->setViewport(view[0], view[1], view[2], view[3]); + + osg::ref_ptr ea = new GLUTEventAdapter; + ea->adaptResize(clockSeconds(), + view[0], view[1], + view[0]+view[2], view[1]+view[3]); + + if (itr->_cameraManipulator->handle(*ea,*this)) + { + // osg::notify(osg::INFO) << "Handled reshape "<sceneView->getSceneData(); + if (node) node->accept(vrv); + } + + // set up each render stage to clear the appropriate buffers. + GLbitfield clear_mask=0; + if (vrv.requiresRGB()) clear_mask |= GL_COLOR_BUFFER_BIT; + if (vrv.requiresDepthBuffer()) clear_mask |= GL_DEPTH_BUFFER_BIT; + if (vrv.requiresStencilBuffer()) clear_mask |= GL_STENCIL_BUFFER_BIT; + + for(itr=_viewportList.begin(); + itr!=_viewportList.end(); + ++itr) + { + osgUtil::RenderStage *stage = itr->sceneView->getRenderStage(); + stage->setClearMask(clear_mask); + } + + + // set the GLUT display mode bit mask up to handle it. + unsigned int displayMode=0; + if (vrv.requiresDoubleBuffer()) displayMode |= GLUT_DOUBLE; + else displayMode |= GLUT_SINGLE; + if (vrv.requiresRGB()) displayMode |= GLUT_RGB; + if (vrv.requiresDepthBuffer()) displayMode |= GLUT_DEPTH; + if (vrv.requiresAlphaBuffer()) displayMode |= GLUT_ALPHA; + if (vrv.requiresStencilBuffer()) displayMode |= GLUT_STENCIL; + + // and we'll add in multisample so that on systems like Onyx's can + // go ahead and use there loverly anti-aliasing. This is ignored + // by other systems I've come across so not need to worry about it. + displayMode |= GLUT_MULTISAMPLE; + + + osg::notify(osg::INFO) <<"osgGLUT::Viewer::open() requesting displayMode = "<accept(dlv); - } + #endif - _sceneView->setSceneData(rootnode); - - if (saveModel) - { - osg::saveNodeFile(*rootnode, _saveFileName.c_str()); - } - - selectCameraManipulator(0); - - osg::ref_ptr ea = new GLUTEventAdapter; - _cameraManipulator->home(*ea,*this); - - - // std::string name = Registry::instance()->createLibraryNameForExt("osg"); - // Registry::instance()->loadLibrary(name); - // Registry::instance()->closeLibrary(name); - + _is_open = 1; return true; - } -void Viewer::registerCameraManipulator(osgUtil::CameraManipulator* cm) + + +unsigned int Viewer::registerCameraManipulator(osgUtil::CameraManipulator* cm, + unsigned int viewport) { - _cameraManipList.push_back(cm); + ViewportDef &viewp = _viewportList[viewport]; + unsigned int pos = viewp._cameraManipList.size(); + viewp._cameraManipList.push_back(cm); + return pos; } -void Viewer::selectCameraManipulator(unsigned int pos) + +void Viewer::setFocusedViewport(unsigned int pos) { - if (pos>=_cameraManipList.size()) return; + if (pos>=_viewportList.size()) return; - _cameraManipulator = _cameraManipList[pos]; - _cameraManipulator->setCamera(_sceneView->getCamera()); - _cameraManipulator->setNode(_sceneView->getSceneData()); + _focusedViewport = pos; +} +void Viewer::selectCameraManipulator(unsigned int pos, unsigned int viewport) +{ + if (viewport>=_viewportList.size()) return; + + ViewportDef &viewp = _viewportList[viewport]; + if (pos>=viewp._cameraManipList.size()) return; + + viewp._cameraManipulator = viewp._cameraManipList[pos]; + + osgUtil::SceneView *sceneView = viewp.sceneView.get(); + viewp._cameraManipulator->setCamera(sceneView->getCamera()); + viewp._cameraManipulator->setNode(sceneView->getSceneData()); + osg::ref_ptr ea = new GLUTEventAdapter; - _cameraManipulator->init(*ea,*this); + viewp._cameraManipulator->init(*ea,*this); } -void Viewer::needWarpPointer(int x,int y) + +void Viewer::requestWarpPointer(int x,int y) { + // glutWarpPointer core dumps if invoked before a GLUT window is open + if ( !_is_open ) { + osg::notify(osg::INFO)<<"osgGLUT::Viewer::requestWarpPointer() called with window closed; ignored."<app(); + + // update the camera manipulator. osg::ref_ptr ea = new GLUTEventAdapter; ea->adaptFrame(clockSeconds()); - if (_cameraManipulator->update(*ea,*this)) + if (_viewportList[viewport]._cameraManipulator->handle(*ea,*this)) { -// osg::notify(osg::INFO) << "Handled update frame"<cull(); - - float timeTraversal = _timer.delta_m(beforeTraversal,_timer.tick()); - if (_printStats) osg::notify(osg::NOTICE) << "Time of Cull Traversal "<cull(); osg::Timer_t beforeDraw = _timer.tick(); - + + return _timer.delta_m(beforeCull,beforeDraw); +} + + +float Viewer::draw(unsigned int viewport) +{ + osg::Timer_t beforeDraw = _timer.tick(); + glLightModeli(GL_LIGHT_MODEL_TWO_SIDE,_two_sided_lighting); - _sceneView->draw(); - - float timeDraw = _timer.delta_m(beforeDraw,_timer.tick()); - if (_printStats) osg::notify(osg::NOTICE) << "Time of Draw "<draw(); - return true; + osg::Timer_t afterDraw = _timer.tick(); + + return _timer.delta_m(beforeDraw,afterDraw); +} + + +int Viewer::mapWindowXYToSceneView(int x, int y) +{ + int ogl_y = wh-y; + + int index = 0; + for(ViewportList::iterator itr=_viewportList.begin(); + itr!=_viewportList.end(); + ++itr, ++index) + { + if ( x >= int( itr->viewport[0]*ww ) && + ogl_y >= int( itr->viewport[1]*wh ) && + x <= int( (itr->viewport[0]+itr->viewport[2])*ww ) && + ogl_y <= int( (itr->viewport[1]+itr->viewport[3])*wh ) ) + return index; + } + return -1; } @@ -265,7 +392,8 @@ void Viewer::displayCB() } -void Viewer::reshapeCB(GLint w, GLint h) +//void Viewer::reshapeCB(GLint w, GLint h) +void Viewer::reshapeCB(int w, int h) { s_theViewer->reshape(w, h); } @@ -301,16 +429,420 @@ void Viewer::keyboardCB(unsigned char key, int x, int y) } +GLuint makeRasterFont(void) +{ // GWM creates a set of display lists which may be used to render a character string on the screen +// data from GWM's reading of the Windows ASCII_FIXED_FONT. + GLubyte rasters[][12] = { // ascii symbols 32-127, small font +{0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, +{0x00, 0x00, 0x08, 0x00, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x00}, +{0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x14, 0x14, 0x14, 0x00}, +{0x00, 0x00, 0x28, 0x28, 0x7e, 0x14, 0x14, 0x14, 0x3f, 0x0a, 0x0a, 0x00}, +{0x00, 0x00, 0x08, 0x1c, 0x22, 0x02, 0x1c, 0x20, 0x22, 0x1c, 0x08, 0x00}, +{0x00, 0x00, 0x02, 0x45, 0x22, 0x10, 0x08, 0x04, 0x22, 0x51, 0x20, 0x00}, +{0x00, 0x00, 0x3b, 0x44, 0x4a, 0x49, 0x30, 0x10, 0x20, 0x20, 0x18, 0x00}, +{0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x08, 0x08, 0x08, 0x00}, +{0x04, 0x08, 0x08, 0x10, 0x10, 0x10, 0x10, 0x10, 0x08, 0x08, 0x04, 0x00}, +{0x10, 0x08, 0x08, 0x04, 0x04, 0x04, 0x04, 0x04, 0x08, 0x08, 0x10, 0x00}, +{0x00, 0x00, 0x00, 0x00, 0x36, 0x1c, 0x7f, 0x1c, 0x36, 0x00, 0x00, 0x00}, +{0x00, 0x00, 0x08, 0x08, 0x08, 0x7f, 0x08, 0x08, 0x08, 0x00, 0x00, 0x00}, +{0x00, 0x10, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, +{0x00, 0x00, 0x00, 0x00, 0x00, 0x7f, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, +{0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, +{0x00, 0x00, 0x00, 0x40, 0x20, 0x10, 0x08, 0x04, 0x02, 0x01, 0x00, 0x00}, +{0x00, 0x00, 0x1c, 0x22, 0x22, 0x22, 0x22, 0x22, 0x22, 0x22, 0x1c, 0x00}, +{0x00, 0x00, 0x3e, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x38, 0x08, 0x00}, +{0x00, 0x00, 0x3e, 0x20, 0x10, 0x08, 0x04, 0x02, 0x02, 0x22, 0x1c, 0x00}, +{0x00, 0x00, 0x1c, 0x22, 0x02, 0x02, 0x0c, 0x02, 0x02, 0x22, 0x1c, 0x00}, +{0x00, 0x00, 0x0e, 0x04, 0x3e, 0x24, 0x14, 0x14, 0x0c, 0x0c, 0x04, 0x00}, +{0x00, 0x00, 0x1c, 0x22, 0x02, 0x02, 0x3c, 0x20, 0x20, 0x20, 0x3e, 0x00}, +{0x00, 0x00, 0x1c, 0x22, 0x22, 0x22, 0x3c, 0x20, 0x20, 0x10, 0x0c, 0x00}, +{0x00, 0x00, 0x10, 0x10, 0x08, 0x08, 0x04, 0x04, 0x02, 0x22, 0x3e, 0x00}, +{0x00, 0x00, 0x1c, 0x22, 0x22, 0x22, 0x1c, 0x22, 0x22, 0x22, 0x1c, 0x00}, +{0x00, 0x00, 0x18, 0x04, 0x02, 0x02, 0x1e, 0x22, 0x22, 0x22, 0x1c, 0x00}, +{0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x00}, +{0x00, 0x10, 0x08, 0x00, 0x00, 0x00, 0x00, 0x08, 0x00, 0x00, 0x00, 0x00}, +{0x00, 0x00, 0x04, 0x08, 0x10, 0x20, 0x10, 0x08, 0x04, 0x00, 0x00, 0x00}, +{0x00, 0x00, 0x00, 0x00, 0x00, 0x3e, 0x00, 0x3e, 0x00, 0x00, 0x00, 0x00}, +{0x00, 0x00, 0x10, 0x08, 0x04, 0x02, 0x04, 0x08, 0x10, 0x00, 0x00, 0x00}, +{0x00, 0x00, 0x08, 0x00, 0x08, 0x08, 0x04, 0x02, 0x02, 0x22, 0x1c, 0x00}, +{0x00, 0x00, 0x1c, 0x20, 0x4e, 0x55, 0x55, 0x55, 0x4d, 0x21, 0x1e, 0x00}, +{0x00, 0x00, 0x77, 0x22, 0x3e, 0x22, 0x14, 0x14, 0x08, 0x08, 0x18, 0x00}, +{0x00, 0x00, 0x7e, 0x21, 0x21, 0x21, 0x3e, 0x21, 0x21, 0x21, 0x7e, 0x00}, +{0x00, 0x00, 0x1e, 0x21, 0x40, 0x40, 0x40, 0x40, 0x40, 0x21, 0x1e, 0x00}, +{0x00, 0x00, 0x7c, 0x22, 0x21, 0x21, 0x21, 0x21, 0x21, 0x22, 0x7c, 0x00}, +{0x00, 0x00, 0x7f, 0x21, 0x20, 0x24, 0x3c, 0x24, 0x20, 0x21, 0x7f, 0x00}, +{0x00, 0x00, 0x78, 0x20, 0x20, 0x24, 0x3c, 0x24, 0x20, 0x21, 0x7f, 0x00}, +{0x00, 0x00, 0x1e, 0x21, 0x41, 0x47, 0x40, 0x40, 0x40, 0x21, 0x1e, 0x00}, +{0x00, 0x00, 0x77, 0x22, 0x22, 0x22, 0x3e, 0x22, 0x22, 0x22, 0x77, 0x00}, +{0x00, 0x00, 0x3e, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x3e, 0x00}, +{0x00, 0x00, 0x38, 0x44, 0x44, 0x04, 0x04, 0x04, 0x04, 0x04, 0x1e, 0x00}, +{0x00, 0x00, 0x73, 0x22, 0x24, 0x38, 0x28, 0x24, 0x24, 0x22, 0x73, 0x00}, +{0x00, 0x00, 0x7f, 0x11, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x7c, 0x00}, +{0x00, 0x00, 0x77, 0x22, 0x22, 0x2a, 0x2a, 0x36, 0x36, 0x22, 0x63, 0x00}, +{0x00, 0x00, 0x72, 0x22, 0x26, 0x26, 0x2a, 0x32, 0x32, 0x22, 0x67, 0x00}, +{0x00, 0x00, 0x1c, 0x22, 0x41, 0x41, 0x41, 0x41, 0x41, 0x22, 0x1c, 0x00}, +{0x00, 0x00, 0x78, 0x20, 0x20, 0x20, 0x3e, 0x21, 0x21, 0x21, 0x7e, 0x00}, +{0x00, 0x1b, 0x1c, 0x22, 0x41, 0x41, 0x41, 0x41, 0x41, 0x22, 0x1c, 0x00}, +{0x00, 0x00, 0x73, 0x22, 0x24, 0x24, 0x3e, 0x21, 0x21, 0x21, 0x7e, 0x00}, +{0x00, 0x00, 0x3e, 0x41, 0x01, 0x01, 0x3e, 0x40, 0x40, 0x41, 0x3e, 0x00}, +{0x00, 0x00, 0x1c, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x49, 0x7f, 0x00}, +{0x00, 0x00, 0x1c, 0x22, 0x22, 0x22, 0x22, 0x22, 0x22, 0x22, 0x77, 0x00}, +{0x00, 0x00, 0x08, 0x08, 0x14, 0x14, 0x14, 0x22, 0x22, 0x22, 0x77, 0x00}, +{0x00, 0x00, 0x14, 0x14, 0x2a, 0x2a, 0x2a, 0x22, 0x22, 0x22, 0x77, 0x00}, +{0x00, 0x00, 0x77, 0x22, 0x14, 0x14, 0x08, 0x14, 0x14, 0x22, 0x77, 0x00}, +{0x00, 0x00, 0x1c, 0x08, 0x08, 0x08, 0x14, 0x14, 0x22, 0x22, 0x77, 0x00}, +{0x00, 0x00, 0x7f, 0x21, 0x10, 0x10, 0x08, 0x04, 0x04, 0x42, 0x7f, 0x00}, +{0x1c, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x10, 0x1c, 0x00}, +{0x00, 0x00, 0x00, 0x01, 0x02, 0x04, 0x08, 0x10, 0x20, 0x40, 0x00, 0x00}, +{0x1c, 0x04, 0x04, 0x04, 0x04, 0x04, 0x04, 0x04, 0x04, 0x04, 0x1c, 0x00}, +{0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x22, 0x14, 0x08}, +{0xff, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00}, +{0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x08, 0x10, 0x00}, +{0x00, 0x00, 0x3d, 0x42, 0x42, 0x3e, 0x02, 0x3c, 0x00, 0x00, 0x00, 0x00}, +{0x00, 0x00, 0x7e, 0x21, 0x21, 0x21, 0x21, 0x3e, 0x20, 0x20, 0x60, 0x00}, +{0x00, 0x00, 0x3e, 0x41, 0x40, 0x40, 0x41, 0x3e, 0x00, 0x00, 0x00, 0x00}, +{0x00, 0x00, 0x3f, 0x42, 0x42, 0x42, 0x42, 0x3e, 0x02, 0x02, 0x06, 0x00}, +{0x00, 0x00, 0x3e, 0x41, 0x40, 0x7f, 0x41, 0x3e, 0x00, 0x00, 0x00, 0x00}, +{0x00, 0x00, 0x3c, 0x10, 0x10, 0x10, 0x10, 0x3c, 0x10, 0x10, 0x0c, 0x00}, +{0x3c, 0x02, 0x02, 0x3e, 0x42, 0x42, 0x42, 0x3f, 0x00, 0x00, 0x00, 0x00}, +{0x00, 0x00, 0x77, 0x22, 0x22, 0x22, 0x32, 0x2c, 0x20, 0x20, 0x60, 0x00}, +{0x00, 0x00, 0x3e, 0x08, 0x08, 0x08, 0x08, 0x38, 0x00, 0x00, 0x08, 0x00}, +{0x38, 0x04, 0x04, 0x04, 0x04, 0x04, 0x04, 0x3c, 0x00, 0x00, 0x04, 0x00}, +{0x00, 0x00, 0x63, 0x24, 0x38, 0x28, 0x24, 0x26, 0x20, 0x20, 0x60, 0x00}, +{0x00, 0x00, 0x3e, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x18, 0x00}, +{0x00, 0x00, 0x6b, 0x2a, 0x2a, 0x2a, 0x2a, 0x74, 0x00, 0x00, 0x00, 0x00}, +{0x00, 0x00, 0x77, 0x22, 0x22, 0x22, 0x32, 0x6c, 0x00, 0x00, 0x00, 0x00}, +{0x00, 0x00, 0x3e, 0x41, 0x41, 0x41, 0x41, 0x3e, 0x00, 0x00, 0x00, 0x00}, +{0x70, 0x20, 0x3e, 0x21, 0x21, 0x21, 0x21, 0x7e, 0x00, 0x00, 0x00, 0x00}, +{0x07, 0x02, 0x3e, 0x42, 0x42, 0x42, 0x42, 0x3f, 0x00, 0x00, 0x00, 0x00}, +{0x00, 0x00, 0x7c, 0x10, 0x10, 0x10, 0x19, 0x76, 0x00, 0x00, 0x00, 0x00}, +{0x00, 0x00, 0x3e, 0x41, 0x06, 0x38, 0x41, 0x3e, 0x00, 0x00, 0x00, 0x00}, +{0x00, 0x00, 0x0c, 0x12, 0x10, 0x10, 0x10, 0x3c, 0x10, 0x10, 0x00, 0x00}, +{0x00, 0x00, 0x1b, 0x26, 0x22, 0x22, 0x22, 0x66, 0x00, 0x00, 0x00, 0x00}, +{0x00, 0x00, 0x08, 0x14, 0x14, 0x22, 0x22, 0x77, 0x00, 0x00, 0x00, 0x00}, +{0x00, 0x00, 0x14, 0x14, 0x2a, 0x2a, 0x22, 0x77, 0x00, 0x00, 0x00, 0x00}, +{0x00, 0x00, 0x77, 0x22, 0x1c, 0x1c, 0x22, 0x77, 0x00, 0x00, 0x00, 0x00}, +{0x30, 0x08, 0x08, 0x14, 0x14, 0x22, 0x22, 0x77, 0x00, 0x00, 0x00, 0x00}, +{0x00, 0x00, 0x7e, 0x22, 0x10, 0x08, 0x44, 0x7e, 0x00, 0x00, 0x00, 0x00}, +{0x06, 0x08, 0x08, 0x08, 0x08, 0x30, 0x08, 0x08, 0x08, 0x08, 0x06, 0x00}, +{0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08, 0x08}, +{0x30, 0x08, 0x08, 0x08, 0x08, 0x06, 0x08, 0x08, 0x08, 0x08, 0x30, 0x00}, +{0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x46, 0x49, 0x31, 0x00, 0x00}, +{0x00, 0x1c, 0x1c, 0x1c, 0x1c, 0x1c, 0x1c, 0x1c, 0x1c, 0x1c, 0x00, 0x00} +}; +// the remaining lines of this routine are similar to code developed and published in the + // OPENGL big red book. However I have modified the code slightly, and + // SGI are not responsible for any errors, omissions etc. + static GLuint fontOffset; // first display list + if (!fontOffset) { // then make the raster fonts + GLuint i; + glPixelStorei(GL_UNPACK_ALIGNMENT, 1); + + fontOffset = glGenLists (128); + for (i = 32; i < 127; i++) { + glNewList(i+fontOffset, GL_COMPILE); + glBitmap(8, 12, 0.0, 2.0, 10.0, 0.0, rasters[i-32]); + glEndList(); + } + } + return fontOffset; +} +void displaytext(int x, int y, char *s) +{ // GWM July 2001 statistics text display at xy text S + GLuint fontOffset=makeRasterFont(); // first display list + glRasterPos2i(x,y); +// glPushAttrib (GL_LIST_BIT); + glListBase(fontOffset); + glCallLists(strlen(s), GL_UNSIGNED_BYTE, (GLubyte *) s); + glListBase(0); +// glPopAttrib (); +} + +// GWM July 2001 - add Statistics structure, and related RenderBin +#include +#include + +void Viewer::showStats() +{ + static GLfloat tmax=100; + glViewport(0,0,ww,wh); + float vh = wh; + + glDisable( GL_DEPTH_TEST ); // to see the stats always + glDisable( GL_ALPHA_TEST ); + glDisable( GL_LIGHTING ); + glDisable( GL_TEXTURE_2D ); + + glMatrixMode( GL_PROJECTION ); + glPushMatrix(); + glLoadIdentity(); + // set tmax using hysteresis to prevent flip-flopping between two values of tmax + if (times[2].timeFrame>360.0f && tmax<1600) tmax=1600; + else if (times[2].timeFrame<300.0f && tmax>800) tmax=800; + else if (times[2].timeFrame>180.0f && tmax<800) tmax=800; + else if (times[2].timeFrame<150.0f && tmax>400) tmax=400; + else if (times[2].timeFrame>90.0f && tmax<400) tmax=400; + else if (times[2].timeFrame<75.0f && tmax>200) tmax=200; + else if (times[2].timeFrame>45.0f && tmax<200) tmax=200; + else if (times[2].timeFrame<36.0f && tmax>100) tmax=100; + glOrtho(-0.1f*tmax, tmax*1.1f,0,vh,0,500); + + glMatrixMode( GL_MODELVIEW ); + glPushMatrix(); + glLoadIdentity(); + glDisable(GL_STENCIL_TEST); // dont want to count pixels set by performance graphs + + if (_printStats>0) { // output the text frame rate + char clin[72]; // buffer to print + glColor3f(1.0f,1.0f,0.0f); + if (frRate>10.0f) + { + float smoothRatio = 0.4; // should be >0 and <= 1.0, + // lower the value greater smoothing. + frRate=(1.0f-smoothRatio)*frRate+smoothRatio*frameRate(); // smooth out variations in frame rate + } + else + { + frRate=frameRate(); // frame rate so slow no need to smooth in frame rate + } + sprintf(clin,"%.1f Hz.", frRate); + displaytext(0,(int)(0.98f*vh),clin); + } + + if (_printStats>1) { // more stats - graphs this time + + int sampleIndex = 2; + float timeApp=times[sampleIndex].timeApp; + float timeCull=times[sampleIndex].timeCull; + float timeDraw=times[sampleIndex].timeDraw; + float timeFrame=times[sampleIndex].timeFrame; + + osg::Vec4 app_color(0.0f,1.0f,0.0f,1.0f); + osg::Vec4 cull_color(1.0f,0.0f,1.0f,1.0f); + osg::Vec4 draw_color(0.0f,1.0f,1.0f,1.0f); + osg::Vec4 swap_color(1.0f,0.5f,0.5f,1.0f); + osg::Vec4 frame_color(1.0f,1.0f,0.0f,1.0f); + + char clin[72]; // buffer to print + glColor4fv((GLfloat * )&app_color); + sprintf(clin,"App %.1f ms.", timeApp); + displaytext((int)(.15f*tmax),(int)(0.98f*vh),clin); + + glColor4fv((GLfloat * )&cull_color); + sprintf(clin,"Cull %.1f ms.", timeCull); + displaytext((int)(.35*tmax),(int)(0.98f*vh),clin); + + glColor4fv((GLfloat * )&draw_color); + sprintf(clin,"Draw %.1f ms.", timeDraw); + displaytext((int)(.55*tmax),(int)(0.98f*vh),clin); + + glColor4fv((GLfloat * )&frame_color); + sprintf(clin,"Frame %.1f ms.", timeFrame); + displaytext((int)(.75*tmax),(int)(0.98f*vh),clin); + + /* osg::notify(osg::NOTICE) << "Time of App "<sceneView->getRenderStage(); + stage->getPrims(&primStats); + } + glColor3f(.9f,.9f,0.0f); + + sprintf(clin,"%d Prims %d Matrices %d nGsets %d nlights %d bins", primStats.nprims, + primStats.nummat, primStats.numOpaque, primStats.nlights, primStats.nbins); + displaytext(0,(int)(0.86f*vh),clin); + strcpy(clin," "); + for (i=0; i<15; i++) { + if (i==0 || primStats.primtypes[i]) { + strcat(clin, prtypes[i]); + } + } + displaytext(0,(int)(0.82f*vh),clin); + strcpy(clin,"GSet type: "); + for (i=0; i<15; i++) { + if (primStats.primtypes[i]) { + sprintf(ctmp,"%5d", primStats.primtypes[i]); + strcat(clin, ctmp); + } + } + displaytext(0,(int)(0.80f*vh),clin); + strcpy(clin,"Prims: "); + for (i=0; i<15; i++) { + if (primStats.numprimtypes[i]) { + sprintf(ctmp,"%5d", primStats.numprimtypes[i]); + strcat(clin, ctmp); + } + } + displaytext(0,(int)(0.78f*vh),clin); + strcpy(clin,"Triangles: "); + for (i=0; i<15; i++) { + if (primStats.primlens[i]) { + sprintf(ctmp,"%5d", primStats.primlens[i]); + strcat(clin, ctmp); + } + } + displaytext(0,(int)(0.76f*vh),clin); + strcpy(clin,"Vertices: "); + for (i=0; i<15; i++) { + if (primStats.primlens[i]) { + sprintf(ctmp,"%5d", primStats.primverts[i]); + strcat(clin, ctmp); + } + } + displaytext(0,(int)(0.74f*vh),clin); + } + if (_printStats==4) { // yet more stats - read the depth complexity + int wid=ww, ht=wh; // temporary local screen size - must change during this section + if (wid>0 && ht>0) { + const int blsize=16; + char *clin=new char[wid/blsize+2]; // buffer to print + float mdc=0; + GLubyte *buffer=new GLubyte[wid*ht]; + if (buffer) { + glPixelStorei(GL_PACK_ALIGNMENT, 1); // no extra bytes at ends of rows- easier to analyse + glColor3f(.9f,.9f,0.0f); + glReadPixels(0,0,wid,ht, GL_STENCIL_INDEX ,GL_UNSIGNED_BYTE, buffer); + for (int j=0; j=0 && ii>=0) { + dc+=buffer[ii+ (ht-jj-1)*wid]; + nav++; + } + } + } + mdc+=dc; + if (dcframe(); @@ -322,15 +854,27 @@ void Viewer::reshape(GLint w, GLint h) { ww = w; wh = h; - - _sceneView->setViewport(0,0,ww,wh); - osg::ref_ptr ea = new GLUTEventAdapter; - ea->adaptResize(clockSeconds(),0,0,ww,wh); - - if (_cameraManipulator->update(*ea,*this)) + // Propagate new window size to viewports + for(ViewportList::iterator itr=_viewportList.begin(); + itr!=_viewportList.end(); + ++itr) { -// osg::notify(osg::INFO) << "Handled reshape "<sceneView.get(); + int view[4] = { int(itr->viewport[0]*ww), int(itr->viewport[1]*wh), + int(itr->viewport[2]*ww), int(itr->viewport[3]*wh) }; + + sceneView->setViewport(view[0], view[1], view[2], view[3]); + + osg::ref_ptr ea = new GLUTEventAdapter; + ea->adaptResize(clockSeconds(), + view[0], view[1], + view[0]+view[2], view[1]+view[3]); + + if (itr->_cameraManipulator->handle(*ea,*this)) + { + // osg::notify(osg::INFO) << "Handled reshape "< ea = new GLUTEventAdapter; ea->adaptMouseMotion(clockSeconds(),x,y); - - if (_cameraManipulator->update(*ea,*this)) - { -// osg::notify(osg::INFO) << "Handled mouseMotion "<_buttonMask<<" x="<_mx<<" y="<_my<handle(*ea,*this)) + { + // osg::notify(osg::INFO) << "Handled mouseMotion "<_buttonMask<<" x="<_mx<<" y="<_my< ea = new GLUTEventAdapter; ea->adaptMousePassiveMotion(clockSeconds(),x,y); - if (_cameraManipulator->update(*ea,*this)) + // Switch viewport focus if no buttons are pressed + if (ea->getButtonMask() == 0) { -// osg::notify(osg::INFO) << "Handled mousePassiveMotion "<_buttonMask<<" x="<_mx<<" y="<_my<= 0 && focus != int(_focusedViewport)) + setFocusedViewport(focus); } - + if (_viewportList[_focusedViewport]._cameraManipulator->handle(*ea,*this)) + { + // osg::notify(osg::INFO) << "Handled mousePassiveMotion "<_buttonMask<<" x="<_mx<<" y="<_my< ea = new GLUTEventAdapter; ea->adaptMouse(clockSeconds(),button,state,x,y); - if (_cameraManipulator->update(*ea,*this)) + // Switch viewport focus if button is pressed, and it is the only one + unsigned mask = ea->getButtonMask(); + if (state == GLUT_DOWN && + (mask == osgUtil::GUIEventAdapter::LEFT_BUTTON || + mask == osgUtil::GUIEventAdapter::MIDDLE_BUTTON || + mask == osgUtil::GUIEventAdapter::RIGHT_BUTTON)) { -// osg::notify(osg::INFO) << "Handled mouse "<_buttonMask<<" x="<_mx<<" y="<_my<= 0 && focus != int(_focusedViewport)) + setFocusedViewport(focus); } - + if (_viewportList[_focusedViewport]._cameraManipulator->handle(*ea,*this)) + { + // osg::notify(osg::INFO) << "Handled mouse "<_buttonMask<<" x="<_mx<<" y="<_my< ea = new GLUTEventAdapter; ea->adaptKeyboard(clockSeconds(),key,x,y); - if (_cameraManipulator->update(*ea,*this)) return; + if (_viewportList[_focusedViewport]._cameraManipulator->handle(*ea,*this)) + return; if (key>='1' && key<='3') { @@ -405,34 +963,48 @@ void Viewer::keyboard(unsigned char key, int x, int y) selectCameraManipulator(pos); } + osgUtil::SceneView* sceneView = getViewportSceneView(_focusedViewport); + switch( key ) { - + + case '7' : + sceneView->setBackgroundColor(osg::Vec4(0.0f,0.0f,0.0f,1.0f)); + break; + + case '8' : + sceneView->setBackgroundColor(osg::Vec4(0.2f, 0.2f, 0.4f, 1.0f)); + break; + + case '9' : + sceneView->setBackgroundColor(osg::Vec4(1.0f, 1.0f, 1.0f, 1.0f)); + break; + case '/' : - if (_sceneView->getLODBias()>0.5) _sceneView->setLODBias(_sceneView->getLODBias()/1.5f); + if (sceneView->getLODBias()>0.5) sceneView->setLODBias(sceneView->getLODBias()/1.5f); break; case '*' : - if (_sceneView->getLODBias()<30) _sceneView->setLODBias(_sceneView->getLODBias()*1.5f); + if (sceneView->getLODBias()<30) sceneView->setLODBias(sceneView->getLODBias()*1.5f); break; case '+' : - #ifdef SGV_USE_RTFS - frame_rate <<= 1; - fs->stop(); - fs->setUpdateRate( frame_rate ); - fs->start(); - #endif + #ifdef SGV_USE_RTFS + frame_rate <<= 1; + fs->stop(); + fs->setUpdateRate( frame_rate ); + fs->start(); + #endif break; case '-' : - #ifdef SGV_USE_RTFS - frame_rate >>= 1; - if( frame_rate < 1 ) frame_rate = 1; - fs->stop(); - fs->setUpdateRate( frame_rate ); - fs->start(); - #endif + #ifdef SGV_USE_RTFS + frame_rate >>= 1; + if( frame_rate < 1 ) frame_rate = 1; + fs->stop(); + fs->setUpdateRate( frame_rate ); + fs->start(); + #endif break; case 'd' : @@ -442,7 +1014,7 @@ void Viewer::keyboard(unsigned char key, int x, int y) // traverse the scene graph setting up all osg::GeoSet's so they will use // OpenGL display lists. osgUtil::DisplayListVisitor dlv(osgUtil::DisplayListVisitor::SWITCH_ON_DISPLAY_LISTS); - _sceneView->getSceneData()->accept(dlv); + sceneView->getSceneData()->accept(dlv); osg::notify(osg::NOTICE) << "Switched on use of OpenGL Display Lists."<getSceneData()->accept(dlv); + sceneView->getSceneData()->accept(dlv); osg::notify(osg::NOTICE) << "Switched off use of OpenGL Display Lists."<4) _printStats=0; + if (_printStats==4) { // count depth complexity by incrementing the stencil buffer every + // time a pixel is hit + glEnable(GL_STENCIL_TEST); + glStencilOp(GL_INCR ,GL_INCR ,GL_INCR); + } else { + glDisable(GL_STENCIL_TEST); + } break; case 's' : @@ -468,43 +1048,72 @@ void Viewer::keyboard(unsigned char key, int x, int y) break; + case 'S' : + { + osg::notify(osg::NOTICE) << "Smoothing scene..."<getSceneData()->accept(sv); + osg::notify(osg::NOTICE) << "Smoothed scene."<getSceneData()->accept(tsv); + osg::notify(osg::NOTICE) << "Tri Striping scene scene."<getGlobalState()->setMode(osg::GeoState::FACE_CULL,osg::GeoState::ON); + sceneView->getGlobalState()->setMode(GL_CULL_FACE,osg::StateAttribute::ON); else - _sceneView->getGlobalState()->setMode(osg::GeoState::FACE_CULL,osg::GeoState::OVERRIDE_OFF); + sceneView->getGlobalState()->setMode(GL_CULL_FACE,osg::StateAttribute::OVERRIDE_OFF); break; - case 'l' : lighting = 1 - lighting ; if( lighting ) - _sceneView->getGlobalState()->setMode(osg::GeoState::LIGHTING,osg::GeoState::ON); + sceneView->getGlobalState()->setMode(GL_LIGHTING,osg::StateAttribute::ON); else - _sceneView->getGlobalState()->setMode(osg::GeoState::LIGHTING,osg::GeoState::OVERRIDE_OFF); + sceneView->getGlobalState()->setMode(GL_LIGHTING,osg::StateAttribute::OVERRIDE_OFF); break; case 'L' : { - osgUtil::SceneView::LightingMode lm= _sceneView->getLightingMode(); + osgUtil::SceneView::LightingMode lm= sceneView->getLightingMode(); switch(lm) { - case(osgUtil::SceneView::HEADLIGHT) : lm = osgUtil::SceneView::SKY_LIGHT; break; - case(osgUtil::SceneView::SKY_LIGHT) : lm = osgUtil::SceneView::NO_SCENEVIEW_LIGHT; break; - case(osgUtil::SceneView::NO_SCENEVIEW_LIGHT) : lm = osgUtil::SceneView::HEADLIGHT; break; + case(osgUtil::SceneView::HEADLIGHT) : lm = osgUtil::SceneView::SKY_LIGHT; break; + case(osgUtil::SceneView::SKY_LIGHT) : lm = osgUtil::SceneView::NO_SCENEVIEW_LIGHT; break; + case(osgUtil::SceneView::NO_SCENEVIEW_LIGHT) : lm = osgUtil::SceneView::HEADLIGHT; break; } - _sceneView->setLightingMode(lm); + sceneView->setLightingMode(lm); break; } case 't' : texture = 1 - texture; if (texture) - _sceneView->getGlobalState()->setMode(osg::GeoState::TEXTURE,osg::GeoState::INHERIT); + { + sceneView->getGlobalState()->setModeToInherit(GL_TEXTURE_2D); +// sceneView->getGlobalState()->setAttributeToInherit(osg::StateAttribute::TEXTURE); + } else - _sceneView->getGlobalState()->setMode(osg::GeoState::TEXTURE,osg::GeoState::OVERRIDE_OFF); + { + // use blank texture to override all local texture in scene graph. + // thus causing them to all use the same texture attribute, hence + // preventing a state attribute change due to unused textures. + static osg::ref_ptr blank_texture = new osg::Texture; + sceneView->getGlobalState()->setMode(GL_TEXTURE_2D,osg::StateAttribute::OVERRIDE_OFF); +// sceneView->getGlobalState()->setAttribute(blank_texture.get(),true); + } break; case 'T' : @@ -512,8 +1121,12 @@ void Viewer::keyboard(unsigned char key, int x, int y) break; case 'w' : - polymode = (polymode+1)%3; - glPolygonMode( GL_FRONT_AND_BACK, polymodes[polymode] ); + { + polymode = (polymode+1)%3; + osg::PolygonMode* polyModeObj = new osg::PolygonMode; + polyModeObj->setMode(osg::PolygonMode::FRONT_AND_BACK,polymodes[polymode]); + sceneView->getGlobalState()->setAttribute(polyModeObj); + } break; case 'f' : @@ -531,7 +1144,7 @@ void Viewer::keyboard(unsigned char key, int x, int y) break; case 'o' : - if (_sceneView->getSceneData() && osg::Registry::instance()->writeNode(*_sceneView->getSceneData(),_saveFileName)) + if (sceneView->getSceneData() && osgDB::writeNodeFile(*sceneView->getSceneData(), _saveFileName)) { osg::notify(osg::NOTICE) << "Saved scene to '"<<_saveFileName<<"'"<getCullVisitor()->setCullingMode((osgUtil::CullViewState::CullingMode) + ((_smallFeatureCullingActive ? osgUtil::CullViewState::SMALL_FEATURE_CULLING : osgUtil::CullViewState::NO_CULLING) | + (_viewFrustumCullingActive ? osgUtil::CullViewState::VIEW_FRUSTUM_CULLING : osgUtil::CullViewState::NO_CULLING))); if (_smallFeatureCullingActive) { osg::notify(osg::NOTICE) << "Small feature culling switched on "<getRenderVisitor()->setCullingActive(osgUtil::RenderVisitor::SMALL_FEATURE_CULLING,_smallFeatureCullingActive); break; case 'C' : _viewFrustumCullingActive = !_viewFrustumCullingActive; - _sceneView->getRenderVisitor()->setCullingActive(osgUtil::RenderVisitor::VIEW_FRUSTUM_CULLING,_viewFrustumCullingActive); if (_viewFrustumCullingActive) { osg::notify(osg::NOTICE) << "View frustum culling switched on "<getCullVisitor()->setCullingMode((osgUtil::CullViewState::CullingMode) + ((_smallFeatureCullingActive ? osgUtil::CullViewState::SMALL_FEATURE_CULLING : osgUtil::CullViewState::NO_CULLING) | + (_viewFrustumCullingActive ? osgUtil::CullViewState::VIEW_FRUSTUM_CULLING : osgUtil::CullViewState::NO_CULLING))); + break; + + case 'P' : + sceneView->setPrioritizeTextures(!sceneView->getPrioritizeTextures()); + if (sceneView->getPrioritizeTextures()) + { + osg::notify(osg::NOTICE) << "Prioritize textures switched on "<projectWindowXYIntoObject(x,wh-y,near_point,far_point)) + if (!sceneView->projectWindowXYIntoObject(x,wh-y,near_point,far_point)) { osg::notify(osg::NOTICE) << "Failed to calculate intersection ray."< seg = new osg::Seg; - seg->set(near_point,far_point); - osg::notify(osg::NOTICE) << "start("<start()<<") end("<end()<<")"< LineSegment = new osg::LineSegment; + LineSegment->set(near_point,far_point); + osg::notify(osg::NOTICE) << "start("<start()<<") end("<end()<<")"<getSceneData()->accept(iv); - + sceneView->getSceneData()->accept(iv); + float endTime = clockSeconds(); osg::notify(osg::NOTICE) << "Time for interesection = "<<(endTime-startTime)*1000<<"ms"<_intersectPoint; osg::Vec3 in = hitr->_intersectNormal; @@ -615,22 +1243,21 @@ void Viewer::keyboard(unsigned char key, int x, int y) if (geode) osg::notify(osg::NOTICE) << "Geode '"<getName()<_geoset; - osg::notify(osg::NOTICE) << " geoset ("<removeGeoSet(gset)<<")"<removeDrawable(gset)<<")"< ea = new GLUTEventAdapter; + + for(ViewportList::iterator itr=_viewportList.begin(); + itr!=_viewportList.end(); + ++itr) + { + itr->_cameraManipulator->home(*ea,*this); + } + updateFrameTick(); - #ifdef SGV_USE_RTFS +#ifdef SGV_USE_RTFS fs->start(); - #endif +#endif glutMainLoop(); return true; } + + +void Viewer::addViewport(osgUtil::SceneView* sv, + float x, float y, float width, float height) +{ + ViewportDef def; + def.sceneView = sv; + def.viewport[0] = x; + def.viewport[1] = y; + def.viewport[2] = width; + def.viewport[3] = height; + _viewportList.push_back(def); +} + + +/** + * Adds a default SceneView referring to the passed scene graph root. + */ +void Viewer::addViewport(osg::Node* rootnode, + float x, float y, float width, float height) +{ + osgUtil::SceneView *sceneView = new osgUtil::SceneView; + sceneView->setDefaults(); + sceneView->setSceneData(rootnode); + + addViewport( sceneView, x, y, width, height ); +} + +void Viewer::init(osg::Node* rootnode) +{ + osg::notify(osg::WARN)<<"Warning - call to Viewer::init(osg::Node*) which is a deprecated method."< +#include +// reading a design workshop file utility +// (c) GW Michel, 2001. +// Design Workshop format files can be downloaded from www.artifice.com +// Design Workshop editor can be downloaded from www.artifice.com = Mac & Win95/98/NT versions are available. +// DW Lite is completely free, produces textured 3D models +// aimed mostly at the architectural world. Flat polygons are generally produced +// No ability to produce smooth shading, unfortunately. +// But it is the best bangs per buck. (Anything/nothing = infinite value, and this is quite a lot/nothing) + +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include + +#include +#include +#include + +#include + +using namespace osg; + +#ifndef WIN32 + #define CALLBACK +#endif + +class _dwobj; // predefine for later call +int dwfgets(char *clin, int max, FILE *fin); // , end of line= 13 as well as Creturn=10 + +class dwmaterial {// design workshop material, to be translated to OGL +public: + typedef enum {Properties,TiledTexture,FullFace, SpotLight,PointLight} mttype; + dwmaterial() { type=Properties; + opacity=1; specular=0; specexp=0; fname="";TextureWidth=1; TextureHeight=1; + ctx=NULL; tx=NULL; id=0; dstate=NULL;colour[0]=colour[1]=colour[2]=colour[3]=1; + bright=halfIn=halfOut=falloff=0;atyp=NONE; + } + ~dwmaterial() { } + void settexture() { + if (!dstate) dstate = new StateSet; + if (isTextured()) { // shares common textures + if (!ctx || !tx) { // new texture needed + if (fname.length()>0) { + ctx=osgDB::readImageFile(fname.c_str()); + if (ctx) { + ctx->setFileName(fname); + tx=new Texture; + tx->setImage(ctx); + tx->setWrap(Texture::WRAP_S, Texture::REPEAT); + tx->setWrap(Texture::WRAP_T, Texture::REPEAT); + } + osg::TexEnv* texenv = new osg::TexEnv; + texenv->setMode(osg::TexEnv::MODULATE); + dstate->setAttribute( texenv ); + } + } + if (ctx && tx) { // texture exists + dstate->setAttributeAndModes(tx,osg::StateAttribute::ON); + dstate->setMode(GL_TEXTURE_2D,StateAttribute::ON); + } + } + } + StateSet *make() { // returns the OSG material + if (!dstate) { // if it does not exist, then make it + dstate = new StateSet; + osg::Material* osgMaterial = new osg::Material; + dstate->setAttribute(osgMaterial); + if (opacity<0.99) { + osgMaterial->setTransparency(Material::FRONT_AND_BACK, opacity); + dstate->setMode(GL_BLEND,StateAttribute::ON); + dstate->setRenderingHint(StateSet::TRANSPARENT_BIN); + colour[3]=opacity; + } + osgMaterial->setAmbient(Material::FRONT_AND_BACK,colour); + osgMaterial->setDiffuse(Material::FRONT_AND_BACK,colour); + + Vec4 colspec=colour*specular; + colspec[3]=colour[3]; + osgMaterial->setSpecular(Material::FRONT_AND_BACK,colspec); + osgMaterial->setShininess(Material::FRONT_AND_BACK,specexp); + + dstate->setMode( GL_LIGHTING, StateAttribute::ON ); + dstate->setMode( GL_CULL_FACE, StateAttribute::ON ); + + osg::CullFace *cf = new osg::CullFace; // to define non-default culling + cf->setMode(osg::CullFace::BACK); + dstate->setAttribute(cf); + + dstate->setMode(GL_TEXTURE_2D,StateAttribute::OFF); + settexture(); + } + return dstate; + } + inline int isType(mttype t1) const {return (type==t1 ); } + inline int isTextured() {return (type==TiledTexture || type==FullFace ); } + void setcolour(const float rgb[3]) { + colour[0]=rgb[0]; colour[1]=rgb[1]; colour[2]=rgb[2]; + } + void settxrep(const float repx, const float repy) { + TextureWidth=repx; + TextureHeight=repy; + } + inline float getRepWid() const { return TextureWidth;} + inline float getRepHt() const { return TextureHeight;} + inline int isFullFace() const { return type==FullFace;} + inline int getid() const { return id;} + inline void setid(const int i) { id=i;} + inline void setopacity(float o) { opacity=o;} + inline void setspecular(float o) { specular=o;} + inline void setspecexp(float o) { specexp=o;} + void setType(const char *buff) { + if (strncmp(buff,"Tiled_Texture",13)==0) + type=dwmaterial::TiledTexture; + else if (strncmp(buff,"Spot_Light",11)==0) + type=dwmaterial::SpotLight; + else if (strncmp(buff,"Point_Light",11)==0) + type=dwmaterial::PointLight; + else if (strncmp(buff,"Properties",11)==0) + type=dwmaterial::Properties; + else if (strncmp(buff,"Full_Face_Texture",16)==0) + type=dwmaterial::FullFace; + } + void setfname(const char *buff) { + fname=new char[strlen(buff+13)+5]; + fname= (buff+13); + fname+= ".tga"; + } + LightSource *makeLight(const Vec4 pos) { + Light *lt= new Light; + Vec4 cdef; + cdef[0]=cdef[1]=cdef[2]=0.0f; cdef[3]=0.0f; + lt->setSpecular(colour*bright/2.0f); + lt->setDiffuse(colour*bright/4.0f); + lt->setAmbient(cdef); + lt->on(); + if (atyp==NONE) ; + else if (atyp==INVERSE_DIST) { + lt->setLinearAttenuation(1.0f); + lt->setConstantAttenuation(0.01f); + } + lt->setPosition(pos); + LightSource *ls=new LightSource(); + ls->setLight(lt); + return ls; + } + void setAtten(const char *buff) { + if (strstr(buff,"kQ3AttenuationTypeNone")) atyp=NONE; + else if (strstr(buff,"kQ3AttenuationTypeInverseDistance")) atyp=INVERSE_DIST; + // else if (strstr(buff,"kQ3AttenuationTypeNone")) ; + } + void setBright(const float br) { bright=br;} + void setHalfAngleIn(const float ha) { halfIn=ha;} + void setHalfAngleOut(const float ha) { halfOut=ha;} + void setFallOff(const float fo) { falloff=fo;} + const Vec4 getcolour() { return colour;} +private: + int id; + Vec4 colour; // the ambient/diffuse+alpha colour + mttype type; + float opacity, specular, specexp; // transp, specularity properties + float TextureWidth, TextureHeight; + std::string fname; // picture file + enum atten {NONE, INVERSE_DIST, INVERSE_SQUARE} atyp; + float bright,halfIn,halfOut,falloff; // light brightness + Image *ctx; + Texture *tx; + StateSet *dstate; // used to represent the dw material in OSG +}; +// structure to use as data for tesselation + +typedef struct { + double pos[3]; // must be double for the tessellator to detect vertices + Vec2 uv; // texture coordainte - may not be used? + Vec3 nrmv; // surface normal + const dwmaterial *themat; + int idx; // index in the verts[] array +} avertex; + +class _face { +public: + _face() { opening=NULL; idx=NULL; nv=0; nop=0; nset=0; nrm[0]=nrm[1]=nrm[2]=0;} + ~_face() { delete [] idx;} + void setnv(const int n){ nv=n; idx=new int[n];} + void addvtx(const int n){ + if (nset < nv) { + idx[nset]=n; + nset++; + } + } + void addholevtx(const int nvtot) { + if (opening) { + opening[nop-1].addvtx(nvtot); + } + } + void norm(Vec3 &n, const Vec3 side, const Vec3 s2) const { + n=s2^side; // perpendicular + n.normalize(); // unit norm + } + const Vec3 getnorm(void) const { return nrm; } // use the predefined normal + void getside12(Vec3 &s1, Vec3 &s2, const Vec3 verts[]) const { + int ic=1; // counter for later vertices to ensure not coincident + int i1=idx[0]; // first vertex of face + int i2=idx[1]; // second, must be non-coincident + while (i2==i1) { + ic++; + i2=idx[ic]; + } + int i3=idx[ic]; // second, must be non-coincident + while (i3==i2 || i3==i1) { + ic++; + i3=idx[ic]; + } + s1=(verts[i2]-verts[i1]); // side 1 of face + s2=(verts[i3]-verts[i2]); // side 2 of face + } + void getnorm(const Vec3 verts[]) { + Vec3 side, s2; // used in cross product to find normal + getside12(side,s2, verts); + norm(nrm, s2, side); + } + void getsides(float *wid, float *ht, const Vec3 verts[]) const + { + Vec3 side, s2; // used in cross product to find normal + getside12(side,s2, verts); + *wid=side.length(); + *ht=s2.length(); + } + void settrans(Matrix &mx, const Vec3 nrm, const Vec3 verts[], const dwmaterial *mat) const { + // define the matrix perpendcular to normal for mapping textures + float wid=mat->getRepWid(); + float ht=mat->getRepHt(); + Vec3 r1, r2,r3; // 3 rows of rotation matrix + if (mat->isFullFace()) { // set wid, ht from polygon + Vec3 s2; // want transformed u coordinate parallel to 'r1' + getside12(r1,s2, verts); // r1 = edge of first side + getsides(&ht, &wid, verts); // get the lengths of sides for transformation of xyz to uv + r3=nrm; + r1.normalize(); + r2=r3^r1; + } else { + // mat.nrm= (0,0,1) AND mat (0,1,0) => (0,a,b) + // the transformation is unitary - preserves lengths; and + // converts points on a plane into (s,t, constant) coords for use with texturing + // Rinv.(0,0,1) = (nrm) implies R since Rinv=R(transpose) + r3=nrm; // already a unit vector + // mat.(010) = (0ab) -> Minv.(0ab) = (010); and this row DOT nrm=0 + if (r3.z() < 0.99f && r3.z() > -0.99f) { // not face parallel to ground - choose r1 perpendicular to nrm & 001 + r2.set(0,0,1); // therefore r1 is in plane of face. + r1=r2^r3; + r1.normalize(); + } else { // parallel to ground - make perpendicular to edge 1 of face + r1=verts[idx[1]]-verts[idx[0]]; + r1.normalize(); + } + r2=r3^r1; + } + for (int j=0; j<3; j++) { // and create the transpose matrix (inverse of rotation matrix) + mx._mat[0][j]=r1[j]; + mx._mat[1][j]=r2[j]; + mx._mat[2][j]=r3[j]; + } + // mx.postTrans(mx,0.5f,0.5f,0.0f); + mx._mat[0][0]*=1.0f/wid; + mx._mat[1][0]*=1.0f/wid; + mx._mat[0][1]*=1.0f/ht; + mx._mat[1][1]*=1.0f/ht; + if (mat->isFullFace()) { // set offset such that mx*verts[idx[0]] -> uv=(0,0) + Vec3 pos; + pos=mx*verts[idx[0]]; + mx._mat[0][3]=pos.x(); + mx._mat[1][3]=pos.y(); + mx._mat[2][3]=pos.z(); + } else { // scale inversely to the texture preferred repeat size + mx._mat[0][3]=0.5f/wid; + mx._mat[1][3]=0.5f/ht; + } + // mx.postScale(mx,1.0f/themat->TextureWidth, 1.0f/themat->TextureHeight,1); + } + inline int setnvop(const osg::ushort n) { // add a new hole in this face with n vertices + _face *oldop=opening; + opening=new _face[nop+1]; + for (int i=0; iidx=NULL;} + inline int getnv() { return nv;} + inline int getvert(const int j) { return idx[j];} + inline int complete() { return (idx && nv>0 && nset==nv);} // face has all defined + inline int holecomplete() { if (!opening) return 1; // no hole, so it is complete + return opening[nop-1].complete();} // latest opening in face has all vertices defined + int getallverts(void) const { int ntot=nv; + for (int i=0; i 0.0f) { // normals are parallel - reverse order of vertices + opening[i].reverse(); + opening[i].setnorm(verts); + } + } + } + void setposes(avertex &poses, const int j, const Vec3 verts[]) const { + poses.pos[0]=verts[idx[j]].x(); + poses.pos[1]=verts[idx[j]].y(); + poses.pos[2]=verts[idx[j]].z(); + poses.nrmv=nrm; + poses.idx=idx[j]; + } + void tesselate(const Vec3 verts[], const dwmaterial *themat, + GLUtesselator *ts, _dwobj *dwob, const Matrix *tmat) const; + void link(const int idop, const _face *f2, const int idop2,const Vec3 verts[], const dwmaterial *themat) const; // to join up opposed faces of a hole + inline const int getidx(int i) const { return idx[i];} +private: + void linkholes(const Vec3 verts[], const dwmaterial *themat, const _face *f2) const; + void reverse() { // reverse order of the vertices + for (int j=0; jidx; // vertex position index + nrms[nload]=pos->nrmv; + txcoords[nload].set(pos->uv[0],pos->uv[1]); + txidx[nload]=nload; // matrix transformed txc + + ntesverts[nbegin]++; + nload++; + } + void End() { + if (nbegin<20 && ntesverts[nbegin]>0) { + primlengs[nff+nbegin]=ntesverts[nbegin]; + nbegin++; + } + } + void begin(GLenum op) { // part of a tesselator callback - starts a new primitive of type op + if (nbegin<20) { // reSet counters + nbegtype[nbegin]=op; + ntesverts[nbegin]=0; + } + switch (op) { + case GL_TRIANGLES: + case GL_TRIANGLE_STRIP: + case GL_TRIANGLE_FAN: + case GL_QUADS: + case GL_QUAD_STRIP: + case GL_POLYGON: + break; + default: + // commenting out since this value is a local and + // is not used, RO July 2001. + // int i=0; + break; + } + } + void combine( GLdouble coords[3], avertex *d[4], + GLfloat w[4], avertex **dataOut , _dwobj *dwob); + void linkholes(const Vec3 verts[], const dwmaterial *themat, + const _face *f1, const _face *f2, + const int ipr[2], const int idx[], const int nv) { + gsidx[nload]=f1->getidx(ipr[1]); // vertex position index + gsidx[nload+1]=f1->getidx(ipr[0]); // vertex position index + gsidx[nload+2]=f2->getidx(nv-ipr[0]-1); // vertex position index + gsidx[nload+3]=f2->getidx(nv-ipr[1]-1); // vertex position index + + Matrix mx; // texture matrix transform to plane + Vec3 s1,s2; + Vec3 nrm; + s1=verts[gsidx[nload+1]]-verts[gsidx[nload]]; + s2=verts[gsidx[nload+2]]-verts[gsidx[nload+1]]; + f1->norm(nrm, s2, s1); + f1->settrans(mx, nrm, verts,themat); + for (int j=0; j<4; j++) { + Vec3 uv; + uv=mx*verts[gsidx[nload]]; + txcoords[nload].set(uv[0],uv[1]); + nrmidx[nload]=nload; + txidx[nload]=nload; // matrix transformed txc + nrms[nload]=nrm; // for per vertex normals + nload++; + } + nff++; + } + void setmode(int md, const int nfnvf) { // define the GL primitive type & number of expected vertices + GLenum mode[]= {GL_TRIANGLES, GL_TRIANGLE_STRIP, GL_TRIANGLE_FAN, + GL_QUADS, GL_QUAD_STRIP, GL_POLYGON}; + curmode=mode[md]; + gsidx=new osg::ushort[6*nfnvf]; + nrmidx=new osg::ushort[6*nfnvf]; + txidx=new osg::ushort[6*nfnvf]; + txcoords=new Vec2[6*nfnvf]; // one texture coord per vertex + nrms=new Vec3[6*nfnvf]; // one normal per face or per vertex + primlengs=new int[nfnvf]; // primitive lengths + nff=0; + nload=0; + } + void tesselate(const _face &fc, const Vec3 verts[], const dwmaterial *themat,GLUtesselator* ts, _dwobj *dwob) + { // generates a set of primitives all of one type (eg tris, qstrip trifan...) + nbegin=0; // number of triangle strips etc generated + fc.tesselate(verts, themat, ts, dwob, tmat); + nff+=nbegin; // the number of primitives generated + } + void buildDrawable(Group *grp, Vec3 verts[], dwmaterial *themat, const int nverts) { + if (nload>0 && nff>0) { // there are some strips of this type + Geode *geode = new Geode; + GeoSet *gset = new GeoSet; + osg::ushort *nunrmidx=new osg::ushort[nload]; + osg::ushort *nutxidx = new osg::ushort[nload]; + osg::ushort *nusidx = new osg::ushort[nload]; + Vec3 *nunrms=new Vec3[nload]; // one normal per face (nff) or per vertex (nload) + int *nuprimlengs=new int[nff]; // primitive lengths + Vec2 *nutxc=new Vec2[nload]; + int i; // general counter + for (i=0; iaddDrawable(gset); + grp->addChild( geode ); // add to the world outside + gset->setNumPrims( nff ); + switch (curmode) { + case GL_TRIANGLES: gset->setPrimType( osg::GeoSet::TRIANGLES ); + gset->setNumPrims( nload/3 ); + break; + case GL_TRIANGLE_STRIP: gset->setPrimType( osg::GeoSet::TRIANGLE_STRIP ); + gset->setPrimLengths( nuprimlengs ); + break; + case GL_TRIANGLE_FAN: gset->setPrimType( osg::GeoSet::TRIANGLE_FAN ); + gset->setPrimLengths( nuprimlengs ); + break; + case GL_QUADS: gset->setPrimType( osg::GeoSet::QUADS ); + gset->setNumPrims( nload/4 ); + break; + case GL_QUAD_STRIP: gset->setPrimType( osg::GeoSet::QUAD_STRIP ); + break; + case GL_POLYGON: gset->setPrimType( osg::GeoSet::POLYGON ); + break; + } + gset->setNormalBinding(osg::GeoSet::BIND_PERVERTEX); //BIND_PERPRIM); // + gset->setNormals(nunrms, nunrmidx); + + gset->setTextureCoords(nutxc,nutxidx); + gset->setCoords( verts, nusidx ); + if (themat->isType(dwmaterial::PointLight) || themat->isType(dwmaterial::SpotLight)) { + Vec4 pos; + pos.set(0,0,0,1); + for (int i=0; imakeLight(pos); + grp->addChild(ls); + } else { + StateSet *dstate=themat->make(); + gset->setStateSet( dstate ); + } + } else { + delete [] primlengs; + delete [] nrms; + delete [] gsidx; + delete [] nrmidx; + delete [] txcoords; + delete [] txidx; + primlengs=NULL; gsidx=NULL; nrmidx=NULL; + txidx=NULL; nrms=NULL; txcoords=NULL;; + } + } + void settmat(const Matrix *mx) { + tmat= mx; + } +private: + int nbegin; + int ntesverts[20]; // number of vertices in each primitive list - up to 20 restarts + GLenum nbegtype[20]; // up to 20 restarts + GLenum curmode; + int nload; // numebr of vertices loaded into these arrays + int nff; // primitive loaded + int *primlengs; + osg::ushort *gsidx; + osg::ushort *nrmidx; + osg::ushort *txidx; + Vec3 *nrms; // one normal per face + Vec2 *txcoords; // one texture coord per vertex + const Matrix *tmat; // local texture matrix, or may be NULL for default mapping +}; +static prims prd; + +// tesselation subroutines +void CALLBACK myFaceBegin(GLenum op) +{// tess vertex call back + prd.begin(op); + //glBegin(op); +} +void CALLBACK myFaceEnd() +{// tess vertex call back + if ( prd.isGLtype()) { // a prim of type == nvf ending; next counter needed + prd.End(); + } + //glEnd(); +} +void CALLBACK myVertex(void *pv) +{// tess vertex call back with texture coord == void *pv1, + // dwob needed if there is a combine callback to add the new vertex to group + if (prd.isGLtype()) { // a prim of type == nvf being created; use this vertex + prd.addv((avertex *)pv); + } +} +void CALLBACK combineCallback( GLdouble coords[3], avertex *d[4], + GLfloat w[4], avertex **dataOut , _dwobj *dwob) +{ + prd.combine(coords, d, w, dataOut,dwob); +} +void CALLBACK error (GLenum errno) +{ // tess error code + const unsigned char *errm=gluErrorString(errno); + printf("tesselator error %d %s\n", errno,errm);//, errm +} + //========== +void _face::linkholes(const Vec3 verts[], const dwmaterial *themat, const _face *f2) const +{ + int ipr[2]; + ipr[0]=nv-1; + for (int i=0; iopening[idop2]); +} +//======== Edges link 2 vertices; indicate where a sharp crease can be found ========== +class _dwedge { +public: + _dwedge(){;} + ~_dwedge(){;} + void set(int i, int j) { e1=i; e2=j; } +private: + int e1,e2; // ends of the edge - it joins verts[e1] to verts[e2] +}; +//=================== +class _dwobj { // class for design workshop read of a single object +public: + _dwobj() {oldv=verts=NULL; nverts=nfaces=0; openings=NULL;faces=NULL; tmat=NULL; edges=NULL; + nopens=nfaceverts=0; fc1=fc2=NULL; colour[0]=colour[1]=colour[2]=colour[3]=1; + } + ~_dwobj() {/*delete verts; delete faces;delete openings;*/ + delete fc1;delete fc2; + } + int readOpenings(FILE *fp, const int nexpected) + { // read up to nexpected openings, each opening may have a number of vertices + char buff[256]; + openings=new int[nexpected*2]; + fc1=new osg::ushort[nexpected]; + fc2=new osg::ushort[nexpected]; + nopens=0; + int nvop=0; // current number of vertices in hole in object + while (nopenssetmx(&mx); // may be used by combine callback to define txcoord + gluTessBeginPolygon(ts, dwob); + gluTessBeginContour(ts); /**/ + for (int j=0; jpos[0] = coords[0]; + newv->pos[1] = coords[1]; + newv->pos[2] = coords[2]; + newv->uv[0] = newv->uv[1] =0; + newv->nrmv[0] = newv->nrmv[1] = newv->nrmv[2] =0; + for (int i=0; i<4; i++) { + if (d[i]) { + newv->uv[0] = w[i]*d[i]->uv[0]; + newv->uv[1] = w[i]*d[i]->uv[1]; + newv->nrmv[0] = w[i]*d[i]->nrmv[0]; + newv->nrmv[1] = w[i]*d[i]->nrmv[1]; + newv->nrmv[2] = w[i]*d[i]->nrmv[2]; + newv->themat=d[i]->themat; + } + } + dwob->makeuv(newv->uv, newv->pos); + newv->idx=dwob->addvtx(coords[0], coords[1], coords[2]); + *dataOut = newv; + } else { + *dataOut = NULL; + } +} +void _dwobj::buildDrawable(Group *grp) +{ // current DWobject complete; make a drawable, and add it to a osg::Group + if (nfaces>0) { + int nvf; + int nfnvf=0; // number of vertices for faces plus holes + int i; // a general counter + for (i=0; i0) obj.readOpenings(fp, nexpected); + } else if( strncmp(buff,"UVW:",4)==0) { // texture application matrix + Matrix mx; + sscanf(buff+4,"%f %f %f%f %f %f%f %f %f", + &mx._mat[0][0], &mx._mat[0][1], &mx._mat[0][2], + &mx._mat[1][0], &mx._mat[1][1], &mx._mat[1][2], + &mx._mat[2][0], &mx._mat[2][1], &mx._mat[2][2]); + obj.settmat(&mx); + } + } + + } + fclose( fp ); + obj.buildDrawable(grp); // tidy up any remaining objects + + return grp; + + } +private: +}; + +int dwfgets(char *clin, int max, FILE *fin) +{ // replace fgets to detect EOL = char 13 as well as Creturn=10 GWM 111100 + // Macintosh produced files (such as those obtainable + //from the great buildings site at www.Artifice.com) use 13 format, PC models use 10. + int nread=0; + char c1=1; + do { + if (!feof( fin )) { + clin[nread]=c1=fgetc(fin); + nread++; + } + } while (nread0) clin[nread-1]='\0'; // null terminate and remove training blank + return nread; +} + +// now register with osg::Registry to instantiate the above +// reader/writer. +osgDB::RegisterReaderWriterProxy g_readerWriter_DW_Proxy; + diff --git a/src/osgPlugins/flt/BoundingVolumeRecords.cpp b/src/osgPlugins/flt/BoundingVolumeRecords.cpp index 418b8434a..0df11358c 100644 --- a/src/osgPlugins/flt/BoundingVolumeRecords.cpp +++ b/src/osgPlugins/flt/BoundingVolumeRecords.cpp @@ -6,7 +6,6 @@ using namespace flt; - //////////////////////////////////////////////////////////////////// // // BoundingBoxRecord @@ -15,7 +14,6 @@ using namespace flt; RegisterRecordProxy g_BoundingBoxProxy; - BoundingBoxRecord::BoundingBoxRecord() { } @@ -32,7 +30,6 @@ void BoundingBoxRecord::endian() } - //////////////////////////////////////////////////////////////////// // // BoundingSphereRecord @@ -41,7 +38,6 @@ void BoundingBoxRecord::endian() RegisterRecordProxy g_BoundingSphereProxy; - BoundingSphereRecord::BoundingSphereRecord() { } @@ -58,7 +54,6 @@ void BoundingSphereRecord::endian() } - //////////////////////////////////////////////////////////////////// // // BoundingCylinderRecord @@ -67,7 +62,6 @@ void BoundingSphereRecord::endian() RegisterRecordProxy g_BoundingCylinderProxy; - BoundingCylinderRecord::BoundingCylinderRecord() { } @@ -92,7 +86,6 @@ void BoundingCylinderRecord::endian() RegisterRecordProxy g_BoundingVolumeCenterProxy; - BoundingVolumeCenterRecord::BoundingVolumeCenterRecord() { } @@ -117,7 +110,6 @@ void BoundingVolumeCenterRecord::endian() RegisterRecordProxy g_BoundingVolumeOrientationProxy; - BoundingVolumeOrientationRecord::BoundingVolumeOrientationRecord() { } @@ -132,5 +124,3 @@ BoundingVolumeOrientationRecord::~BoundingVolumeOrientationRecord() void BoundingVolumeOrientationRecord::endian() { } - - diff --git a/src/osgPlugins/flt/BoundingVolumeRecords.h b/src/osgPlugins/flt/BoundingVolumeRecords.h index 5ba1af8c8..bf8450e5f 100644 --- a/src/osgPlugins/flt/BoundingVolumeRecords.h +++ b/src/osgPlugins/flt/BoundingVolumeRecords.h @@ -21,7 +21,7 @@ namespace flt { typedef struct BoundingBoxTag { - SRecHeader RecHeader; + SRecHeader RecHeader; #if 0 Int 4 Reserved Double 8 x coordinate of lowest corner @@ -65,7 +65,7 @@ class BoundingBoxRecord : public AncillaryRecord typedef struct BoundingSphereTag { - SRecHeader RecHeader; + SRecHeader RecHeader; #if 0 Unsigned Int 2 Length of the record Int 4 Reserved @@ -105,7 +105,7 @@ class BoundingSphereRecord : public AncillaryRecord typedef struct BoundingCylinderTag { - SRecHeader RecHeader; + SRecHeader RecHeader; #if 0 Int 4 Reserved Double 8 Radius of the cylinder base @@ -144,7 +144,7 @@ class BoundingCylinderRecord : public AncillaryRecord typedef struct BoundingVolumeCenterTag { - SRecHeader RecHeader; + SRecHeader RecHeader; #if 0 Int 4 Reserved Double 8 x coordinate of center @@ -184,7 +184,7 @@ class BoundingVolumeCenterRecord : public AncillaryRecord typedef struct BoundingVolumeOrientationTag { - SRecHeader RecHeader; + SRecHeader RecHeader; #if 0 Int 2 Bounding Volume Orientation Opcode 109 Unsigned Int 2 Length of the record diff --git a/src/osgPlugins/flt/ColorPaletteRecord.cpp b/src/osgPlugins/flt/ColorPaletteRecord.cpp index 533d2dadf..425660cab 100644 --- a/src/osgPlugins/flt/ColorPaletteRecord.cpp +++ b/src/osgPlugins/flt/ColorPaletteRecord.cpp @@ -7,17 +7,14 @@ using namespace flt; - //////////////////////////////////////////////////////////////////// // // MaterialPaletteRecord // //////////////////////////////////////////////////////////////////// - RegisterRecordProxy g_ColorPaletteRecordProxy; - ColorPaletteRecord::ColorPaletteRecord() { } @@ -32,24 +29,48 @@ ColorPaletteRecord::~ColorPaletteRecord() // virtual void ColorPaletteRecord::endian() { - SColorPalette* pSColor = (SColorPalette*)getData(); - int nOffset = sizeof(SColorPalette); - - if (nOffset < getSize()) + // note, sizeof returns unsigned int, while getSize() etc returns + // int, this correctly generates a warning when comparisons are made + // under Linux. This really needs to be fixed so getSize() returns + // an unsigned int. I won't do it now as it may well break code + // which I don't fully understand. I've made the hacky use of an + // (int) cast to fix the warning, I don't think this will cause an + // problems. RO August 2001. + if (getSize() > (int) sizeof(SOldColorPalette)) { - int n = 0; - ENDIAN( pSColor->nNames ); + SColorPalette* pSColor = (SColorPalette*)getData(); + int nOffset = sizeof(SColorPalette); - while ((n++ < pSColor->nNames) && (nOffset < getSize())) + if (nOffset < getSize()) { - SColorName* pName = (SColorName*)((char*)getData())+nOffset; - ENDIAN( pName->swSize ); - ENDIAN( pName->nIndex ); - nOffset += pName->swSize; - }; + int n = 0; + ENDIAN( pSColor->nNames ); + + while ((n++ < pSColor->nNames) && (nOffset < getSize())) + { + SColorName* pName = (SColorName*)((char*)getData())+nOffset; + ENDIAN( pName->swSize ); + ENDIAN( pName->nIndex ); + nOffset += pName->swSize; + }; + } + } + else // version 11, 12 & 13 + { + SOldColorPalette* pSColor = (SOldColorPalette*)getData(); + unsigned int i; + for (i=0; i < sizeof(pSColor->Colors)/sizeof(pSColor->Colors[0]); i++) + { + ENDIAN( pSColor->Colors[i]._red ); + ENDIAN( pSColor->Colors[i]._green ); + ENDIAN( pSColor->Colors[i]._blue ); + } + + for (i=0; i < sizeof(pSColor->FixedColors)/sizeof(pSColor->FixedColors[0]); i++) + { + ENDIAN( pSColor->FixedColors[i]._red ); + ENDIAN( pSColor->FixedColors[i]._green ); + ENDIAN( pSColor->FixedColors[i]._blue ); + } } } - - - - diff --git a/src/osgPlugins/flt/ColorPaletteRecord.h b/src/osgPlugins/flt/ColorPaletteRecord.h index 579427d99..6f75ee689 100644 --- a/src/osgPlugins/flt/ColorPaletteRecord.h +++ b/src/osgPlugins/flt/ColorPaletteRecord.h @@ -30,14 +30,22 @@ struct SColorName struct SColorPalette { - SRecHeader RecHeader; - char szReserved[128]; // Reserved - color32 Colors[1024]; // Color 0 - 1023 - int32 nNames; + SRecHeader RecHeader; + char szReserved[128]; // Reserved + color32 Colors[1024]; // Color 0 - 1023 + int32 nNames; // Followed by SColorName. SColorName is of valiable length! }; +struct SOldColorPalette +{ + SRecHeader RecHeader; + color48 Colors[32]; // Color 0 - 31 + color48 FixedColors[56]; // Fixed Intensity Color 0 - 55 (4096-> ) +}; + + class ColorPaletteRecord : public AncillaryRecord { public: diff --git a/src/osgPlugins/flt/CommentRecord.cpp b/src/osgPlugins/flt/CommentRecord.cpp index f87a23154..db299b0ab 100644 --- a/src/osgPlugins/flt/CommentRecord.cpp +++ b/src/osgPlugins/flt/CommentRecord.cpp @@ -4,7 +4,6 @@ #include "Registry.h" #include "CommentRecord.h" - using namespace flt; //////////////////////////////////////////////////////////////////// @@ -15,7 +14,6 @@ using namespace flt; RegisterRecordProxy g_CommentRecordProxy; - CommentRecord::CommentRecord() { } @@ -31,7 +29,3 @@ CommentRecord::~CommentRecord() void CommentRecord::endian() { } - - - - diff --git a/src/osgPlugins/flt/CommentRecord.h b/src/osgPlugins/flt/CommentRecord.h index 07d3b543c..d4b122f05 100644 --- a/src/osgPlugins/flt/CommentRecord.h +++ b/src/osgPlugins/flt/CommentRecord.h @@ -20,7 +20,7 @@ namespace flt { typedef struct CommentTag { - SRecHeader RecHeader; + SRecHeader RecHeader; // TODO } SComment; diff --git a/src/osgPlugins/flt/ControlRecord.cpp b/src/osgPlugins/flt/ControlRecord.cpp index 9da7b2e1d..e4c6d338b 100644 --- a/src/osgPlugins/flt/ControlRecord.cpp +++ b/src/osgPlugins/flt/ControlRecord.cpp @@ -1,15 +1,10 @@ // ControlRecord.cpp - - #include "Registry.h" #include "ControlRecord.h" - using namespace flt; - - RegisterRecordProxy g_PushLevelProxy; RegisterRecordProxy g_PopLevelProxy; @@ -18,4 +13,3 @@ RegisterRecordProxy g_PopSubfaceProxy; RegisterRecordProxy g_PushExtensionProxy; RegisterRecordProxy g_PopExtensionProxy; - diff --git a/src/osgPlugins/flt/DofRecord.cpp b/src/osgPlugins/flt/DofRecord.cpp index c5c957011..13ea38c0f 100644 --- a/src/osgPlugins/flt/DofRecord.cpp +++ b/src/osgPlugins/flt/DofRecord.cpp @@ -6,7 +6,6 @@ using namespace flt; - //////////////////////////////////////////////////////////////////// // // DofRecord @@ -15,7 +14,6 @@ using namespace flt; RegisterRecordProxy g_DofProxy; - DofRecord::DofRecord() { } @@ -29,24 +27,20 @@ DofRecord::~DofRecord() void DofRecord::endian() { - SDegreeOfFreedom *pSDof = (SDegreeOfFreedom*)getData(); + SDegreeOfFreedom *pSDof = (SDegreeOfFreedom*)getData(); ENDIAN( pSDof->diReserved ); pSDof->OriginLocalDOF.endian(); pSDof->PointOnXaxis.endian(); pSDof->PointInXYplane.endian(); - pSDof->dfZ.endian(); - pSDof->dfY.endian(); - pSDof->dfX.endian(); - pSDof->dfPitch.endian(); - pSDof->dfRoll.endian(); - pSDof->dfYaw.endian(); - pSDof->dfZscale.endian(); - pSDof->dfYscale.endian(); - pSDof->dfXscale.endian(); - ENDIAN( pSDof->dwFlags ); + pSDof->dfZ.endian(); + pSDof->dfY.endian(); + pSDof->dfX.endian(); + pSDof->dfPitch.endian(); + pSDof->dfRoll.endian(); + pSDof->dfYaw.endian(); + pSDof->dfZscale.endian(); + pSDof->dfYscale.endian(); + pSDof->dfXscale.endian(); + ENDIAN( pSDof->dwFlags ); } - - - - diff --git a/src/osgPlugins/flt/DofRecord.h b/src/osgPlugins/flt/DofRecord.h index 83cda932d..605012724 100644 --- a/src/osgPlugins/flt/DofRecord.h +++ b/src/osgPlugins/flt/DofRecord.h @@ -15,10 +15,10 @@ namespace flt { struct SRange { - float64 _dfMin; // Minimum value with respect to the local coord system - float64 _dfMax; // Maximum value with respect to the local coordsystem - float64 _dfCurrent; // Current value with respect to the local coord system - float64 _dfIncrement; // Increment + float64 _dfMin; // Minimum value with respect to the local coord system + float64 _dfMax; // Maximum value with respect to the local coordsystem + float64 _dfCurrent; // Current value with respect to the local coord system + float64 _dfIncrement; // Increment inline float64 minRange() { return _dfMin; } inline float64 maxRange() { return _dfMax; } @@ -35,22 +35,22 @@ struct SRange typedef struct DegreeOfFreedomTag { - SRecHeader RecHeader; - char szIdent[8]; // 7 char ASCII ID; 0 terminates - int32 diReserved; // Reserved - float64x3 OriginLocalDOF; // Origin (x,y,z) of the DOF's local coordinate system - float64x3 PointOnXaxis; // Point (x,y,z) on the x-axis of the DOF's local coord system - float64x3 PointInXYplane; // Point (x,y,z) in xy plane of the DOF's local coord system - SRange dfZ; // Legal z values with respect to the local coord system - SRange dfY; // Legal y values with respect to the local coord system - SRange dfX; // Legal x values with respect to the local coord system - SRange dfPitch; // Legal pitch values (rotation about the x-axis) - SRange dfRoll; // Legal roll values( rotation about the y-axis) - SRange dfYaw; // Legal yaw values (rotation about the z-axis) - SRange dfZscale; // Legal z scale values (about local origin) - SRange dfYscale; // Legal y scale values about local origin) - SRange dfXscale; // Legal x scale values (about local origin) - uint32 dwFlags; // Flags, bits from left to right (see OF doc) + SRecHeader RecHeader; + char szIdent[8]; // 7 char ASCII ID; 0 terminates + int32 diReserved; // Reserved + float64x3 OriginLocalDOF; // Origin (x,y,z) of the DOF's local coordinate system + float64x3 PointOnXaxis; // Point (x,y,z) on the x-axis of the DOF's local coord system + float64x3 PointInXYplane; // Point (x,y,z) in xy plane of the DOF's local coord system + SRange dfZ; // Legal z values with respect to the local coord system + SRange dfY; // Legal y values with respect to the local coord system + SRange dfX; // Legal x values with respect to the local coord system + SRange dfPitch; // Legal pitch values (rotation about the x-axis) + SRange dfRoll; // Legal roll values( rotation about the y-axis) + SRange dfYaw; // Legal yaw values (rotation about the z-axis) + SRange dfZscale; // Legal z scale values (about local origin) + SRange dfYscale; // Legal y scale values about local origin) + SRange dfXscale; // Legal x scale values (about local origin) + uint32 dwFlags; // Flags, bits from left to right (see OF doc) } SDegreeOfFreedom; diff --git a/src/osgPlugins/flt/ExtensionRecord.cpp b/src/osgPlugins/flt/ExtensionRecord.cpp index dab5ca885..f22db28b2 100644 --- a/src/osgPlugins/flt/ExtensionRecord.cpp +++ b/src/osgPlugins/flt/ExtensionRecord.cpp @@ -6,7 +6,6 @@ using namespace flt; - //////////////////////////////////////////////////////////////////// // // ExtensionRecord @@ -15,7 +14,6 @@ using namespace flt; RegisterRecordProxy g_ExtensionProxy; - ExtensionRecord::ExtensionRecord() { } @@ -29,11 +27,8 @@ ExtensionRecord::~ExtensionRecord() void ExtensionRecord::endian() { - SExtension *pExtension = (SExtension*)getData(); + SExtension *pExtension = (SExtension*)getData(); -// VALID_RECORD(SHeader, pRecHdr) - ENDIAN( pExtension->code ); + // VALID_RECORD(SHeader, pRecHdr) + ENDIAN( pExtension->code ); } - - - diff --git a/src/osgPlugins/flt/ExtensionRecord.h b/src/osgPlugins/flt/ExtensionRecord.h index 985c86fe8..ed07b7352 100644 --- a/src/osgPlugins/flt/ExtensionRecord.h +++ b/src/osgPlugins/flt/ExtensionRecord.h @@ -24,7 +24,7 @@ namespace flt { typedef struct ExtensionTag { - SRecHeader RecHeader; + SRecHeader RecHeader; char szIdent[8]; // 7 char ASCII ID; 0 terminates char site[8]; // Site ID - Unique site name diff --git a/src/osgPlugins/flt/ExternalRecord.cpp b/src/osgPlugins/flt/ExternalRecord.cpp index 3c1f3e3e2..004546d7e 100644 --- a/src/osgPlugins/flt/ExternalRecord.cpp +++ b/src/osgPlugins/flt/ExternalRecord.cpp @@ -1,6 +1,5 @@ // ExternalRecord.cpp - #include "flt.h" #include "Registry.h" #include "FltFile.h" @@ -16,37 +15,33 @@ using namespace flt; RegisterRecordProxy g_ExternalProxy; - ExternalRecord::ExternalRecord() { - _pExternal = NULL; } // virtual ExternalRecord::~ExternalRecord() { - if (_pExternal) - _pExternal->unref(); } void ExternalRecord::setExternal(FltFile* pExternal) { - if (_pExternal) - _pExternal->unref(); - - _pExternal = pExternal; - _pExternal->ref(); + _fltfile = pExternal; } void ExternalRecord::endian() { - SExternalReference *pSExternal = (SExternalReference*)getData(); + SExternalReference *pSExternal = (SExternalReference*)getData(); - ENDIAN( pSExternal->diFlags ); + if (getSize() >= sizeof(SExternalReference)) + { + ENDIAN( pSExternal->diFlags ); + } + else + { + pSExternal->diFlags = 0; + } } - - - diff --git a/src/osgPlugins/flt/ExternalRecord.h b/src/osgPlugins/flt/ExternalRecord.h index 172de0fa1..7f64ac28d 100644 --- a/src/osgPlugins/flt/ExternalRecord.h +++ b/src/osgPlugins/flt/ExternalRecord.h @@ -8,23 +8,25 @@ #include "Record.h" #include "RecordVisitor.h" +#include namespace flt { struct SExternalReference { - SRecHeader RecHeader; - char szPath[200]; // 199 char ASCII Path; 0 terminates - uint8 swReserved[4]; // Reserved - int32 diFlags; // Flags (bits from left to right) - // 0 = Color Palette Override - // 1 = Material Palette Override - // 2 = Texture Palette Override - // 3 = Line Palette Override - // 4 = Sound Palette Override - // 5 = Light source Palette Override - // 6-31 Spare - int16 iReserved; // Reserved + SRecHeader RecHeader; + char szPath[200]; // 199 char ASCII Path; 0 terminates + // version 11, 12 & 13 stops here! + uint8 swReserved[4]; // Reserved + int32 diFlags; // Flags (bits from left to right) + // 0 = Color Palette Override + // 1 = Material Palette Override + // 2 = Texture Palette Override + // 3 = Line Palette Override + // 4 = Sound Palette Override + // 5 = Light source Palette Override + // 6-31 Spare +// int16 iReserved; // Reserved }; @@ -42,7 +44,7 @@ class ExternalRecord : public PrimNodeRecord SExternalReference* getData() const { return (SExternalReference*)_pData; } void setExternal(FltFile* pExternal); - FltFile* getExternal() { return _pExternal; } + FltFile* getExternal() { return _fltfile.get(); } const std::string getFilename( void ) const { return std::string(getData()->szPath); } protected: @@ -53,7 +55,7 @@ class ExternalRecord : public PrimNodeRecord virtual void endian(); - FltFile* _pExternal; + osg::ref_ptr _fltfile; }; diff --git a/src/osgPlugins/flt/FaceRecord.cpp b/src/osgPlugins/flt/FaceRecord.cpp index 87e341d22..be1dc9db2 100644 --- a/src/osgPlugins/flt/FaceRecord.cpp +++ b/src/osgPlugins/flt/FaceRecord.cpp @@ -5,7 +5,6 @@ #include "FaceRecord.h" #include "Input.h" - using namespace flt; //////////////////////////////////////////////////////////////////// @@ -16,7 +15,6 @@ using namespace flt; RegisterRecordProxy g_FaceProxy; - FaceRecord::FaceRecord() { } @@ -56,7 +54,7 @@ int FaceRecord::getVertexPoolOffset(int index) void FaceRecord::endian() { - SFace *pSFace = (SFace*)getData(); + SFace *pSFace = (SFace*)getData(); ENDIAN( pSFace->diIRColor ); ENDIAN( pSFace->iObjectRelPriority ); @@ -69,17 +67,20 @@ void FaceRecord::endian() ENDIAN( pSFace->iFeature ); ENDIAN( pSFace->diIRMaterial ); ENDIAN( pSFace->wTransparency ); - ENDIAN( pSFace->diFlags ); -// ENDIAN( pSFace->PrimaryPackedColor ); -// ENDIAN( pSFace->SecondaryPackedColor ); - ENDIAN( pSFace->iTextureMapIndex ); - ENDIAN( pSFace->dwPrimaryColorIndex ); - ENDIAN( pSFace->dwAlternateColorIndex ); + + // Added after version 13 + if (getSize() >= sizeof(SFace)) + { + ENDIAN( pSFace->dwFlags ); + // ENDIAN( pSFace->PrimaryPackedColor ); + // ENDIAN( pSFace->SecondaryPackedColor ); + ENDIAN( pSFace->iTextureMapIndex ); + ENDIAN( pSFace->dwPrimaryColorIndex ); + ENDIAN( pSFace->dwAlternateColorIndex ); + } } - - // virtual bool FaceRecord::readLocalData(Input& fr) { @@ -114,7 +115,6 @@ bool FaceRecord::readLocalData(Input& fr) } - //////////////////////////////////////////////////////////////////// // // VertexListRecord @@ -123,7 +123,6 @@ bool FaceRecord::readLocalData(Input& fr) RegisterRecordProxy g_VertexListProxy; - VertexListRecord::VertexListRecord() { } @@ -143,7 +142,7 @@ int VertexListRecord::numberOfVertices() int VertexListRecord::getVertexPoolOffset(int index) { - SSingleVertexList *pSVertexList = (SSingleVertexList*)getData(); + SSingleVertexList *pSVertexList = (SSingleVertexList*)getData(); if ((index >= 0) && (index < numberOfVertices())) return pSVertexList->diSOffset[index]; @@ -154,29 +153,16 @@ int VertexListRecord::getVertexPoolOffset(int index) void VertexListRecord::endian() { - SSingleVertexList *pSVertexList = (SSingleVertexList*)getData(); - int nNumberOfVertices = numberOfVertices(); + SSingleVertexList *pSVertexList = (SSingleVertexList*)getData(); + int nNumberOfVertices = numberOfVertices(); - for(int i=0; i < nNumberOfVertices; i++) - { + for(int i=0; i < nNumberOfVertices; i++) + { ENDIAN( pSVertexList->diSOffset[i] ); } } - - - -// virtual -bool VertexListRecord::readLocalData(Input& fr) -{ - // A vertex node is a leaf node in the database and - // therefore cannot have any children. - return true; -} - - - //////////////////////////////////////////////////////////////////// // // MorphVertexListRecord @@ -185,7 +171,6 @@ bool VertexListRecord::readLocalData(Input& fr) RegisterRecordProxy g_MorphVertexListRecordProxy; - MorphVertexListRecord::MorphVertexListRecord() { } @@ -205,62 +190,10 @@ int MorphVertexListRecord::numberOfVertices() void MorphVertexListRecord::endian() { -// SMorphVertexList *pSMorpVertexList = (SMorphVertexList*)getData(); + // SMorphVertexList *pSMorpVertexList = (SMorphVertexList*)getData(); } - - - -// virtual -bool MorphVertexListRecord::readLocalData(Input& fr) -{ - // A vertex node is a leaf node in the database and - // therefore cannot have any children. - return true; -} - - -//////////////////////////////////////////////////////////////////// -// -// UnknownListRecord -// -//////////////////////////////////////////////////////////////////// - -//RegisterRecordProxy g_UnknownListProxy; - - -UnknownListRecord::UnknownListRecord() -{ -} - - -// virtual -UnknownListRecord::~UnknownListRecord() -{ -} - - -void UnknownListRecord::endian() -{ -} - - - - - -// virtual -bool UnknownListRecord::readLocalData(Input& fr) -{ - // A vertex node is a leaf node in the database and - // therefore cannot have any children. - return true; -} - - - - - //////////////////////////////////////////////////////////////////// // // VectorRecord @@ -269,7 +202,6 @@ bool UnknownListRecord::readLocalData(Input& fr) RegisterRecordProxy g_VectorProxy; - VectorRecord::VectorRecord() { } @@ -283,10 +215,7 @@ VectorRecord::~VectorRecord() void VectorRecord::endian() { - SVector *pSVector = (SVector*)getData(); + SVector *pSVector = (SVector*)getData(); pSVector->Vec.endian(); } - - - diff --git a/src/osgPlugins/flt/FaceRecord.h b/src/osgPlugins/flt/FaceRecord.h index 5be918d91..68f74d15e 100644 --- a/src/osgPlugins/flt/FaceRecord.h +++ b/src/osgPlugins/flt/FaceRecord.h @@ -22,61 +22,62 @@ namespace flt { struct SFace { - SRecHeader RecHeader; - char szIdent[8]; // 7 char ASCII ID; 0 terminates - int32 diIRColor; // IR Color Code - int16 iObjectRelPriority; // Polygon relative priority - uint8 swDrawFlag; // How to draw the polygon - // = 0 Draw solid backfaced - // = 1 Draw solid no backface - // = 2 Draw wireframe and not closed - // = 3 Draw closed wireframe - // = 4 Surround with wireframe in alternate color - // = 8 Omni-directional light - // = 9 Unidirectional light - // = 10 Bidirectional light - uint8 swTexWhite; // if TRUE, draw textured polygon white (see note 1 below) - uint16 wPrimaryNameIndex; // Color name index - uint16 wSecondaryNameIndex; // Alternate color name index - uint8 swNotUsed; // Not used - uint8 swTemplateTrans; // Set template transparency - // = 0 None - // = 1 Fixed - // = 2 Axis type rotate - // = 4 Point rotate - int16 iDetailTexturePattern; // Detail texture pattern no. -1 if none - int16 iTexturePattern; // Texture pattern no. -1 if none - int16 iMaterial; // Material code [0-63]. -1 if none - int16 iSurfaceMaterial; // Surface material code (for DFAD) - int16 iFeature; // Feature ID (for DFAD) - int32 diIRMaterial; // IR Material codes - uint16 wTransparency; // Transparency - // = 0 opaque - // = 65535 for totally clear - uint8 swInfluenceLODGen; // LOD Generation Control - uint8 swLinestyle; // Linestyle Index - int32 diFlags; // Flags (bits from to right) - // 0 = Terrain - // 1 = No Color - // 2 = No Alt Color - // 3 = Packed color - // 4 = Terrain culture cutout (footprint) - // 5 = Hidden (not drawn) - // 6-31 Spare - uint8 swLightMode; // Lightmode - // = 0 use face color, not illuminated - // = 1 use vertex color, not illuminated - // = 2 use face color and vertex normal - // = 3 use vertex color and vertex normal + SRecHeader RecHeader; + char szIdent[8]; // 7 char ASCII ID; 0 terminates + int32 diIRColor; // IR Color Code + int16 iObjectRelPriority; // Polygon relative priority + uint8 swDrawFlag; // How to draw the polygon + // = 0 Draw solid backfaced + // = 1 Draw solid no backface + // = 2 Draw wireframe and not closed + // = 3 Draw closed wireframe + // = 4 Surround with wireframe in alternate color + // = 8 Omni-directional light + // = 9 Unidirectional light + // = 10 Bidirectional light + uint8 swTexWhite; // if TRUE, draw textured polygon white (see note 1 below) + uint16 wPrimaryNameIndex; // Color name index + uint16 wSecondaryNameIndex; // Alternate color name index + uint8 swNotUsed; // Not used + uint8 swTemplateTrans; // Set template transparency + // = 0 None + // = 1 Fixed + // = 2 Axis type rotate + // = 4 Point rotate + int16 iDetailTexturePattern; // Detail texture pattern no. -1 if none + int16 iTexturePattern; // Texture pattern no. -1 if none + int16 iMaterial; // Material code [0-63]. -1 if none + int16 iSurfaceMaterial; // Surface material code (for DFAD) + int16 iFeature; // Feature ID (for DFAD) + int32 diIRMaterial; // IR Material codes + uint16 wTransparency; // Transparency + // = 0 opaque + // = 65535 for totally clear + // version 11, 12 & 13 stops here! + uint8 swInfluenceLODGen; // LOD Generation Control + uint8 swLinestyle; // Linestyle Index + uint32 dwFlags; // Flags (bits from left to right) + // 0 = Terrain + // 1 = No Color + // 2 = No Alt Color + // 3 = Packed color + // 4 = Terrain culture cutout (footprint) + // 5 = Hidden (not drawn) + // 6-31 Spare + uint8 swLightMode; // Lightmode + // = 0 use face color, not illuminated + // = 1 use vertex color, not illuminated + // = 2 use face color and vertex normal + // = 3 use vertex color and vertex normal - uint8 swReserved1[7]; // Reserved - color32 PrimaryPackedColor; // Packed Color Primary (A, B, G, R) - color32 SecondaryPackedColor; // Packed Color Secondary (A, B, G, R) - int16 iTextureMapIndex; // Texture mapping index - int16 iReserved2; - uint32 dwPrimaryColorIndex; - uint32 dwAlternateColorIndex; - int16 iReserved3[2]; + uint8 Reserved1[7]; // Reserved + color32 PrimaryPackedColor; // Packed Color Primary (A, B, G, R) + color32 SecondaryPackedColor; // Packed Color Secondary (A, B, G, R) + int16 iTextureMapIndex; // Texture mapping index + int16 iReserved2; + uint32 dwPrimaryColorIndex; + uint32 dwAlternateColorIndex; + uint16 Reserved3[2]; }; @@ -92,14 +93,23 @@ class FaceRecord : public PrimNodeRecord SURROUND_ALTERNATE_COLOR = 4, OMNIDIRECTIONAL_LIGHT = 8, UNIDIRECTIONAL_LIGHT = 9, - BIDIRECTIONAL_LIGHT = 10 + BIDIRECTIONAL_LIGHT = 10 }; enum LightMode { FACE_COLOR = 0, VERTEX_COLOR = 1, FACE_COLOR_LIGHTING = 2, - VERTEX_COLOR_LIGHTING = 3, + VERTEX_COLOR_LIGHTING = 3 + }; + + enum FlagBit { + TERRAIN_BIT = 0x80000000, + NO_COLOR_BIT = 0x40000000, + NO_ALT_COLOR_BIT = 0x20000000, + PACKED_COLOR_BIT = 0x10000000, + FOOTPRINT_BIT = 0x08000000, + HIDDEN_BIT = 0x04000000 }; FaceRecord(); @@ -135,10 +145,10 @@ class FaceRecord : public PrimNodeRecord // //////////////////////////////////////////////////////////////////// -typedef struct SingleVertexListTag +typedef struct SingleVertexListTag { - SRecHeader RecHeader; - int32 diSOffset[1]; // Byte offset to this vertex record in vertex table, + SRecHeader RecHeader; + int32 diSOffset[1]; // Byte offset to this vertex record in vertex table, // the actual vertex of the face } SSingleVertexList; @@ -163,10 +173,6 @@ class VertexListRecord : public PrimNodeRecord protected: virtual ~VertexListRecord(); - - virtual bool readLocalData(Input& fr); -// virtual bool writeLocalData(Output& fw); - virtual void endian(); }; @@ -177,9 +183,9 @@ class VertexListRecord : public PrimNodeRecord // //////////////////////////////////////////////////////////////////// -typedef struct MorphVertexListTag +typedef struct MorphVertexListTag { - SRecHeader RecHeader; + SRecHeader RecHeader; uint32 dwOffset0; // Byte offset into vertex palette of the 0% vertex uint32 dwOffset100; // Byte offset into vertex palette of the 100% vertex } SMorphVertexList; @@ -204,45 +210,10 @@ class MorphVertexListRecord : public PrimNodeRecord protected: virtual ~MorphVertexListRecord(); - - virtual bool readLocalData(Input& fr); -// virtual bool writeLocalData(Output& fw); - virtual void endian(); }; - -//////////////////////////////////////////////////////////////////// -// -// UnknownListRecord -// -//////////////////////////////////////////////////////////////////// - - - -class UnknownListRecord : public PrimNodeRecord -{ - public: - UnknownListRecord(); - - virtual Record* clone() const { return new UnknownListRecord(); } - virtual const char* className() const { return "UnknownListRecord"; } - virtual int classOpcode() const { return 53; } -// virtual void accept(RecordVisitor& rv) { rv.apply(*this); } -// virtual void traverse(RecordVisitor& rv); - - protected: - virtual ~UnknownListRecord(); - - virtual bool readLocalData(Input& fr); -// virtual bool writeLocalData(Output& fw); - - virtual void endian(); -}; - - - //////////////////////////////////////////////////////////////////// // // VectorRecord @@ -253,10 +224,10 @@ class UnknownListRecord : public PrimNodeRecord // Its only use is to provide the direction vector for old-style // unidirectional and bidirectional light point faces. -typedef struct VectorTag +typedef struct VectorTag { - SRecHeader RecHeader; - float32x3 Vec; + SRecHeader RecHeader; + float32x3 Vec; } SVector; diff --git a/src/osgPlugins/flt/FltFile.cpp b/src/osgPlugins/flt/FltFile.cpp index 043eb908c..fe755f661 100644 --- a/src/osgPlugins/flt/FltFile.cpp +++ b/src/osgPlugins/flt/FltFile.cpp @@ -1,39 +1,35 @@ // FltFile.cpp -#include #include #include #include #include "FltFile.h" +#include "Registry.h" #include "Record.h" #include "RecordVisitor.h" #include "ExternalRecord.h" -#include "flt2osg.h" // ConvertFromFLT +#include "flt2osg.h" // ConvertFromFLT #include "Input.h" using namespace flt; - FltFile::FltFile( - ColorPool* pColorPool, - TexturePool* pTexturePool, - MaterialPool* pMaterialPool) +ColorPool* pColorPool, +TexturePool* pTexturePool, +MaterialPool* pMaterialPool) { - if (pColorPool) - _pColorPool = pColorPool; - else - _pColorPool = &_colorPool; + _pColorPool = pColorPool; - if (pTexturePool) - _pTexturePool = pTexturePool; - else + if (pTexturePool) + _pTexturePool = pTexturePool; + else _pTexturePool = &_texturePool; - if (pMaterialPool) - _pMaterialPool = pMaterialPool; - else + if (pMaterialPool) + _pMaterialPool = pMaterialPool; + else _pMaterialPool = &_materialPool; _pHeaderRecord = NULL; @@ -61,8 +57,8 @@ osg::Node* FltFile::readNode(const std::string& fileName) // Convert record tree to osg scene graph node = convert(); - - pRootRec->unref(); // delete record tree + + pRootRec->unref(); // delete record tree return node; } @@ -102,12 +98,11 @@ Record* FltFile::readFile(const std::string& fileName) return NULL; } - if (pRec->isPrimaryNode()) // Header - pRec->readLocalData(fin); // Read rest of file + if (pRec->isPrimaryNode()) // Header + pRec->readLocalData(fin);// Read rest of file fin.close(); - return pRec; } @@ -121,29 +116,47 @@ public: setTraverseMode(RecordVisitor::TRAVERSE_ALL_CHILDREN); } +#define REGISTER_FLT 1 + virtual void apply(ExternalRecord& rec) { SExternalReference* pSExternal = (SExternalReference*)rec.getData(); - osg::notify(osg::INFO) << "External=" << pSExternal->szPath << endl; - - ColorPool* pColorPool = NULL; - TexturePool* pTexturePool = NULL; - MaterialPool* pMaterialPool = NULL; - - if (pSExternal->diFlags & BIT0) - pColorPool = _fltFile->getColorPool(); - - if (pSExternal->diFlags & BIT2) - pTexturePool = _fltFile->getTexturePool(); - - if (pSExternal->diFlags & BIT1) - pMaterialPool = _fltFile->getMaterialPool(); - - FltFile* flt = new FltFile(pColorPool, pTexturePool, pMaterialPool); - if (flt) + if (pSExternal) { - flt->readModel(pSExternal->szPath); + FltFile* flt = NULL; + ColorPool* pColorPool = NULL; + TexturePool* pTexturePool = NULL; + MaterialPool* pMaterialPool = NULL; + std::string filename(pSExternal->szPath); + + osg::notify(osg::INFO) << "External=" << filename << endl; + + if (_fltFile && _fltFile->getFlightVersion() > 13) + { + if (pSExternal->diFlags & BIT0) + pColorPool = _fltFile->getColorPool(); + + if (pSExternal->diFlags & BIT2) + pTexturePool = _fltFile->getTexturePool(); + + if (pSExternal->diFlags & BIT1) + pMaterialPool = _fltFile->getMaterialPool(); + } + +#if REGISTER_FLT + flt = Registry::instance()->getFltFile(filename); + if (flt == NULL) + { + flt = new FltFile(pColorPool, pTexturePool, pMaterialPool); + flt->readModel(filename); + } + Registry::instance()->addFltFile(filename, flt); +#else + flt = new FltFile(pColorPool, pTexturePool, pMaterialPool); + flt->readModel(filename); +#endif + rec.setExternal(flt); } } @@ -152,6 +165,7 @@ public: FltFile* _fltFile; }; + void FltFile::readExternals(Record* pRec) { @@ -163,4 +177,13 @@ void FltFile::readExternals(Record* pRec) } - +int FltFile::getFlightVersion() +{ + if (_pHeaderRecord) + { + SHeader* pSHeader = (SHeader*)_pHeaderRecord->getData(); + if (pSHeader) + return pSHeader->diFormatRevLev; + } + return 0; +} diff --git a/src/osgPlugins/flt/FltFile.h b/src/osgPlugins/flt/FltFile.h index 3b8b354db..c02ef401b 100644 --- a/src/osgPlugins/flt/FltFile.h +++ b/src/osgPlugins/flt/FltFile.h @@ -7,9 +7,10 @@ #include #include -#include +#include #include "Pool.h" +#include "HeaderRecord.h" namespace flt { @@ -32,9 +33,15 @@ public: Record* getHeaderRecord() { return _pHeaderRecord; } Record* readModel(const std::string& fileName); - ColorPool* getColorPool() { return _pColorPool; } - TexturePool* getTexturePool() { return _pTexturePool; } - MaterialPool* getMaterialPool() { return _pMaterialPool; } + ColorPool* getColorPool() { return _pColorPool; } + TexturePool* getTexturePool() { return _pTexturePool; } + MaterialPool* getMaterialPool() { return _pMaterialPool; } + + void useLocalColorPool() { _pColorPool = &_colorPool; } + void useLocalTexturePool() { _pTexturePool = &_texturePool; } + void useLocalMaterialPool() { _pMaterialPool = &_materialPool; } + + int getFlightVersion(); protected: @@ -55,6 +62,7 @@ private: }; + }; // end namespace flt #endif diff --git a/src/osgPlugins/flt/FltRecords.h b/src/osgPlugins/flt/FltRecords.h index f2663aec2..e12c72fd6 100644 --- a/src/osgPlugins/flt/FltRecords.h +++ b/src/osgPlugins/flt/FltRecords.h @@ -13,37 +13,37 @@ namespace flt { -typedef struct MorphingVertexListTag +typedef struct MorphingVertexListTag { - SRecHeader RecHeader; - int32 diAOffset; // Byte offset to the actual vertex record in the vertex table. - int32 diMOffset; // Byte offset to the morph vertex record in the vertex table. -} SMorphingVertexList; // see OF doc + SRecHeader RecHeader; + int32 diAOffset; // Byte offset to the actual vertex record in the vertex table. + int32 diMOffset; // Byte offset to the morph vertex record in the vertex table. +} SMorphingVertexList; // see OF doc typedef struct ReplicateTag { - SRecHeader RecHeader; - int16 iNumber; // Number of replications - int16 iSpare; // Spare for fullword alignment + SRecHeader RecHeader; + int16 iNumber; // Number of replications + int16 iSpare; // Spare for fullword alignment } SReplicate; /* -typedef struct ReferenceTag // OBSOLETE +typedef struct ReferenceTag // OBSOLETE { - SRecHeader RecHeader; - int16 iSpare; // Spare - int16 iNumber; // Instance definition number + SRecHeader RecHeader; + int16 iSpare; // Spare + int16 iNumber; // Instance definition number } SReference; -typedef struct DefinitionTag // OBSOLETE +typedef struct DefinitionTag // OBSOLETE { - SRecHeader RecHeader; - int16 iSpare; // Spare - int16 iNumber; // Instance definition number + SRecHeader RecHeader; + int16 iSpare; // Spare + int16 iNumber; // Instance definition number } SDefinition; */ @@ -53,9 +53,9 @@ typedef struct DefinitionTag // OBSOLETE /* typedef struct ColorTableTag { - SRecHeader RecHeader; - char szReserved[128];// Reserved - color32 Colors[1024]; // Array of brightest RGB of color 0 - 1024 + SRecHeader RecHeader; + char szReserved[128];// Reserved + color32 Colors[1024]; // Array of brightest RGB of color 0 - 1024 } SColorTable; // this record is sometimes immediately followed by a: int32 numberOfColorNames @@ -64,20 +64,20 @@ typedef struct ColorTableTag typedef struct ColorNameListTag { - uint16 wEntryLength; - int16 iReserved_1; - int16 iEntryIndex; - int16 iReserved_2; - char *szName; // calc length of string from wEntryLength + uint16 wEntryLength; + int16 iReserved_1; + int16 iEntryIndex; + int16 iReserved_2; + char *szName; // calc length of string from wEntryLength } SColorNameList; */ /* typedef struct ComponentTag { - float32 sfRed; // red component of material - float32 sfGreen; // green component of material - float32 sfBlue; // blue component of material + float32 sfRed; // red component of material + float32 sfGreen; // green component of material + float32 sfBlue; // blue component of material } SComponent; */ diff --git a/src/osgPlugins/flt/GeoSetBuilder.cpp b/src/osgPlugins/flt/GeoSetBuilder.cpp index 86304d73e..cd09715af 100644 --- a/src/osgPlugins/flt/GeoSetBuilder.cpp +++ b/src/osgPlugins/flt/GeoSetBuilder.cpp @@ -1,5 +1,9 @@ // GeoSetBuilder.cpp +#ifdef WIN32 +#pragma warning( disable : 4786 ) +#endif + #include "flt.h" #include "FltFile.h" #include "Pool.h" @@ -11,22 +15,22 @@ #include #include -#include #include #include -#include #include #include #include #include +#include +#include +#include #include -#include #include +#include using namespace flt; - //////////////////////////////////////////////////////////////////// // // GeoSetBuilder @@ -58,7 +62,7 @@ GeoSetBuilder::~GeoSetBuilder() void GeoSetBuilder::initPrimData() { _appearance.init(); - _aVertex.erase(_aVertex.begin(), _aVertex.end()); + _aVertex.clear(); } @@ -82,10 +86,10 @@ osg::Geode* GeoSetBuilder::createOsgGeoSets(osg::Geode* geode) { osg::GeoSet* gset = (*itr)->createOsgGeoSet(); if (gset) - geode->addGeoSet(gset); + geode->addDrawable(gset); } - if (bInternalGeodeAllocation && (geode->getNumGeosets() == 0)) + if (bInternalGeodeAllocation && (geode->getNumDrawables() == 0)) { geode->unref(); return NULL; @@ -132,7 +136,6 @@ bool GeoSetBuilder::addPrimitive() //////////////////////// protected ///////////////////////////////// - TmpGeoSet* GeoSetBuilder::findMatchingGeoSet() { @@ -143,7 +146,7 @@ TmpGeoSet* GeoSetBuilder::findMatchingGeoSet() if (_appearance == (*itr)->_appearance) return *itr; } - + return NULL; } @@ -181,21 +184,21 @@ PrimitiveType GeoSetBuilder::findPrimType( int nVertices) switch (nVertices) { - case 1: - primtype = osg::GeoSet::POINTS; - break; - case 2: - primtype = osg::GeoSet::LINES; - break; - case 3: - primtype = osg::GeoSet::TRIANGLES; - break; - case 4: - primtype = osg::GeoSet::QUADS; - break; - default: - if (nVertices >= 5) primtype = osg::GeoSet::POLYGON; - break; + case 1: + primtype = osg::GeoSet::POINTS; + break; + case 2: + primtype = osg::GeoSet::LINES; + break; + case 3: + primtype = osg::GeoSet::TRIANGLES; + break; + case 4: + primtype = osg::GeoSet::QUADS; + break; + default: + if (nVertices >= 5) primtype = osg::GeoSet::POLYGON; + break; } return primtype; @@ -210,7 +213,6 @@ PrimitiveType GeoSetBuilder::findPrimType( int nVertices) // GeoSet with dynamic size. Used by GeoSetBuilder as a temp. buffer. - TmpGeoSet::TmpGeoSet(FltFile* pFltFile) { _pFltFile = pFltFile; @@ -248,37 +250,39 @@ osg::GeoSet* TmpGeoSet::createOsgGeoSet() gset->setNumPrims(prims); gset->setPrimType(_appearance.getPrimType()); - osg::GeoState* gstate = new osg::GeoState; - gset->setGeoState(gstate); + osg::StateSet* gstate = new osg::StateSet; + gset->setStateSet(gstate); // Material osg::Material* osgMaterial = _appearance.getMaterial(); if (osgMaterial) - { - gstate->setAttribute(osg::GeoState::MATERIAL, osgMaterial); - } + gstate->setAttribute(osgMaterial); - // Color BIND_OVERALL - if (_appearance.getColorBinding() == osg::GeoSet::BIND_OVERALL) + // Color + switch(_appearance.getColorBinding()) { - osg::Vec4* color = new osg::Vec4[1]; - *color = _appearance.getColor(); - gset->setColorBinding(_appearance.getColorBinding()); - gset->setColors(color); - } + case osg::GeoSet::BIND_OVERALL: + { + osg::Vec4* color = new osg::Vec4[1]; + *color = _appearance.getFaceColor(); + gset->setColorBinding(osg::GeoSet::BIND_OVERALL); + gset->setColors(color); + } + break; - // Color BIND_PERVERTEX - if (_appearance.getColorBinding() == osg::GeoSet::BIND_PERVERTEX) - { - gset->setColorBinding(_appearance.getColorBinding()); - gset->setColors(new osg::Vec4[indices]); + case osg::GeoSet::BIND_PERVERTEX: + { + gset->setColorBinding(osg::GeoSet::BIND_PERVERTEX); + gset->setColors(new osg::Vec4[indices]); + } + break; } // Transparency if (_appearance.getTransparency()) { - gstate->setMode(osg::GeoState::TRANSPARENCY, osg::GeoState::ON); - gstate->setAttribute(osg::GeoState::TRANSPARENCY, new osg::Transparency); + gstate->setMode(GL_BLEND,osg::StateAttribute::ON); + gstate->setRenderingHint(osg::StateSet::TRANSPARENT_BIN); } // Cull face @@ -287,29 +291,27 @@ osg::GeoSet* TmpGeoSet::createOsgGeoSet() osg::CullFace* cullface = new osg::CullFace; if (cullface) { - gstate->setMode(osg::GeoState::FACE_CULL, osg::GeoState::ON); cullface->setMode(osg::CullFace::BACK); - gstate->setAttribute(osg::GeoState::FACE_CULL, cullface); + gstate->setAttributeAndModes(cullface, osg::StateAttribute::ON); } } else { - gstate->setMode(osg::GeoState::FACE_CULL, osg::GeoState::OFF); + gstate->setMode(GL_CULL_FACE, osg::StateAttribute::OFF); } // Texture if (_appearance.getTexture()) { - gstate->setMode( osg::GeoState::TEXTURE, osg::GeoState::ON ); - gstate->setAttribute( osg::GeoState::TEXTURE, _appearance.getTexture() ); - gstate->setAttribute( osg::GeoState::TEXENV, new osg::TexEnv ); + gstate->setAttributeAndModes( _appearance.getTexture(), osg::StateAttribute::ON ); + gstate->setAttribute( new osg::TexEnv ); } // Lighting if (_appearance.getLighting()) - gstate->setMode( osg::GeoState::LIGHTING, osg::GeoState::ON ); + gstate->setMode( GL_LIGHTING, osg::StateAttribute::ON ); else - gstate->setMode( osg::GeoState::LIGHTING, osg::GeoState::OFF ); + gstate->setMode( GL_LIGHTING, osg::StateAttribute::OFF ); // Subface if (_appearance.getSubface() > 0) @@ -318,9 +320,9 @@ osg::GeoSet* TmpGeoSet::createOsgGeoSet() if (polyoffset) { int level = _appearance.getSubface(); - gstate->setMode(osg::GeoState::POLYGON_OFFSET,osg::GeoState::ON); - polyoffset->setOffset(-1*level, -20*level); - gstate->setAttribute(osg::GeoState::POLYGON_OFFSET, polyoffset); + polyoffset->setFactor(-1*level); + polyoffset->setUnits(-20*level); + gstate->setAttributeAndModes(polyoffset,osg::StateAttribute::ON); } } @@ -330,10 +332,8 @@ osg::GeoSet* TmpGeoSet::createOsgGeoSet() osg::Point* point = new osg::Point; if (point) { - gstate->setMode(osg::GeoState::POINT,osg::GeoState::ON); point->setSize(8); - point->enableSmooth(); - gstate->setAttribute(osg::GeoState::POINT, point); + gstate->setAttributeAndModes(point,osg::StateAttribute::ON); } } @@ -350,36 +350,52 @@ osg::GeoSet* TmpGeoSet::createOsgGeoSet() // Vertices switch(_appearance.getVertexOp()) { - case VERTEX_C_OP: - gset->setCoords(new osg::Vec3[indices]); - break; - case VERTEX_CN_OP: - gset->setNormalBinding(osg::GeoSet::BIND_PERVERTEX); - gset->setCoords(new osg::Vec3[indices]); - gset->setNormals(new osg::Vec3[indices]); - break; - case VERTEX_CT_OP: - gset->setTextureBinding(osg::GeoSet::BIND_PERVERTEX); - gset->setCoords(new osg::Vec3[indices]); - gset->setTextureCoords(new osg::Vec2[indices]); - break; - case VERTEX_CNT_OP: - gset->setNormalBinding(osg::GeoSet::BIND_PERVERTEX); - gset->setTextureBinding(osg::GeoSet::BIND_PERVERTEX); - gset->setCoords(new osg::Vec3[indices]); - gset->setNormals(new osg::Vec3[indices]); - gset->setTextureCoords(new osg::Vec2[indices]); - break; - case OLD_VERTEX_OP: - gset->setCoords(new osg::Vec3[indices]); - break; - case OLD_VERTEX_COLOR_OP: - gset->setCoords(new osg::Vec3[indices]); - break; - case OLD_VERTEX_COLOR_NORMAL_OP: - gset->setCoords(new osg::Vec3[indices]); -// gset->setNormals(new osg::Vec3[indices]); - break; + case VERTEX_C_OP: + gset->setCoords(new osg::Vec3[indices]); + break; + case VERTEX_CN_OP: + gset->setNormalBinding(osg::GeoSet::BIND_PERVERTEX); + gset->setCoords(new osg::Vec3[indices]); + gset->setNormals(new osg::Vec3[indices]); + break; + case VERTEX_CT_OP: + gset->setTextureBinding(osg::GeoSet::BIND_PERVERTEX); + gset->setCoords(new osg::Vec3[indices]); + gset->setTextureCoords(new osg::Vec2[indices]); + break; + case VERTEX_CNT_OP: + gset->setNormalBinding(osg::GeoSet::BIND_PERVERTEX); + gset->setTextureBinding(osg::GeoSet::BIND_PERVERTEX); + gset->setCoords(new osg::Vec3[indices]); + gset->setNormals(new osg::Vec3[indices]); + gset->setTextureCoords(new osg::Vec2[indices]); + break; + case OLD_VERTEX_OP: + gset->setCoords(new osg::Vec3[indices]); + if (_appearance.getTexture()) + { + gset->setTextureBinding(osg::GeoSet::BIND_PERVERTEX); + gset->setTextureCoords(new osg::Vec2[indices]); + } + break; + case OLD_VERTEX_COLOR_OP: + gset->setCoords(new osg::Vec3[indices]); + if (_appearance.getTexture()) + { + gset->setTextureBinding(osg::GeoSet::BIND_PERVERTEX); + gset->setTextureCoords(new osg::Vec2[indices]); + } + break; + case OLD_VERTEX_COLOR_NORMAL_OP: + gset->setCoords(new osg::Vec3[indices]); + gset->setNormalBinding(osg::GeoSet::BIND_PERVERTEX); + gset->setNormals(new osg::Vec3[indices]); + if (_appearance.getTexture()) + { + gset->setTextureBinding(osg::GeoSet::BIND_PERVERTEX); + gset->setTextureCoords(new osg::Vec2[indices]); + } + break; } @@ -401,14 +417,13 @@ osg::GeoSet* TmpGeoSet::createOsgGeoSet() ///////////////////////// private ////////////////////////////////// - void TmpGeoSet::setVertex(osg::GeoSet* gset, int index, Record* vertex) { bool bColorBindPerVertex = _appearance.getColorBinding() == osg::GeoSet::BIND_PERVERTEX; switch(_appearance.getVertexOp()) { - case VERTEX_C_OP: + case VERTEX_C_OP: { SVertex* pVert = (SVertex*)vertex->getData(); osg::Vec3* coords = gset->getCoords(); @@ -417,23 +432,28 @@ void TmpGeoSet::setVertex(osg::GeoSet* gset, int index, Record* vertex) (float)pVert->Coord.x(), (float)pVert->Coord.y(), (float)pVert->Coord.z()); + if (bColorBindPerVertex) { osg::Vec4* colors = gset->getColors(); - if (pVert->swFlags & BIT3) - colors[index] = pVert->PackedColor.get(); + if (pVert->swFlags & V_NO_COLOR_BIT) + colors[index] = _appearance.getFaceColor(); else { - ColorPool* pColorPool = _pFltFile->getColorPool(); - if (pColorPool) + if (pVert->swFlags & V_PACKED_COLOR_BIT) + colors[index] = pVert->PackedColor.get(); + else + { + ColorPool* pColorPool = _pFltFile->getColorPool(); colors[index] = pColorPool->getColor(pVert->dwVertexColorIndex); + } } } } break; - case VERTEX_CN_OP: + case VERTEX_CN_OP: { SNormalVertex* pVert = (SNormalVertex*)vertex->getData(); osg::Vec3* coords = gset->getCoords(); @@ -447,28 +467,33 @@ void TmpGeoSet::setVertex(osg::GeoSet* gset, int index, Record* vertex) (float)pVert->Normal.x(), (float)pVert->Normal.y(), (float)pVert->Normal.z()); + if (bColorBindPerVertex) { osg::Vec4* colors = gset->getColors(); - if (pVert->swFlags & BIT3) - colors[index] = pVert->PackedColor.get(); + if (pVert->swFlags & V_NO_COLOR_BIT) + colors[index] = _appearance.getFaceColor(); else { - ColorPool* pColorPool = _pFltFile->getColorPool(); - if (pColorPool) + if (pVert->swFlags & V_PACKED_COLOR_BIT) + colors[index] = pVert->PackedColor.get(); + else + { + ColorPool* pColorPool = _pFltFile->getColorPool(); colors[index] = pColorPool->getColor(pVert->dwVertexColorIndex); + } } } } break; - case VERTEX_CNT_OP: + case VERTEX_CNT_OP: { SNormalTextureVertex* pVert = (SNormalTextureVertex*)vertex->getData(); osg::Vec3* coords = gset->getCoords(); osg::Vec3* normals = gset->getNormals(); - osg::Vec2* texuv = gset->getTCoords(); + osg::Vec2* texuv = gset->getTextureCoords(); coords[index].set( (float)pVert->Coord.x(), @@ -481,27 +506,32 @@ void TmpGeoSet::setVertex(osg::GeoSet* gset, int index, Record* vertex) texuv[index].set( (float)pVert->Texture.x(), (float)pVert->Texture.y()); + if (bColorBindPerVertex) { osg::Vec4* colors = gset->getColors(); - if (pVert->swFlags & BIT3) - colors[index] = pVert->PackedColor.get(); + if (pVert->swFlags & V_NO_COLOR_BIT) + colors[index] = _appearance.getFaceColor(); else { - ColorPool* pColorPool = _pFltFile->getColorPool(); - if (pColorPool) + if (pVert->swFlags & V_PACKED_COLOR_BIT) + colors[index] = pVert->PackedColor.get(); + else + { + ColorPool* pColorPool = _pFltFile->getColorPool(); colors[index] = pColorPool->getColor(pVert->dwVertexColorIndex); + } } } } break; - case VERTEX_CT_OP: + case VERTEX_CT_OP: { STextureVertex* pVert = (STextureVertex*)vertex->getData(); osg::Vec3* coords = gset->getCoords(); - osg::Vec2* texuv = gset->getTCoords(); + osg::Vec2* texuv = gset->getTextureCoords(); coords[index].set( (float)pVert->Coord.x(), @@ -510,65 +540,111 @@ void TmpGeoSet::setVertex(osg::GeoSet* gset, int index, Record* vertex) texuv[index].set( (float)pVert->Texture.x(), (float)pVert->Texture.y()); + if (bColorBindPerVertex) { osg::Vec4* colors = gset->getColors(); - if (pVert->swFlags & BIT3) - colors[index] = pVert->PackedColor.get(); + if (pVert->swFlags & V_NO_COLOR_BIT) + colors[index] = _appearance.getFaceColor(); else { - ColorPool* pColorPool = _pFltFile->getColorPool(); - if (pColorPool) + if (pVert->swFlags & V_PACKED_COLOR_BIT) + colors[index] = pVert->PackedColor.get(); + else + { + ColorPool* pColorPool = _pFltFile->getColorPool(); colors[index] = pColorPool->getColor(pVert->dwVertexColorIndex); + } } } } break; - case OLD_VERTEX_OP: + case OLD_VERTEX_OP: { SOldVertex* pVert = (SOldVertex*)vertex->getData(); osg::Vec3* coords = gset->getCoords(); + osg::Vec2* texuv = gset->getTextureCoords(); coords[index].set( (float)pVert->v[0], (float)pVert->v[1], (float)pVert->v[2]); + + if (texuv && vertex->getSize() >= sizeof(SOldVertex)) + { + texuv[index].set( + (float)pVert->t[0], + (float)pVert->t[1]); + } } break; - case OLD_VERTEX_COLOR_OP: + case OLD_VERTEX_COLOR_OP: { SOldVertexColor* pVert = (SOldVertexColor*)vertex->getData(); osg::Vec3* coords = gset->getCoords(); + osg::Vec2* texuv = gset->getTextureCoords(); coords[index].set( (float)pVert->v[0], (float)pVert->v[1], (float)pVert->v[2]); + + if (bColorBindPerVertex) + { + osg::Vec4* colors = gset->getColors(); + ColorPool* pColorPool = _pFltFile->getColorPool(); + if (pColorPool && (pVert->color_index >= 0)) + colors[index] = pColorPool->getColor(pVert->color_index); + else + colors[index] = _appearance.getFaceColor(); + } + + if (texuv && vertex->getSize() >= sizeof(SOldVertexColor)) + { + texuv[index].set( + (float)pVert->t[0], + (float)pVert->t[1]); + } } break; - case OLD_VERTEX_COLOR_NORMAL_OP: + case OLD_VERTEX_COLOR_NORMAL_OP: { SOldVertexColorNormal* pVert = (SOldVertexColorNormal*)vertex->getData(); osg::Vec3* coords = gset->getCoords(); -// osg::Vec3* normals = gset->getNormals(); + osg::Vec3* normals = gset->getNormals(); + osg::Vec2* texuv = gset->getTextureCoords(); coords[index].set( - (float)pVert->Coord[0], - (float)pVert->Coord[1], - (float)pVert->Coord[2]); -/* + (float)pVert->v[0], + (float)pVert->v[1], + (float)pVert->v[2]); normals[index].set( - (float)pVert->Normal[0], - (float)pVert->Normal[1], - (float)pVert->Normal[2]); -*/ + (float)pVert->n[0] / (1<<30), // =pow(2,30) + (float)pVert->n[1] / (1<<30), + (float)pVert->n[2] / (1<<30)); + + if (bColorBindPerVertex) + { + osg::Vec4* colors = gset->getColors(); + ColorPool* pColorPool = _pFltFile->getColorPool(); + if (pColorPool && (pVert->color_index >= 0)) + colors[index] = pColorPool->getColor(pVert->color_index); + else + colors[index] = _appearance.getFaceColor(); + } + + if (texuv && vertex->getSize() >= sizeof(SOldVertexColorNormal)) + { + texuv[index].set( + (float)pVert->t[0], + (float)pVert->t[1]); + } } break; } } - diff --git a/src/osgPlugins/flt/GeoSetBuilder.h b/src/osgPlugins/flt/GeoSetBuilder.h index 3b74f4daa..5b999913f 100644 --- a/src/osgPlugins/flt/GeoSetBuilder.h +++ b/src/osgPlugins/flt/GeoSetBuilder.h @@ -7,6 +7,7 @@ #include #include +#include #include #include #include @@ -15,10 +16,8 @@ namespace osg { class Node; class LOD; -class GeoSet; class Geode; class GeoState; -class Material; class Texture; } @@ -52,7 +51,7 @@ public: _primtype = osg::GeoSet::NO_TYPE; _material = NULL; _texture = NULL; - _color = osg::Vec4(1,1,1,1); + _face_color = osg::Vec4(1,1,1,1); _color_binding = osg::GeoSet::BIND_OFF; _cullface = false; _transparency = false; @@ -66,11 +65,11 @@ public: void setPrimType(PrimitiveType pt) { _primtype = pt; } PrimitiveType getPrimType() { return _primtype; } - void setColor(osg::Vec4 color) { _color = color; } - osg::Vec4& getColor() { return _color; } + void setFaceColor(osg::Vec4 color) { _face_color = color; } + osg::Vec4& getFaceColor() { return _face_color; } - void setColorBinding( BindingType binding ) { _color_binding = binding; } - BindingType getColorBinding() { return _color_binding; } + inline void setColorBinding( BindingType binding ) { _color_binding = binding; } + inline const BindingType getColorBinding() const { return _color_binding; } void setMaterial(osg::Material *material) { _material = material; } osg::Material* getMaterial() { return _material; } @@ -102,7 +101,7 @@ public: if (_color_binding != b) return false; if (_color_binding == osg::GeoSet::BIND_OVERALL) - return (_color == c); + return (_face_color == c); return true; } @@ -111,7 +110,7 @@ public: return ((_nVertexOp == a._nVertexOp) && (_primtype == a._primtype) && mat_equal(a._material) - && col_equal(a._color_binding, a._color) + && col_equal(a._color_binding, a._face_color) && (_texture == a._texture) && (_cullface == a._cullface) && (_transparency == a._transparency) @@ -125,7 +124,7 @@ private: PrimitiveType _primtype; osg::Material* _material; osg::Texture* _texture; - osg::Vec4 _color; // BIND_OVERALL + osg::Vec4 _face_color; BindingType _color_binding; bool _cullface; bool _transparency; @@ -152,8 +151,8 @@ public: void addVertex(Record* vertex); void setPrimType(PrimitiveType pt) { _appearance.setPrimType(pt); } - void setColor(osg::Vec4 color) { _appearance.setColor(color); } - void setColorBinding(BindingType binding ) { _appearance.setColorBinding(binding); } + void setFaceColor(osg::Vec4 color) { _appearance.setFaceColor(color); } + void setColorBinding(const BindingType binding) { _appearance.setColorBinding(binding); } void setMaterial(osg::Material *material) { _appearance.setMaterial(material); } void setTexture(osg::Texture *texture) { _appearance.setTexture(texture); } void setCullface(bool cullface) { _appearance.setCullface(cullface); } @@ -162,7 +161,7 @@ public: void setSubface(int level) { _appearance.setSubface(level); } PrimitiveType getPrimType() { return _appearance.getPrimType(); } - osg::Vec4& getColor() { return _appearance.getColor(); } + osg::Vec4& getFaceColor() { return _appearance.getFaceColor(); } BindingType getColorBinding() { return _appearance.getColorBinding(); } osg::Material* getMaterial() { return _appearance.getMaterial(); } osg::Texture* getTexture() { return _appearance.getTexture(); } @@ -226,7 +225,7 @@ private: -} // end of namespace flt +} // end of namespace flt diff --git a/src/osgPlugins/flt/GroupRecord.cpp b/src/osgPlugins/flt/GroupRecord.cpp index 0e758715a..7d98c7142 100644 --- a/src/osgPlugins/flt/GroupRecord.cpp +++ b/src/osgPlugins/flt/GroupRecord.cpp @@ -1,6 +1,5 @@ // GroupRecord.cpp - #include "flt.h" #include "Registry.h" #include "GroupRecord.h" @@ -15,7 +14,6 @@ using namespace flt; RegisterRecordProxy g_GroupProxy; - GroupRecord::GroupRecord() { } @@ -29,7 +27,7 @@ GroupRecord::~GroupRecord() void GroupRecord::endian() { - SGroup *pSGroup = (SGroup*)getData(); + SGroup *pSGroup = (SGroup*)getData(); ENDIAN( pSGroup->iGroupRelPriority ); ENDIAN( pSGroup->dwFlags ); @@ -37,8 +35,3 @@ void GroupRecord::endian() ENDIAN( pSGroup->iSpecialId_2 ); ENDIAN( pSGroup->iSignificance ); } - - - - - diff --git a/src/osgPlugins/flt/GroupRecord.h b/src/osgPlugins/flt/GroupRecord.h index eb558b14c..b5038806b 100644 --- a/src/osgPlugins/flt/GroupRecord.h +++ b/src/osgPlugins/flt/GroupRecord.h @@ -13,23 +13,23 @@ namespace flt { struct SGroup { - SRecHeader RecHeader; - char szIdent[8]; // 7 char ASCII ID; 0 terminates - int16 iGroupRelPriority; // Group relative priority - int16 iSpare; // Spare for fullword alignment - uint32 dwFlags; // Flags (bits, from left to right) - // 0 = Reserved - // 1 = Forward animation - // 2 = Cycling animation - // 3 = Bounding box follows - // 4 = Freeze bounding box - // 5 = Default parent - // 6-31 Spare - int16 iSpecialId_1; // Special effects ID 1 - defined by real time - int16 iSpecialId_2; // Special effects ID 2 - defined by real time - int16 iSignificance; // Significance Flags - uint8 swLayer; // Layer Number - uint8 swReserved[5]; // Reserved + SRecHeader RecHeader; + char szIdent[8]; // 7 char ASCII ID; 0 terminates + int16 iGroupRelPriority; // Group relative priority + int16 iSpare; // Spare for fullword alignment + uint32 dwFlags; // Flags (bits, from left to right) + // 0 = Reserved + // 1 = Forward animation + // 2 = Cycling animation + // 3 = Bounding box follows + // 4 = Freeze bounding box + // 5 = Default parent + // 6-31 Spare + int16 iSpecialId_1; // Special effects ID 1 - defined by real time + int16 iSpecialId_2; // Special effects ID 2 - defined by real time + int16 iSignificance; // Significance Flags + uint8 swLayer; // Layer Number + uint8 swReserved[5]; // Reserved }; diff --git a/src/osgPlugins/flt/HeaderRecord.cpp b/src/osgPlugins/flt/HeaderRecord.cpp index a75da0448..dd94c12be 100644 --- a/src/osgPlugins/flt/HeaderRecord.cpp +++ b/src/osgPlugins/flt/HeaderRecord.cpp @@ -9,6 +9,62 @@ using namespace flt; +/* +From MultiGen-Paradigm User Forum: +http://www.multigen-paradigm.com/ubb/Forum8/HTML/000035.html + +Q: +Hi, +I am using the MultiGen API to read .flt files. Today I received a +.flt file with Packed color for polygons. Going through the MGAPI +documentation I didn't find anything about Packed colors in polygons +except fltPolyFlagRgbMode, which is set to "1" in that file. +Could you please answer the following questions: +1) Name of the parameter used for Packed +primary color in the fltPolygon structure; +2) The function to read the values. +Regards, Zoia. + + +A: +The short answer is: +There is no fltPolygon attribute that defines the packed color. +You need to use mgGetPolyColorRGB and mgGetPolyAltColorRGB to +get the primary and alternate rgb values for a polygon. + +The long answer, including a bit of explanation is: + +OpenFlight databases can define color values in RGB space (packed +color as you called it) or color index space. The fltHdrRgbMode +field of the fltHeader record specifies which color space is used +by the database. + +If the database is in color index mode, you can get the RGB +colors applied to a polygon by first getting the fltPolyPrimeColor +and fltPolyPrimeIntensity attributes of the polygon and then +converting those values to RGB by calling mgRGB2Index. + +Note: The attributes fltPolyAltColor and fltPolyAltIntensity can +be used to get the alternate color index and intensity. + +If the database is in RGB mode, you can get the RGB colors applied +to a polygon by calling the function mgGetPolyColorRGB. But if you +take a closer look at this function you will discover that it +returns the RGB colors for a polygon regardless of whether the +database is in color index or RGB mode. +If the database is in color index mode, mgGetPolyColorRGB acquires +the color index applied to the polygon and looks up the +corresponding RGB values for you. + +So, if you are only after the RGB color values applied to a +polygon, the function mgGetPolyColorRGB is always your best bet. +Note: mgGetPolyAltColorRGB is the equivalent function to use to +get the alternate RGB color values applied to a polygon. + +Hope this helps. +*/ + + //////////////////////////////////////////////////////////////////// // @@ -18,10 +74,8 @@ using namespace flt; RegisterRecordProxy g_HeaderProxy; - HeaderRecord::HeaderRecord() { -// _pNode = NULL; } @@ -33,48 +87,44 @@ HeaderRecord::~HeaderRecord() void HeaderRecord::endian() { - SHeader *pHeader = (SHeader*)getData(); + SHeader *pHeader = (SHeader*)getData(); -// VALID_RECORD(SHeader, pRecHdr) - ENDIAN( pHeader->diFormatRevLev ); - ENDIAN( pHeader->diDatabaseRevLev ); - ENDIAN( pHeader->iNextGroup ); - ENDIAN( pHeader->iNextLOD ); - ENDIAN( pHeader->iNextObject ); - ENDIAN( pHeader->iNextPolygon ); - ENDIAN( pHeader->iMultDivUnit ); - ENDIAN( pHeader->diFlags ); - ENDIAN( pHeader->diProjection ); - ENDIAN( pHeader->iNextDegOfFreedom ); - ENDIAN( pHeader->iVertexStorage ); - ENDIAN( pHeader->diDatabaseSource ); - ENDIAN( pHeader->dfSWDatabaseCoordX ); - ENDIAN( pHeader->dfSWDatabaseCoordY ); - ENDIAN( pHeader->dfDatabaseOffsetX ); - ENDIAN( pHeader->dfDatabaseOffsetY ); - ENDIAN( pHeader->iNextSound ); - ENDIAN( pHeader->iNextPath ); - ENDIAN( pHeader->iNextClippingRegion ); - ENDIAN( pHeader->iNextText ); - ENDIAN( pHeader->iNextBSP ); - ENDIAN( pHeader->iNextSwitch ); - pHeader->SWCorner.endian(); - pHeader->NECorner.endian(); - pHeader->Origin.endian(); - ENDIAN( pHeader->dfLambertUpperLat ); - ENDIAN( pHeader->dfLambertLowerLat ); - ENDIAN( pHeader->iNextLightSource ); + ENDIAN( pHeader->diFormatRevLev ); + ENDIAN( pHeader->diDatabaseRevLev ); + ENDIAN( pHeader->iNextGroup ); + ENDIAN( pHeader->iNextLOD ); + ENDIAN( pHeader->iNextObject ); + ENDIAN( pHeader->iNextPolygon ); + ENDIAN( pHeader->iMultDivUnit ); + ENDIAN( pHeader->dwFlags ); + ENDIAN( pHeader->diProjection ); + ENDIAN( pHeader->iNextDegOfFreedom ); + ENDIAN( pHeader->iVertexStorage ); + ENDIAN( pHeader->diDatabaseSource ); + ENDIAN( pHeader->dfSWDatabaseCoordX ); + ENDIAN( pHeader->dfSWDatabaseCoordY ); + ENDIAN( pHeader->dfDatabaseOffsetX ); + ENDIAN( pHeader->dfDatabaseOffsetY ); + ENDIAN( pHeader->iNextSound ); + ENDIAN( pHeader->iNextPath ); + ENDIAN( pHeader->iNextClippingRegion ); + ENDIAN( pHeader->iNextText ); + ENDIAN( pHeader->iNextBSP ); + ENDIAN( pHeader->iNextSwitch ); + pHeader->SWCorner.endian(); + pHeader->NECorner.endian(); + pHeader->Origin.endian(); + ENDIAN( pHeader->dfLambertUpperLat ); + ENDIAN( pHeader->dfLambertLowerLat ); + ENDIAN( pHeader->iNextLightSource ); } // virtual void HeaderRecord::decode() { -// SHeader *pHeader = (SHeader*)getData(); + SHeader *pHeader = (SHeader*)getData(); - // Add node to scene graph -// _pNode = new osg::Node; -// _pNode->setName(pHeader->szIdent); } @@ -84,114 +134,3 @@ bool HeaderRecord::readLocalData(Input& fr) return PrimNodeRecord::readLocalData(fr); } - -// virtual -int HeaderRecord::decodeAncillary(int op) -{ -/* - switch (op) - { - case COLOUR_TABLE_OP: - G_TRACE0( "\tCOLOUR_TABLE_R\n" ); - break; - - case MATERIAL_PALETTE_OP: - { - fltMaterialPalette rec( _pFltFile ); - rec.readRecordBody(); - rec.decodeRecord(); - } - break; - - case LIGHT_SOURCE_PALETTE_R: - G_TRACE0( "\tLIGHT_SOURCE_PALETTE_R\n" ); - break; - - case VERTEX_PALETTE_R: - { - fltVertexPalette rec( _pFltFile ); - rec.readRecordBody(); - rec.decodeRecord(); - } - break; - - case VERTEX_COORD_R: - { - fltVertex rec( _pFltFile ); - rec.readRecordBody(); - rec.decodeRecord(); - } - break; - - case VERTEX_NORMAL_COORD_R: - { - fltNormalVertex rec( _pFltFile ); - rec.readRecordBody(); - rec.decodeRecord(); - } - break; - - case VERTEX_NORMAL_UV_COORD_R: - { - fltNormalTextureVertex rec( _pFltFile ); - rec.readRecordBody(); - rec.decodeRecord(); - } - break; - - case VERTEX_UV_COORD_R: - { - fltTextureVertex rec( _pFltFile ); - rec.readRecordBody(); - rec.decodeRecord(); - } - break; - - default: - return FALSE; - } // end-switch -*/ - return true; -} - - -// virtual -int HeaderRecord::decodeLevel( int op ) -{ -/* - switch (op) - { - case GROUP_OP: - { - fltGroup rec( _pFltFile, (csGroup*)_pContainer ); - rec.readRecordBody(); - rec.decodeRecord(); - } - break; - default: - return FALSE; - } -*/ - return true; -} - -/* -void HeaderRecord::write() -{ - SHeader *pHeader = (SHeader*)getData(); - - G_TRACE0("Header\n"); - G_TRACE1("\tFormatRevisionLevel %ld\n", pHeader->diFormatRevLev); - G_TRACE1("\tDatabaseRevisionLevel %ld\n", pHeader->diDatabaseRevLev); - G_TRACE1("\tDateAndTimeOfLastRev. %s\n", pHeader->szDaTimLastRev); - G_TRACE1("\tProjection %ld\n", pHeader->diProjection); - G_TRACE1("\tDatabase Source %ld\n", pHeader->diDatabaseSource); - G_TRACE1("\tSWCorner,Lat %lf\n", pHeader->SWCorner.dfLat); - G_TRACE1("\tSWCorner,Lon %lf\n", pHeader->SWCorner.dfLon); - G_TRACE1("\tNECorner,Lat %lf\n", pHeader->NECorner.dfLat); - G_TRACE1("\tNECorner,Lon %lf\n", pHeader->NECorner.dfLon); - G_TRACE1("\tOrigin,Lat %lf\n", pHeader->Origin.dfLat); - G_TRACE1("\tOrigin,Lon %lf\n", pHeader->Origin.dfLon); -} -*/ - diff --git a/src/osgPlugins/flt/HeaderRecord.h b/src/osgPlugins/flt/HeaderRecord.h index 5149730bb..29a8189c4 100644 --- a/src/osgPlugins/flt/HeaderRecord.h +++ b/src/osgPlugins/flt/HeaderRecord.h @@ -3,94 +3,91 @@ #ifndef __FLT_HEADER_RECORD_H #define __FLT_HEADER_RECORD_H - #include "opcodes.h" #include "Record.h" #include "RecordVisitor.h" -//namespace flt { -//class Node; -//}; - - namespace flt { struct SHeader { - SRecHeader RecHeader; - char szIdent[8]; // ID field (Not curr used) - int32 diFormatRevLev; // Format revision level - int32 diDatabaseRevLev; // Edit rev. level - char szDaTimLastRev[32]; // Date and time last rev. - int16 iNextGroup; // Next group ID number - int16 iNextLOD; // Next LOD ID number - int16 iNextObject; // Next object ID number - int16 iNextPolygon; // Next polygon ID number - int16 iMultDivUnit; // Unit multiplier/divisor, always = 1 - uint8 swVertexCoordUnit; // Vertex coordinate units - // 0 = Meters - // 1 = Kilometers - // 4 = Feet - // 5 = Inches - // 8 = Nautical miles - uint8 swTexWhite; // if TRUE set texwhite on new polygons - int32 diFlags; // Flags (bits, from left to right) - // 0 = Save vertex normals - // 1-31 Spare - int32 diNotUsed_1[6]; // Not Used - int32 diProjection; // Projection Type - // 0 = Flat Earth - // 1 = Trapezoidal - // 2 = Round Earth - // 3 = Lambert - // 4 = UTM - // 5 = Geodetic - // 6 = Geocentric - int32 diNotUsed_2[7]; // Not Used - int16 iNextDegOfFreedom; // Next degree of freedom ID number - int16 iVertexStorage; // Vertex Storage Type - // 1 = Double Precision Float - int32 diDatabaseSource; // Database Source - // 100 = OpenFlight - // 200 = DIG I/DIG II - // 300 = Evans and Sutherland CT5A/CT6 - // 400 = PSP DIG - // 600 = General Electric CIV/CV / PT2000 - // 700 = Evans and Sutherland GDF - float64 dfSWDatabaseCoordX; // Southwest Database Coordinate (x,y) - float64 dfSWDatabaseCoordY; - float64 dfDatabaseOffsetX; // Delta (x,y) to Place Database - float64 dfDatabaseOffsetY; - int16 iNextSound; // Next Sound Bead Id - int16 iNextPath; // Next Path Bead ID - int32 diReserved_1[2]; // Reserved for MultiGen - int16 iNextClippingRegion;// Next Clipping Region Bead ID - int16 iNextText; // Next Text Bead ID - int16 iNextBSP; // Next BSP ID - int16 iNextSwitch; // Next Switch Bead ID - int32 diReserved_2; // Reserved - float64x2 SWCorner; // South West Corner Lat/Lon (NB: dec. degrees) - float64x2 NECorner; // North East Corner Lat/Lon (NB: dec. degrees) - float64x2 Origin; // Origin Lat/Lon (NB: dec. degrees, not radians) - float64 dfLambertUpperLat; // Lambert Upper Latitude - float64 dfLambertLowerLat; // Lambert Lower Latitude - int16 iNextLightSource; // Next Light Source ID Number - int16 iReserved_3; // Reserved - int16 iNextRoad; // Next road bead ID number - int16 iNextCat; // Next CAT bead ID number - int16 iReserved_4[4]; // Reserved - int32 diEllipsoid; // Earth ellipsoid model - // 0 - WGS 1984 - // 1 - WGS 1972 - // 2 - Bessel - // 3 - Clarke 1866 - // 4 - NAD 1927 + SRecHeader RecHeader; + char szIdent[8]; // ID field (Not curr used) + int32 diFormatRevLev; // Format revision level + int32 diDatabaseRevLev; // Edit rev. level + char szDaTimLastRev[32]; // Date and time last rev. + int16 iNextGroup; // Next group ID number + int16 iNextLOD; // Next LOD ID number + int16 iNextObject; // Next object ID number + int16 iNextPolygon; // Next polygon ID number + int16 iMultDivUnit; // Unit multiplier/divisor, always = 1 + uint8 swVertexCoordUnit; // Vertex coordinate units + // 0 = Meters + // 1 = Kilometers + // 4 = Feet + // 5 = Inches + // 8 = Nautical miles + uint8 swTexWhite; // if TRUE set texwhite on new polygons + uint32 dwFlags; // Flags (bits, from left to right) + // 0 = Save vertex normals + // 1 = Packed Color mode + // 2 = CAD View mode + // 3-31 = Spare + int32 diNotUsed_1[6]; // Not Used + int32 diProjection; // Projection Type + // 0 = Flat Earth + // 1 = Trapezoidal + // 2 = Round Earth + // 3 = Lambert + // 4 = UTM + // 5 = Geodetic + // 6 = Geocentric + int32 diNotUsed_2[7]; // Not Used + int16 iNextDegOfFreedom; // Next degree of freedom ID number + int16 iVertexStorage; // Vertex Storage Type + // 1 = Double Precision Float + int32 diDatabaseSource; // Database Source + // 100 = OpenFlight + // 200 = DIG I/DIG II + // 300 = Evans and Sutherland CT5A/CT6 + // 400 = PSP DIG + // 600 = General Electric CIV/CV / PT2000 + // 700 = Evans and Sutherland GDF + float64 dfSWDatabaseCoordX; // Southwest Database Coordinate (x,y) + float64 dfSWDatabaseCoordY; + float64 dfDatabaseOffsetX; // Delta (x,y) to Place Database + float64 dfDatabaseOffsetY; + int16 iNextSound; // Next Sound Bead Id + int16 iNextPath; // Next Path Bead ID + int32 diReserved_1[2]; // Reserved for MultiGen + int16 iNextClippingRegion;// Next Clipping Region Bead ID + int16 iNextText; // Next Text Bead ID + int16 iNextBSP; // Next BSP ID + int16 iNextSwitch; // Next Switch Bead ID + int32 diReserved_2; // Reserved + float64x2 SWCorner; // South West Corner Lat/Lon (NB: dec. degrees) + float64x2 NECorner; // North East Corner Lat/Lon (NB: dec. degrees) + float64x2 Origin; // Origin Lat/Lon (NB: dec. degrees, not radians) + float64 dfLambertUpperLat; // Lambert Upper Latitude + float64 dfLambertLowerLat; // Lambert Lower Latitude + int16 iNextLightSource; // Next Light Source ID Number + int16 iReserved_3; // Reserved + int16 iNextRoad; // Next road bead ID number + int16 iNextCat; // Next CAT bead ID number + int16 iReserved_4[4]; // Reserved + int32 diEllipsoid; // Earth ellipsoid model + // 0 - WGS 1984 + // 1 - WGS 1972 + // 2 - Bessel + // 3 - Clarke 1866 + // 4 - NAD 1927 }; class HeaderRecord : public PrimNodeRecord { public: + HeaderRecord(); virtual Record* clone() const { return new HeaderRecord(); } @@ -98,12 +95,12 @@ class HeaderRecord : public PrimNodeRecord virtual int classOpcode() const { return HEADER_OP; } virtual int sizeofData() const { return sizeof(SHeader); } virtual void accept(RecordVisitor& rv) { rv.apply(*this); } -// virtual void traverse(RecordVisitor& rv); SHeader* getData() const { return (SHeader*)_pData; } virtual const std::string getName( void ) const { return std::string(getData()->szIdent); } protected: + virtual ~HeaderRecord(); virtual void endian(); @@ -112,13 +109,6 @@ class HeaderRecord : public PrimNodeRecord virtual bool readLocalData(Input& fr); // virtual bool writeLocalData(Output& fw); - virtual int decodeAncillary(int op); - virtual int decodeLevel(int op); - - private: - // vertex pool -// osg::Node* _pNode; - }; }; // end namespace flt diff --git a/src/osgPlugins/flt/Input.cpp b/src/osgPlugins/flt/Input.cpp index 4cf9aeb68..80c10a71c 100644 --- a/src/osgPlugins/flt/Input.cpp +++ b/src/osgPlugins/flt/Input.cpp @@ -22,9 +22,6 @@ using namespace std; using namespace flt; - - - FileInput::FileInput() { _init(); @@ -63,7 +60,6 @@ bool FileInput::eof() } - bool FileInput::open(const std::string& fileName) { _file=::fopen( fileName.c_str(), "rb"); @@ -99,12 +95,13 @@ bool FileInput::_readHeader(SRecHeader* pHdr) { int nItemsRead; - _lRecOffset = ::ftell( _file ); // Save file position for rewind operation + // Save file position for rewind operation + _lRecOffset = ::ftell( _file ); // Read record header (4 bytes) nItemsRead = _read(pHdr, sizeof(SRecHeader)); if (nItemsRead != 1) - return false; + return false; if (isLittleEndianMachine()) pHdr->endian(); @@ -112,22 +109,22 @@ bool FileInput::_readHeader(SRecHeader* pHdr) if ((unsigned)pHdr->length() < sizeof(SRecHeader)) return false; - return true; + return true; } bool FileInput::_readBody(SRecHeader* pData) { - // Read record body + // Read record body int nBodySize = pData->length() - sizeof(SRecHeader); if (nBodySize > 0) { int nItemsRead = _read(pData+1, nBodySize); - if (nItemsRead != 1) - return false; + if (nItemsRead != 1) + return false; } - return true; + return true; } @@ -139,7 +136,9 @@ SRecHeader* FileInput::readRecord() if (!_readHeader(&hdr)) return NULL; - // Allocate buffer for record (including header) + // Allocate buffer for record (including header) + // This buffer is extended later in Record::cloneRecord() + // if defined struct is bigger than read. pData = (SRecHeader*)::malloc(hdr.length()); if (pData == NULL) return NULL; @@ -186,17 +185,15 @@ Record* Input::readCreateRecord() return NULL; } -#if 0 - osg::notify(osg::INFO) << "class=" << pRec->className(); - osg::notify(osg::INFO) << " op=" << pRec->getOpcode(); - osg::notify(osg::INFO) << " name=" << pRec->getName(); - osg::notify(osg::INFO) << " offset=" << offset() << endl; -#endif + #if 0 + osg::notify(osg::ALWAYS) << "class=" << pRec->className(); + osg::notify(osg::ALWAYS) << " op=" << pRec->getOpcode(); + osg::notify(osg::ALWAYS) << " name=" << pRec->getName(); + osg::notify(osg::ALWAYS) << " offset=" << offset() << endl; + #endif - if (isLittleEndianMachine()) // From Intel with love :-( + if (isLittleEndianMachine()) // From Intel with love :-( pRec->endian(); return pRec; } - - diff --git a/src/osgPlugins/flt/InstanceRecords.cpp b/src/osgPlugins/flt/InstanceRecords.cpp index 7b2b6f121..527f60a63 100644 --- a/src/osgPlugins/flt/InstanceRecords.cpp +++ b/src/osgPlugins/flt/InstanceRecords.cpp @@ -1,6 +1,5 @@ // InstanceRecords.cpp - #include "flt.h" #include "Registry.h" #include "InstanceRecords.h" @@ -15,7 +14,6 @@ using namespace flt; RegisterRecordProxy g_InstanceDefinitionProxy; - InstanceDefinitionRecord::InstanceDefinitionRecord() { } @@ -32,8 +30,6 @@ void InstanceDefinitionRecord::endian() } - - //////////////////////////////////////////////////////////////////// // // InstanceReferenceRecord @@ -42,7 +38,6 @@ void InstanceDefinitionRecord::endian() RegisterRecordProxy g_InstanceReferenceProxy; - InstanceReferenceRecord::InstanceReferenceRecord() { } @@ -57,6 +52,3 @@ InstanceReferenceRecord::~InstanceReferenceRecord() void InstanceReferenceRecord::endian() { } - - - diff --git a/src/osgPlugins/flt/InstanceRecords.h b/src/osgPlugins/flt/InstanceRecords.h index 668d6bb24..2837cfcbf 100644 --- a/src/osgPlugins/flt/InstanceRecords.h +++ b/src/osgPlugins/flt/InstanceRecords.h @@ -21,7 +21,7 @@ namespace flt { typedef struct InstanceDefinitionTag { - SRecHeader RecHeader; + SRecHeader RecHeader; }SInstanceDefinition; @@ -54,7 +54,7 @@ class InstanceDefinitionRecord : public PrimNodeRecord typedef struct InstanceReferenceTag { - SRecHeader RecHeader; + SRecHeader RecHeader; }SInstanceReference; diff --git a/src/osgPlugins/flt/LightPointRecord.cpp b/src/osgPlugins/flt/LightPointRecord.cpp index b5aadeee6..59b0aa57e 100644 --- a/src/osgPlugins/flt/LightPointRecord.cpp +++ b/src/osgPlugins/flt/LightPointRecord.cpp @@ -1,6 +1,5 @@ // LightPointRecord.cpp - #include "flt.h" #include "Registry.h" #include "LightPointRecord.h" @@ -15,7 +14,6 @@ using namespace flt; RegisterRecordProxy g_LightPointProxy; - LightPointRecord::LightPointRecord() { } @@ -29,7 +27,7 @@ LightPointRecord::~LightPointRecord() void LightPointRecord::endian() { - SLightPoint *pSLightPoint = (SLightPoint*)getData(); + SLightPoint *pSLightPoint = (SLightPoint*)getData(); ENDIAN( pSLightPoint->iMaterial ); ENDIAN( pSLightPoint->iFeature ); @@ -66,8 +64,3 @@ void LightPointRecord::endian() ENDIAN( pSLightPoint->sfFlags ); pSLightPoint->animRot.endian(); } - - - - - diff --git a/src/osgPlugins/flt/LightPointRecord.h b/src/osgPlugins/flt/LightPointRecord.h index 2063c6a59..9b7636f51 100644 --- a/src/osgPlugins/flt/LightPointRecord.h +++ b/src/osgPlugins/flt/LightPointRecord.h @@ -13,7 +13,7 @@ namespace flt { struct SLightPoint { - SRecHeader RecHeader; + SRecHeader RecHeader; char szIdent[8]; // 7 char ASCII ID; 0 terminates int16 iMaterial; // Surface material code (for DFAD) int16 iFeature; // Feature ID (for DFAD) diff --git a/src/osgPlugins/flt/LightSourcePaletteRecord.cpp b/src/osgPlugins/flt/LightSourcePaletteRecord.cpp index f83635705..d67479a5f 100644 --- a/src/osgPlugins/flt/LightSourcePaletteRecord.cpp +++ b/src/osgPlugins/flt/LightSourcePaletteRecord.cpp @@ -6,17 +6,14 @@ using namespace flt; - //////////////////////////////////////////////////////////////////// // // LightSourcePaletteRecord // //////////////////////////////////////////////////////////////////// - RegisterRecordProxy g_LightSourcePaletteProxy; - LightSourcePaletteRecord::LightSourcePaletteRecord() { } @@ -32,7 +29,3 @@ LightSourcePaletteRecord::~LightSourcePaletteRecord() void LightSourcePaletteRecord::endian() { } - - - - diff --git a/src/osgPlugins/flt/LightSourcePaletteRecord.h b/src/osgPlugins/flt/LightSourcePaletteRecord.h index 8848f0824..f6bce5f86 100644 --- a/src/osgPlugins/flt/LightSourcePaletteRecord.h +++ b/src/osgPlugins/flt/LightSourcePaletteRecord.h @@ -14,27 +14,27 @@ namespace flt { typedef struct LightSourcePaletteTag { - SRecHeader RecHeader; - int32 diIndex; // Palette index - int32 diReserved_1[2]; - char szName[20]; // Light source name - int32 diReserved_2; - float32 sfAmbientRGBA[4]; // Alpha comp. currently unused - float32 sfDiffuseRGBA[4]; // Alpha comp. currently unused - float32 sfSpecularRGBA[4]; // Alpha comp. currently unused - int32 diLightType; // 0 = INFINITE - // 1 = LOCAL - // 2 = SPOT - int32 diReserved_3[10]; - float32 sfDropoff; // Spot exponential dropoff term - float32 sfCutoff; // Spot cutoff angle (radians) - float32 sfYaw; - float32 sfPitch; - float32 sfConstantAttuenation; - float32 sfLinearAttuenation; - float32 sfQuadraticAttuenation; - int32 diModelingLight; // TRUE/FALSE - int32 diSpare[19]; + SRecHeader RecHeader; + int32 diIndex; // Palette index + int32 diReserved_1[2]; + char szName[20]; // Light source name + int32 diReserved_2; + float32 sfAmbientRGBA[4]; // Alpha comp. currently unused + float32 sfDiffuseRGBA[4]; // Alpha comp. currently unused + float32 sfSpecularRGBA[4]; // Alpha comp. currently unused + int32 diLightType; // 0 = INFINITE + // 1 = LOCAL + // 2 = SPOT + int32 diReserved_3[10]; + float32 sfDropoff; // Spot exponential dropoff term + float32 sfCutoff; // Spot cutoff angle (radians) + float32 sfYaw; + float32 sfPitch; + float32 sfConstantAttuenation; + float32 sfLinearAttuenation; + float32 sfQuadraticAttuenation; + int32 diModelingLight; // TRUE/FALSE + int32 diSpare[19]; } SLightSourcePalette; diff --git a/src/osgPlugins/flt/LightSourceRecord.cpp b/src/osgPlugins/flt/LightSourceRecord.cpp index 03b438419..b3f745fc0 100644 --- a/src/osgPlugins/flt/LightSourceRecord.cpp +++ b/src/osgPlugins/flt/LightSourceRecord.cpp @@ -4,7 +4,6 @@ #include "Registry.h" #include "LightSourceRecord.h" - using namespace flt; //////////////////////////////////////////////////////////////////// @@ -15,7 +14,6 @@ using namespace flt; RegisterRecordProxy g_LightSourceRecordProxy; - LightSourceRecord::LightSourceRecord() { } @@ -30,18 +28,14 @@ LightSourceRecord::~LightSourceRecord() // virtual void LightSourceRecord::endian() { - SLightSource *pSLightSource = (SLightSource*)getData(); + SLightSource *pSLightSource = (SLightSource*)getData(); - ENDIAN( pSLightSource->diReserved_1 ); - ENDIAN( pSLightSource->diIndex ); - ENDIAN( pSLightSource->diReserved_2 ); - ENDIAN( pSLightSource->dwFlags ); - ENDIAN( pSLightSource->diReserved_3 ); - pSLightSource->Coord.endian(); - ENDIAN( pSLightSource->sfYaw ); - ENDIAN( pSLightSource->sfPitch ); + ENDIAN( pSLightSource->diReserved_1 ); + ENDIAN( pSLightSource->diIndex ); + ENDIAN( pSLightSource->diReserved_2 ); + ENDIAN( pSLightSource->dwFlags ); + ENDIAN( pSLightSource->diReserved_3 ); + pSLightSource->Coord.endian(); + ENDIAN( pSLightSource->sfYaw ); + ENDIAN( pSLightSource->sfPitch ); } - - - - diff --git a/src/osgPlugins/flt/LightSourceRecord.h b/src/osgPlugins/flt/LightSourceRecord.h index 8ca0c8e57..38292d5cb 100644 --- a/src/osgPlugins/flt/LightSourceRecord.h +++ b/src/osgPlugins/flt/LightSourceRecord.h @@ -22,22 +22,22 @@ namespace flt { typedef struct LightSourceTag { - SRecHeader RecHeader; - char szIdent[8]; // 7 char ASCII ID; 0 terminates - int32 diReserved_1; - int32 diIndex; //index into lightpalette - int32 diReserved_2; - uint32 dwFlags; //bits from left to right - //0=enabled - //1=global - //2=reserve - //3=export - //4=reserved - //5-31 spare - int32 diReserved_3; - float64x3 Coord; // x,y,z coordinate - float32 sfYaw; - float32 sfPitch; + SRecHeader RecHeader; + char szIdent[8]; // 7 char ASCII ID; 0 terminates + int32 diReserved_1; + int32 diIndex; //index into lightpalette + int32 diReserved_2; + uint32 dwFlags; //bits from left to right + //0=enabled + //1=global + //2=reserve + //3=export + //4=reserved + //5-31 spare + int32 diReserved_3; + float64x3 Coord; // x,y,z coordinate + float32 sfYaw; + float32 sfPitch; } SLightSource; diff --git a/src/osgPlugins/flt/LodRecord.cpp b/src/osgPlugins/flt/LodRecord.cpp index 7c7f78407..8869e3d58 100644 --- a/src/osgPlugins/flt/LodRecord.cpp +++ b/src/osgPlugins/flt/LodRecord.cpp @@ -14,7 +14,6 @@ using namespace flt; RegisterRecordProxy g_LodProxy; - LodRecord::LodRecord() { } @@ -28,19 +27,18 @@ LodRecord::~LodRecord() void LodRecord::endian() { - SLevelOfDetail *pSLod = (SLevelOfDetail*)getData(); + SLevelOfDetail *pSLod = (SLevelOfDetail*)getData(); - ENDIAN( pSLod->dfSwitchInDist ); - ENDIAN( pSLod->dfSwitchOutDist ); - ENDIAN( pSLod->iSpecialId_1 ); - ENDIAN( pSLod->iSpecialId_2 ); - ENDIAN( pSLod->diFlags ); - pSLod->Center.endian(); - ENDIAN( pSLod->dfTransitionRange ); + ENDIAN( pSLod->dfSwitchInDist ); + ENDIAN( pSLod->dfSwitchOutDist ); + ENDIAN( pSLod->iSpecialId_1 ); + ENDIAN( pSLod->iSpecialId_2 ); + ENDIAN( pSLod->diFlags ); + pSLod->Center.endian(); + ENDIAN( pSLod->dfTransitionRange ); } - //////////////////////////////////////////////////////////////////// // // OldLodRecord @@ -49,7 +47,6 @@ void LodRecord::endian() RegisterRecordProxy g_OldLodProxy; - OldLodRecord::OldLodRecord() { } @@ -63,16 +60,14 @@ OldLodRecord::~OldLodRecord() void OldLodRecord::endian() { - SOldLOD *pSLod = (SOldLOD*)getData(); + SOldLOD *pSLod = (SOldLOD*)getData(); - ENDIAN( pSLod->dfSwitchInDist ); - ENDIAN( pSLod->dfSwitchOutDist ); - ENDIAN( pSLod->iSpecialId_1 ); - ENDIAN( pSLod->iSpecialId_2 ); - ENDIAN( pSLod->diFlags ); - pSLod->Center.endian(); - ENDIAN( pSLod->dfTransitionRange ); + ENDIAN( pSLod->dwSwitchInDist ); + ENDIAN( pSLod->dwSwitchOutDist ); + ENDIAN( pSLod->iSpecialId_1 ); + ENDIAN( pSLod->iSpecialId_2 ); + ENDIAN( pSLod->diFlags ); + ENDIAN( pSLod->Center[0] ); + ENDIAN( pSLod->Center[1] ); + ENDIAN( pSLod->Center[2] ); } - - - diff --git a/src/osgPlugins/flt/LodRecord.h b/src/osgPlugins/flt/LodRecord.h index 69c11032f..e28480362 100644 --- a/src/osgPlugins/flt/LodRecord.h +++ b/src/osgPlugins/flt/LodRecord.h @@ -17,23 +17,23 @@ namespace flt { // //////////////////////////////////////////////////////////////////// -typedef struct LevelOfDetailTag +struct SLevelOfDetail { - SRecHeader RecHeader; - char szIdent[8]; // 7 char ASCII ID; 0 terminates - int32 iSpare; // Spare - float64 dfSwitchInDist; // Switch in distance - float64 dfSwitchOutDist;// Switch out distance - int16 iSpecialId_1; // Special effects ID 1 - defined by real time - int16 iSpecialId_2; // Special effects ID 2 - defined by real time - int32 diFlags; // Flags (bits, from left to right) - // 0 = Use previous slant range - // 1 = SPT flag: 0 if replacement LOD, 1 for additive LOD - // 2 = Freeze center (don't recalculate) - // 3-31 Spare - float64x3 Center; // Center coordinate (x,y,z) of LOD block - float64 dfTransitionRange; // Transition Range for Morphing -} SLevelOfDetail; + SRecHeader RecHeader; + char szIdent[8]; // 7 char ASCII ID; 0 terminates + int32 iSpare; // Spare + float64 dfSwitchInDist; // Switch in distance + float64 dfSwitchOutDist;// Switch out distance + int16 iSpecialId_1; // Special effects ID 1 - defined by real time + int16 iSpecialId_2; // Special effects ID 2 - defined by real time + int32 diFlags; // Flags (bits, from left to right) + // 0 = Use previous slant range + // 1 = SPT flag: 0 if replacement LOD, 1 for additive LOD + // 2 = Freeze center (don't recalculate) + // 3-31 Spare + float64x3 Center; // Center coordinate (x,y,z) of LOD block + float64 dfTransitionRange; // Transition Range for Morphing +}; @@ -67,23 +67,22 @@ class LodRecord : public PrimNodeRecord //////////////////////////////////////////////////////////////////// -typedef struct OldLodTag +struct SOldLOD { - SRecHeader RecHeader; - char szIdent[8]; // 7 char ASCII ID; 0 terminates - int32 iSpare; // Spare - float64 dfSwitchInDist; // Switch in distance - float64 dfSwitchOutDist;// Switch out distance - int16 iSpecialId_1; // Special effects ID 1 - defined by real time - int16 iSpecialId_2; // Special effects ID 2 - defined by real time - int32 diFlags; // Flags (bits, from left to right) - // 0 = Use previous slant range - // 1 = SPT flag: 0 if replacement LOD, 1 for additive LOD - // 2 = Freeze center (don't recalculate) - // 3-31 Spare - float64x3 Center; // Center coordinate (x,y,z) of LOD block - float64 dfTransitionRange; // Transition Range for Morphing -} SOldLOD; + SRecHeader RecHeader; + char szIdent[8]; // 7 char ASCII ID; 0 terminates + uint32 dwSwitchInDist; // Switch in distance + uint32 dwSwitchOutDist; // Switch out distance + int16 iSpecialId_1; // Special effects ID 1 - defined by real time + int16 iSpecialId_2; // Special effects ID 2 - defined by real time + int32 diFlags; // Flags (bits, from left to right) + // 0 = Use previous slant range + // 1 = SPT flag: 0 if replacement LOD, 1 for additive LOD + // 2 = Freeze center (don't recalculate) + // 3-31 Spare + int32 Center[3]; // Center coordinate (x,y,z) of LOD block +// int32 spare[14]; +}; diff --git a/src/osgPlugins/flt/LongIDRecord.cpp b/src/osgPlugins/flt/LongIDRecord.cpp index da9679666..2ae8ec4b3 100644 --- a/src/osgPlugins/flt/LongIDRecord.cpp +++ b/src/osgPlugins/flt/LongIDRecord.cpp @@ -6,17 +6,14 @@ using namespace flt; - //////////////////////////////////////////////////////////////////// // // MaterialPaletteRecord // //////////////////////////////////////////////////////////////////// - RegisterRecordProxy g_LongIDProxy; - LongIDRecord::LongIDRecord() { } @@ -33,5 +30,3 @@ void LongIDRecord::endian() { } - - diff --git a/src/osgPlugins/flt/LongIDRecord.h b/src/osgPlugins/flt/LongIDRecord.h index ce27f606e..197a592c4 100644 --- a/src/osgPlugins/flt/LongIDRecord.h +++ b/src/osgPlugins/flt/LongIDRecord.h @@ -14,7 +14,7 @@ namespace flt { struct SLongID { - SRecHeader RecHeader; + SRecHeader RecHeader; char szIdent[1]; // (Length - 4) ASCII ID of node }; diff --git a/src/osgPlugins/flt/Makefile b/src/osgPlugins/flt/Makefile index 0f8f08f72..b888072dd 100644 --- a/src/osgPlugins/flt/Makefile +++ b/src/osgPlugins/flt/Makefile @@ -10,6 +10,7 @@ C++FILES = \ ObjectRecord.cpp\ ControlRecord.cpp\ OldVertexRecords.cpp\ + OldMaterialPaletteRecord.cpp\ DofRecord.cpp\ ExtensionRecord.cpp\ ExternalRecord.cpp\ diff --git a/src/osgPlugins/flt/MaterialPaletteRecord.cpp b/src/osgPlugins/flt/MaterialPaletteRecord.cpp index c69551fd3..9b0d58d3b 100644 --- a/src/osgPlugins/flt/MaterialPaletteRecord.cpp +++ b/src/osgPlugins/flt/MaterialPaletteRecord.cpp @@ -6,17 +6,14 @@ using namespace flt; - //////////////////////////////////////////////////////////////////// // // MaterialPaletteRecord // //////////////////////////////////////////////////////////////////// - RegisterRecordProxy g_MaterialPaletteProxy; - MaterialPaletteRecord::MaterialPaletteRecord() { } @@ -31,7 +28,7 @@ MaterialPaletteRecord::~MaterialPaletteRecord() // virtual void MaterialPaletteRecord::endian() { - SMaterial *pSMaterial = (SMaterial*)getData(); + SMaterial *pSMaterial = (SMaterial*)getData(); ENDIAN( pSMaterial->diIndex ); ENDIAN( pSMaterial->diFlags ); @@ -42,8 +39,3 @@ void MaterialPaletteRecord::endian() ENDIAN( pSMaterial->sfShininess ); ENDIAN( pSMaterial->sfAlpha ); } - - - - - diff --git a/src/osgPlugins/flt/MaterialPaletteRecord.h b/src/osgPlugins/flt/MaterialPaletteRecord.h index 1005a9693..91ac7155a 100644 --- a/src/osgPlugins/flt/MaterialPaletteRecord.h +++ b/src/osgPlugins/flt/MaterialPaletteRecord.h @@ -14,18 +14,18 @@ namespace flt { struct SMaterial { - SRecHeader RecHeader; + SRecHeader RecHeader; int32 diIndex; char szName[12]; uint32 diFlags; // bit 0 Materials used // bit 1-31 Spare - float32x3 Ambient; // Ambient component of material - float32x3 Diffuse; // Diffuse component of material - float32x3 Specular; // Specular component of material - float32x3 Emissive; // Emissive component of material - float32 sfShininess; // Shininess. [0.0-128.0] - float32 sfAlpha; // Alpha. [0.0-1.0], where 1.0 is opaque - int32 diSpare; + float32x3 Ambient; // Ambient component of material + float32x3 Diffuse; // Diffuse component of material + float32x3 Specular; // Specular component of material + float32x3 Emissive; // Emissive component of material + float32 sfShininess; // Shininess. [0.0-128.0] + float32 sfAlpha; // Alpha. [0.0-1.0], where 1.0 is opaque + int32 diSpare; }; diff --git a/src/osgPlugins/flt/ObjectRecord.cpp b/src/osgPlugins/flt/ObjectRecord.cpp index 8b3348346..ad55fc3f6 100644 --- a/src/osgPlugins/flt/ObjectRecord.cpp +++ b/src/osgPlugins/flt/ObjectRecord.cpp @@ -14,7 +14,6 @@ using namespace flt; RegisterRecordProxy g_ObjectProxy; - ObjectRecord::ObjectRecord() { } @@ -28,7 +27,7 @@ ObjectRecord::~ObjectRecord() void ObjectRecord::endian() { - SObject *pSObject = (SObject*)getData(); + SObject *pSObject = (SObject*)getData(); ENDIAN( pSObject->dwFlags ); ENDIAN( pSObject->iObjectRelPriority ); @@ -37,6 +36,3 @@ void ObjectRecord::endian() ENDIAN( pSObject->iSpecialId_2 ); ENDIAN( pSObject->iSignificance ); } - - - diff --git a/src/osgPlugins/flt/ObjectRecord.h b/src/osgPlugins/flt/ObjectRecord.h index 14c0399e5..8c8f58c78 100644 --- a/src/osgPlugins/flt/ObjectRecord.h +++ b/src/osgPlugins/flt/ObjectRecord.h @@ -14,24 +14,24 @@ namespace flt { typedef struct ObjectTag { - SRecHeader RecHeader; - char szIdent[8]; // 7 char ASCII ID; 0 terminates - uint32 dwFlags; // Flags (bits from to right) - // 0 = Don't display in daylight - // 1 = Don't display at dusk - // 2 = Don't display at night - // 3 = Don't illuminate - // 4 = Flat shaded - // 5 = Group's shadow object - // 6-31 Spare - int16 iObjectRelPriority; // Object relative priority - uint16 wTransparency; // Transparency factor - // = 0 opaque - // = 65535 for totally clear - int16 iSpecialId_1; // Special effects ID 1 - defined by real time - int16 iSpecialId_2; // Special effects ID 2 - defined by real time - int16 iSignificance; // Significance - int16 iSpare; // Spare + SRecHeader RecHeader; + char szIdent[8]; // 7 char ASCII ID; 0 terminates + uint32 dwFlags; // Flags (bits from to right) + // 0 = Don't display in daylight + // 1 = Don't display at dusk + // 2 = Don't display at night + // 3 = Don't illuminate + // 4 = Flat shaded + // 5 = Group's shadow object + // 6-31 Spare + int16 iObjectRelPriority; // Object relative priority + uint16 wTransparency; // Transparency factor + // = 0 opaque + // = 65535 for totally clear + int16 iSpecialId_1; // Special effects ID 1 - defined by real time + int16 iSpecialId_2; // Special effects ID 2 - defined by real time + int16 iSignificance; // Significance + int16 iSpare; // Spare } SObject; diff --git a/src/osgPlugins/flt/OldVertexRecords.cpp b/src/osgPlugins/flt/OldVertexRecords.cpp index 2477549c2..b8f968497 100644 --- a/src/osgPlugins/flt/OldVertexRecords.cpp +++ b/src/osgPlugins/flt/OldVertexRecords.cpp @@ -4,11 +4,8 @@ #include "Registry.h" #include "OldVertexRecords.h" - using namespace flt; - - //////////////////////////////////////////////////////////////////// // // OldVertexRecord @@ -17,7 +14,6 @@ using namespace flt; RegisterRecordProxy g_OldVertexProxy; - OldVertexRecord::OldVertexRecord() { } @@ -28,28 +24,35 @@ OldVertexRecord::~OldVertexRecord() { } + // virtual void OldVertexRecord::endian() { - SOldVertex *pVertex = (SOldVertex*)getData(); + SOldVertex *pVertex = (SOldVertex*)getData(); ENDIAN( pVertex->v[0] ); ENDIAN( pVertex->v[1] ); ENDIAN( pVertex->v[2] ); + if (getSize() >= sizeofData()) + pVertex->t.endian(); } +// virtual +bool OldVertexRecord::readLocalData(Input& fr) +{ + return true; +} /* ostream& operator << (ostream& output, const OldVertexRecord& rec) { - output << rec.className() << " " + output << rec.className() << " " << rec.getData()->swFlags << " " << rec.getData()->Coord; - return output; // to enable cascading + return output; // to enable cascading } */ - //////////////////////////////////////////////////////////////////// // // OldVertexColorRecord @@ -58,7 +61,6 @@ ostream& operator << (ostream& output, const OldVertexRecord& rec) RegisterRecordProxy g_OldVertexColorProxy; - OldVertexColorRecord::OldVertexColorRecord() { } @@ -69,24 +71,35 @@ OldVertexColorRecord::~OldVertexColorRecord() { } + // virtual void OldVertexColorRecord::endian() { - SOldVertexColor *pVertex = (SOldVertexColor*)getData(); + SOldVertexColor *pVertex = (SOldVertexColor*)getData(); ENDIAN( pVertex->v[0] ); ENDIAN( pVertex->v[1] ); ENDIAN( pVertex->v[2] ); + ENDIAN( pVertex->color_index ); + if (getSize() >= sizeofData()) + pVertex->t.endian(); +} + + +// virtual +bool OldVertexColorRecord::readLocalData(Input& fr) +{ + return true; } /* ostream& operator << (ostream& output, const OldVertexColorRecord& rec) { - output << rec.className() << " " + output << rec.className() << " " << rec.getData()->swFlags << " " << rec.getData()->Coord; - return output; // to enable cascading + return output; // to enable cascading } */ @@ -98,7 +111,6 @@ ostream& operator << (ostream& output, const OldVertexColorRecord& rec) RegisterRecordProxy g_OldVertexColorNormalProxy; - OldVertexColorNormalRecord::OldVertexColorNormalRecord() { } @@ -113,26 +125,33 @@ OldVertexColorNormalRecord::~OldVertexColorNormalRecord() // virtual void OldVertexColorNormalRecord::endian() { - SOldVertexColorNormal *pVertex = (SOldVertexColorNormal*)getData(); + SOldVertexColorNormal *pVertex = (SOldVertexColorNormal*)getData(); - ENDIAN( pVertex->Coord[0] ); - ENDIAN( pVertex->Coord[1] ); - ENDIAN( pVertex->Coord[2] ); - ENDIAN( pVertex->swColor ); - ENDIAN( pVertex->swFlags ); -// ENDIAN( pVertex->Normal[0] ); -// ENDIAN( pVertex->Normal[1] ); -// ENDIAN( pVertex->Normal[2] ); + ENDIAN( pVertex->v[0] ); + ENDIAN( pVertex->v[1] ); + ENDIAN( pVertex->v[2] ); + ENDIAN( pVertex->color_index ); + ENDIAN( pVertex->n[0] ); + ENDIAN( pVertex->n[1] ); + ENDIAN( pVertex->n[2] ); + if (getSize() >= sizeofData()) + pVertex->t.endian(); } + +// virtual +bool OldVertexColorNormalRecord::readLocalData(Input& fr) +{ + return true; +} + + /* ostream& operator << (ostream& output, const OldVertexColorNormalRecord& rec) { - output << rec.className() << " " + output << rec.className() << " " << rec.getData()->swFlags << " " << rec.getData()->Coord; - return output; // to enable cascading + return output; // to enable cascading } */ - - diff --git a/src/osgPlugins/flt/OldVertexRecords.h b/src/osgPlugins/flt/OldVertexRecords.h index 6c37f5e66..e67297c11 100644 --- a/src/osgPlugins/flt/OldVertexRecords.h +++ b/src/osgPlugins/flt/OldVertexRecords.h @@ -3,12 +3,12 @@ #ifndef __FLT_OLD_VERTEX_RECORDS_H #define __FLT_OLD_VERTEX_RECORDS_H -#include - #include "opcodes.h" #include "Record.h" #include "RecordVisitor.h" +#include + #ifdef OSG_USE_IO_DOT_H #include #else @@ -26,11 +26,13 @@ namespace flt { // //////////////////////////////////////////////////////////////////// -typedef struct OldVertexTag +struct SOldVertex { - SRecHeader RecHeader; + SRecHeader RecHeader; int32 v[3]; -} SOldVertex; + float32x2 t; // optional texture u,v + // check record size. +}; class OldVertexRecord : public PrimNodeRecord @@ -44,12 +46,14 @@ class OldVertexRecord : public PrimNodeRecord virtual void accept(RecordVisitor& rv) { rv.apply(*this); } // virtual void traverse(RecordVisitor& rv); virtual SOldVertex* getData() const { return (SOldVertex*)_pData; } -// friend ostream& operator << (ostream& output, const OldVertexRecord& rec); +// friend ostream& operator << (ostream& output, const OldVertexRecord& rec); protected: virtual ~OldVertexRecord(); virtual void endian(); + virtual bool readLocalData(Input& fr); +// virtual bool writeLocalData(Output& fw); }; @@ -60,20 +64,16 @@ class OldVertexRecord : public PrimNodeRecord //////////////////////////////////////////////////////////////////// -typedef struct OldVertexColorTag +struct SOldVertexColor { - SRecHeader RecHeader; + SRecHeader RecHeader; int32 v[3]; -/* - float64_t x; - float64_t y; - float64_t z; - uint16_t color_name_index; - uint16_t flags; - uint32_t packed_color; - uint32_t color_index; -*/ -} SOldVertexColor; + uint8 edge_flag; // Hard edge flag + uint8 shading_flag; // Don’t touch normal when shading flag. + uint16 color_index; // Vertex color. + float32x2 t; // optional texture u,v + // check record size. +}; class OldVertexColorRecord : public PrimNodeRecord @@ -87,12 +87,14 @@ class OldVertexColorRecord : public PrimNodeRecord virtual void accept(RecordVisitor& rv) { rv.apply(*this); } // virtual void traverse(RecordVisitor& rv); virtual SOldVertexColor* getData() const { return (SOldVertexColor*)_pData; } -// friend ostream& operator << (ostream& output, const OldVertexColorRecord& rec); +// friend ostream& operator << (ostream& output, const OldVertexColorRecord& rec); protected: virtual ~OldVertexColorRecord(); virtual void endian(); + virtual bool readLocalData(Input& fr); +// virtual bool writeLocalData(Output& fw); }; @@ -102,14 +104,17 @@ class OldVertexColorRecord : public PrimNodeRecord // //////////////////////////////////////////////////////////////////// -typedef struct OldVertexColorNormalTag +struct SOldVertexColorNormal { - SRecHeader RecHeader; - int32 Coord[3]; - uint16 swColor; // Color Name Index - uint16 swFlags; // Flags (bits, from left to right) - int16 Normal[3]; -} SOldVertexColorNormal; + SRecHeader RecHeader; + int32 v[3]; + uint8 edge_flag; // Hard edge flag + uint8 shading_flag; // Don’t touch normal when shading flag. + uint16 color_index; // Vertex color. + int32 n[3]; // Normal scaled 2**30 + float32x2 t; // optional texture u,v + // check record size. +}; class OldVertexColorNormalRecord : public PrimNodeRecord @@ -123,12 +128,14 @@ class OldVertexColorNormalRecord : public PrimNodeRecord virtual void accept(RecordVisitor& rv) { rv.apply(*this); } // virtual void traverse(RecordVisitor& rv); virtual SOldVertexColorNormal* getData() const { return (SOldVertexColorNormal*)_pData; } -// friend ostream& operator << (ostream& output, const OldVertexColorNormalRecord& rec); +// friend ostream& operator << (ostream& output, const OldVertexColorNormalRecord& rec); protected: virtual ~OldVertexColorNormalRecord(); virtual void endian(); + virtual bool readLocalData(Input& fr); +// virtual bool writeLocalData(Output& fw); }; diff --git a/src/osgPlugins/flt/Pool.cpp b/src/osgPlugins/flt/Pool.cpp index 56ac16970..b64170656 100644 --- a/src/osgPlugins/flt/Pool.cpp +++ b/src/osgPlugins/flt/Pool.cpp @@ -1,8 +1,14 @@ // Pool.cpp +#ifdef WIN32 + #pragma warning( disable : 4786 ) +#endif + #include #include +#include "MaterialPaletteRecord.h" +#include "OldMaterialPaletteRecord.h" #include "Pool.h" using namespace flt; @@ -25,8 +31,8 @@ osg::Vec4 ColorPool::getColor(int nColorIndex) if (nColorIndex >= 0) { - int index = nColorIndex / 128; - float intensity = (nColorIndex % 128) / 128.0f; + int index = nColorIndex / 128; // = nColorIndex >> 7 + float intensity = (nColorIndex % 128) / 128.0f; // = nColorIndex & 0x7f ColorName* cn = getColorName(index); if (cn) @@ -41,7 +47,7 @@ osg::Vec4 ColorPool::getColor(int nColorIndex) } -void ColorPool::regisiterColor(int nIndex, const osg::Vec4& color) +void ColorPool::addColor(int nIndex, const osg::Vec4& color) { if (nIndex >= 0) { @@ -73,13 +79,12 @@ void ColorPool::eraseAll() if (colorname) delete colorname; } - _colorNameMap.erase(_colorNameMap.begin(), _colorNameMap.end()); + _colorNameMap.clear(); } //////////////////////////////////////////////////////////////////// - TexturePool::TexturePool() { } @@ -102,7 +107,7 @@ osg::Texture* TexturePool::getTexture(int nIndex) } -void TexturePool::regisiterTexture(int nIndex, osg::Texture* osgTexture) +void TexturePool::addTexture(int nIndex, osg::Texture* osgTexture) { _textureMap[nIndex] = osgTexture; } @@ -110,7 +115,7 @@ void TexturePool::regisiterTexture(int nIndex, osg::Texture* osgTexture) void TexturePool::eraseAll() { - _textureMap.erase(_textureMap.begin(), _textureMap.end()); + _textureMap.clear(); } @@ -128,8 +133,9 @@ MaterialPool::~MaterialPool() } -SMaterial* MaterialPool::getMaterial(int nIndex) +PoolMaterial* MaterialPool::getMaterial(int nIndex) { + if (nIndex < 0) return NULL; MaterialMap::iterator fitr = _MaterialMap.find(nIndex); if (fitr != _MaterialMap.end()) return (*fitr).second; @@ -138,7 +144,7 @@ SMaterial* MaterialPool::getMaterial(int nIndex) } -void MaterialPool::regisiterMaterial(int nIndex, SMaterial* material) +void MaterialPool::addMaterial(int nIndex, PoolMaterial* material) { _MaterialMap[nIndex] = material; } @@ -146,5 +152,13 @@ void MaterialPool::regisiterMaterial(int nIndex, SMaterial* material) void MaterialPool::eraseAll() { - _MaterialMap.erase(_MaterialMap.begin(), _MaterialMap.end()); + for(MaterialMap::iterator itr=_MaterialMap.begin(); + itr!=_MaterialMap.end(); + ++itr) + { + PoolMaterial* material = (*itr).second; + if (material) + delete material; + } + _MaterialMap.clear(); } diff --git a/src/osgPlugins/flt/Pool.h b/src/osgPlugins/flt/Pool.h index 95e74d0c9..cc819b0c5 100644 --- a/src/osgPlugins/flt/Pool.h +++ b/src/osgPlugins/flt/Pool.h @@ -3,18 +3,19 @@ #ifndef __FLT_POOL_H #define __FLT_POOL_H +#include "flt.h" + +#include +#include + #include #include #include //#include -#include -#include - namespace flt { -struct SMaterial; class ColorPool { @@ -24,7 +25,7 @@ public: virtual ~ColorPool(); osg::Vec4 getColor(int nColorIndex); - void regisiterColor(int nIndex, const osg::Vec4& color); + void addColor(int nIndex, const osg::Vec4& color); private: @@ -57,7 +58,7 @@ public: virtual ~TexturePool(); osg::Texture* getTexture(int nIndex); - void regisiterTexture(int nIndex, osg::Texture* osgTexture); + void addTexture(int nIndex, osg::Texture* osgTexture); private: @@ -68,6 +69,19 @@ private: }; +struct PoolMaterial +{ + float32x3 Ambient; // Ambient component of material + float32x3 Diffuse; // Diffuse component of material + float32x3 Specular; // Specular component of material + float32x3 Emissive; // Emissive component of material + float32 sfShininess; // Shininess. [0.0-128.0] + float32 sfAlpha; // Alpha. [0.0-1.0], where 1.0 is opaque +}; + +struct SMaterial; +struct SOldMaterial; + class MaterialPool { public: @@ -75,14 +89,14 @@ public: MaterialPool(); virtual ~MaterialPool(); - SMaterial* getMaterial(int nIndex); - void regisiterMaterial(int nIndex, SMaterial* material); + PoolMaterial* getMaterial(int nIndex); + void addMaterial(int nIndex, PoolMaterial* material); private: void eraseAll(); - typedef std::map MaterialMap; + typedef std::map MaterialMap; MaterialMap _MaterialMap; }; diff --git a/src/osgPlugins/flt/ReaderWriterFLT.cpp b/src/osgPlugins/flt/ReaderWriterFLT.cpp index 7f82c0b0b..24f522aba 100644 --- a/src/osgPlugins/flt/ReaderWriterFLT.cpp +++ b/src/osgPlugins/flt/ReaderWriterFLT.cpp @@ -7,14 +7,13 @@ #include "ReaderWriterFLT.h" #include "FltFile.h" -#include #include #include +#include using namespace flt; - osg::Object* ReaderWriterFLT::readObject(const std::string& fileName) { FltFile read; @@ -33,9 +32,4 @@ osg::Node* ReaderWriterFLT::readNode(const std::string& fileName) // now register with Registry to instantiate the above // reader/writer. -osg::RegisterReaderWriterProxy g_fltReaderWriterProxy; - - - - - +osgDB::RegisterReaderWriterProxy g_fltReaderWriterProxy; diff --git a/src/osgPlugins/flt/ReaderWriterFLT.h b/src/osgPlugins/flt/ReaderWriterFLT.h index 755b641a6..8d86644e3 100644 --- a/src/osgPlugins/flt/ReaderWriterFLT.h +++ b/src/osgPlugins/flt/ReaderWriterFLT.h @@ -34,25 +34,25 @@ #include -#include #include #include -#include "export.h" +#include +#include namespace flt { -class FLT_EXPORT ReaderWriterFLT : public osg::ReaderWriter +class ReaderWriterFLT : public osgDB::ReaderWriter { public: virtual const char* className() { return "FLT Reader/Writer"; } - virtual bool acceptsExtension(const std::string& extension) { return extension=="flt"; } - - virtual bool writeObject(osg::Object& obj,const std::string& fileName) { return false; } - virtual bool writeNode(osg::Node& node,const std::string& fileName) { return false; } + virtual bool acceptsExtension(const std::string& extension) + { + return osgDB::equalCaseInsensitive(extension,"flt"); + } virtual osg::Object* readObject(const std::string& fileName); virtual osg::Node* readNode(const std::string& fileName); diff --git a/src/osgPlugins/flt/Record.cpp b/src/osgPlugins/flt/Record.cpp index 80673ef1d..69cd49de9 100644 --- a/src/osgPlugins/flt/Record.cpp +++ b/src/osgPlugins/flt/Record.cpp @@ -6,7 +6,6 @@ #include -#include "export.h" #include "flt.h" #include "Registry.h" #include "Record.h" @@ -23,18 +22,14 @@ using namespace std; #endif - using namespace flt; - //////////////////////////////////////////////////////////////////// // // Record // //////////////////////////////////////////////////////////////////// - - Record::Record() { _pData = NULL; @@ -47,6 +42,7 @@ Record::~Record() if (_pData) ::free(_pData); } + Record* Record::cloneRecord(SRecHeader* pData) { Record* pRec = clone(); @@ -55,7 +51,7 @@ Record* Record::cloneRecord(SRecHeader* pData) pData = (SRecHeader*)::realloc(pData, pRec->sizeofData()); pRec->_pData = (SRecHeader*)pData; - + return pRec; } @@ -65,6 +61,7 @@ void Record::accept(RecordVisitor& rv) rv.apply(*this); } + /* void Record::ascend(RecordVisitor& rv) { @@ -72,13 +69,12 @@ void Record::ascend(RecordVisitor& rv) } */ - ostream& operator << (ostream& output, const Record& rec) { - output << rec.className() - << " op=" << rec.getOpcode() - << " size=" << rec.getSize(); - return output; // to enable cascading + output << rec.className() + << " op=" << rec.getOpcode() + << " size=" << rec.getSize(); + return output; // to enable cascading } @@ -110,9 +106,9 @@ void PrimNodeRecord::accept(RecordVisitor& rv) // virtual void PrimNodeRecord::traverse(RecordVisitor& rv) { - for(ChildList::iterator itr=_children.begin(); - itr!=_children.end(); - ++itr) + for (ChildList::iterator itr=_children.begin(); + itr!=_children.end(); + ++itr) { (*itr)->accept(rv); } @@ -126,16 +122,9 @@ void PrimNodeRecord::addChild( Record *child ) ChildList::iterator itr = std::find(_children.begin(),_children.end(),child); if (itr==_children.end()) { - - // add child to group. + // note ref_ptr<> automatically handles incrementing child's reference count. _children.push_back(child); - - // register as parent of child. -#if 0 -// child->_parents.push_back(this); -#else child->_pParent = this; -#endif } } @@ -147,72 +136,68 @@ void PrimNodeRecord::removeChild( Record *child ) ChildList::iterator itr = std::find(_children.begin(),_children.end(),child); if (itr!=_children.end()) { + // note ref_ptr<> automatically handles decrementing child's reference count. _children.erase(itr); - -// ParentList::iterator pitr = std::find(child->_parents.begin(),child->_parents.end(),child); -// if (pitr!=child->_parents.end()) child->_parents.erase(pitr); } } void PrimNodeRecord::removeAllChildren() { - _children.erase(_children.begin(),_children.end()); + _children.clear(); } -bool PrimNodeRecord::readExtensions(Input& fr) +bool PrimNodeRecord::readExtensionLevel(Input& fr) { Record* pRec; - while ((pRec=readNextRecord(fr))) + while (pRec=fr.readCreateRecord()) { - if (pRec->isOfType(POP_EXTENSION_OP)) return true; + if (pRec->isOfType(POP_EXTENSION_OP)) + return true; // ignore extensions for now } return false; } +// Read from PUSH to POP bool PrimNodeRecord::readLevel(Input& fr) { Record* pRec; - while ((pRec=readNextRecord(fr))) + pRec = readRecord(fr); + + while (pRec && !pRec->isOfType(POP_LEVEL_OP)) { - if (pRec->isOfType(POP_LEVEL_OP)) return true; if (!pRec->isPrimaryNode()) { - osg::notify(osg::WARN) << "Non primary record found as child. op="; - osg::notify(osg::WARN) << pRec->getOpcode() << endl; + osg::notify(osg::WARN) << "Non primary record found as child. op=" + << pRec->getOpcode() << endl; return false; } + addChild(pRec); if (!((PrimNodeRecord*)pRec)->readLocalData(fr)) return false; + + pRec = readRecord(fr); } - return false; + + return true; } - -Record* PrimNodeRecord::readNextRecord(Input& fr) +// Read next record, including extension record +Record* PrimNodeRecord::readRecord(Input& fr) { - Record* pRec; - - while ((pRec=fr.readCreateRecord())) + Record* pRec = fr.readCreateRecord(); + + while (pRec && (pRec->getOpcode() == PUSH_EXTENSION_OP)) { - switch (pRec->getOpcode()) - { - case PUSH_EXTENSION_OP: - readExtensions(fr); - break; - case PUSH_LEVEL_OP: - readLevel(fr); - break; - default: - return pRec; - } + readExtensionLevel(fr); + pRec=fr.readCreateRecord(); } return pRec; } @@ -223,90 +208,31 @@ bool PrimNodeRecord::readLocalData(Input& fr) { Record* pRec; - while ((pRec=readNextRecord(fr))) - { -// if (pRec->isOfType(PUSH_LEVEL_OP)) -// return true; - if (!pRec->isAncillaryRecord()) - return fr.rewindLast(); + pRec = readRecord(fr); + // Get ancillary records (if any) + while (pRec && pRec->isAncillaryRecord()) + { addChild(pRec); - } - return false; -} - - -/* -// virtual -bool PrimNodeRecord::readLocalData(Input& fr) -{ - Record* pRec; - int until_op = 0; - - // - // read ancillary records - // - - while (pRec=fr.readCreateRecord()) - { - // read extension records - if (pRec->isOfType(PUSH_EXTENSION_OP)) - { - while (pRec=fr.readCreateRecord()) - { - if (pRec->isOfType(POP_EXTENSION_OP)) - { - pRec=fr.readCreateRecord(); - break; - } - }; - } - - - - - if (!pRec->isAncillaryRecord()) - break; - - addChild(pRec); - }; -// if (pRec == NULL) return false; - - if (pRec == NULL) return false; - - - if (pRec->getOpcode() != PUSH_LEVEL_OP) - { -// if (pRec->isPrimaryNode()) - return fr.rewindLast(); - -// osg::notify(osg::INFO) << "Missing PUSH_LEVEL_OP" << endl; -// return false; - } - - // - // read primary node records - // - - while (pRec=fr.readCreateRecord()) - { - if (pRec->getOpcode() == POP_LEVEL_OP) return true; - - if (pRec->isPrimaryNode()) - { - addChild(pRec); - - if (!((PrimNodeRecord*)pRec)->readLocalData(fr)) - return false; - } + pRec = readRecord(fr); } if (pRec == NULL) return false; + // The next record should be PUSH or primary + switch (pRec->getOpcode()) + { + case PUSH_LEVEL_OP: + readLevel(fr); + break; + + default: + fr.rewindLast(); + } + return true; } -*/ //////////////////////////////////////////////////////////////////// @@ -315,13 +241,13 @@ bool PrimNodeRecord::readLocalData(Input& fr) // //////////////////////////////////////////////////////////////////// - // virtual void ControlRecord::accept(RecordVisitor& rv) { rv.apply(*this); } + //////////////////////////////////////////////////////////////////// // // AncillaryRecord @@ -333,6 +259,3 @@ void AncillaryRecord::accept(RecordVisitor& rv) { rv.apply(*this); } - - - diff --git a/src/osgPlugins/flt/Record.h b/src/osgPlugins/flt/Record.h index 32a9e0631..47103d027 100644 --- a/src/osgPlugins/flt/Record.h +++ b/src/osgPlugins/flt/Record.h @@ -5,6 +5,7 @@ #include #include +#include #include "FltRecords.h" @@ -65,7 +66,7 @@ class Record : public osg::Referenced bool isOfType(int op) const; Record* getParent() const { return _pParent; } - friend ostream& operator << (ostream& output, const Record& rec); + friend ostream& operator << (ostream& output, const Record& rec); protected: @@ -168,9 +169,9 @@ class PrimNodeRecord : public Record virtual bool readLocalData(Input& fr); private: - bool readExtensions(Input& fr); + bool readExtensionLevel(Input& fr); bool readLevel(Input& fr); - Record* readNextRecord(Input& fr); + Record* readRecord(Input& fr); typedef std::vector > ChildList; ChildList _children; diff --git a/src/osgPlugins/flt/RecordVisitor.cpp b/src/osgPlugins/flt/RecordVisitor.cpp index 9c74547ca..16f5e28e4 100644 --- a/src/osgPlugins/flt/RecordVisitor.cpp +++ b/src/osgPlugins/flt/RecordVisitor.cpp @@ -11,11 +11,13 @@ RecordVisitor::RecordVisitor(TraversalMode tm) _traverseMode = tm; } + RecordVisitor::~RecordVisitor() { // if (_traverseVisitor) detach from _traverseVisitor; } + void RecordVisitor::setTraverseMode(TraversalMode mode) { if (_traverseMode==mode) return; @@ -31,6 +33,7 @@ void RecordVisitor::setTraverseMode(TraversalMode mode) } } + void RecordVisitor::setTraverseVisitor(RecordVisitor* rv) { if (_traverseVisitor==rv) return; diff --git a/src/osgPlugins/flt/RecordVisitor.h b/src/osgPlugins/flt/RecordVisitor.h index 00e27e229..27975cff2 100644 --- a/src/osgPlugins/flt/RecordVisitor.h +++ b/src/osgPlugins/flt/RecordVisitor.h @@ -38,6 +38,9 @@ class ExternalRecord; class CommentRecord; class LongIDRecord; class VectorRecord; +class OldVertexRecord; +class OldVertexColorRecord; +class OldVertexColorNormalRecord; // Transformation records (ancillary) class MatrixRecord; @@ -129,15 +132,20 @@ class RecordVisitor virtual void apply(CommentRecord& rec) { apply((Record&)rec); } virtual void apply(LongIDRecord& rec) { apply((Record&)rec); } virtual void apply(VectorRecord& rec) { apply((Record&)rec); } + virtual void apply(OldVertexRecord& rec) { apply((Record&)rec); } + virtual void apply(OldVertexColorRecord& rec) { apply((Record&)rec); } + virtual void apply(OldVertexColorNormalRecord& rec) { apply((Record&)rec); } // Transformation records (ancillary) virtual void apply(MatrixRecord& rec) { apply((Record&)rec); } +/* virtual void apply(RotatAboutEdgeRecord& rec) { apply((Record&)rec); } virtual void apply(TranslateRecord& rec) { apply((Record&)rec); } virtual void apply(ScaleRecord& rec) { apply((Record&)rec); } virtual void apply(RotatAboutPointRecord& rec) { apply((Record&)rec); } virtual void apply(RotatScaleToPointRecord& rec) { apply((Record&)rec); } virtual void apply(PutTransformRecord& rec) { apply((Record&)rec); } +*/ virtual void apply(GeneralMatrixRecord& rec) { apply((Record&)rec); } protected: diff --git a/src/osgPlugins/flt/Registry.cpp b/src/osgPlugins/flt/Registry.cpp index 9e907332f..1a20d9ad3 100644 --- a/src/osgPlugins/flt/Registry.cpp +++ b/src/osgPlugins/flt/Registry.cpp @@ -1,7 +1,7 @@ -#include "osg/Node" -#include "osg/Group" -#include "osg/Output" +#include +#include +//#include #include #include @@ -9,6 +9,7 @@ #include "Record.h" #include "Input.h" +#include "FltFile.h" #include "Registry.h" #ifdef OSG_USE_IO_DOT_H @@ -20,7 +21,6 @@ using namespace std; #include - using namespace flt; // definition of the Registry @@ -32,7 +32,7 @@ Registry::Registry() Registry::~Registry() { - + osg::notify(osg::INFO) << "Destructing flt flt::Registry"<< endl; // note, do not need to unrefence records as the combination of @@ -96,7 +96,6 @@ Registry::RecordProtoList::iterator Registry::getRecordProtoItr(const int opcode } - Record* Registry::getRecordProto(const int opcode) { RecordProtoList::iterator itr = getRecordProtoItr(opcode); @@ -106,3 +105,73 @@ Record* Registry::getRecordProto(const int opcode) return itr->get(); } +/////////////////////////////////////////////////////////////////// + + +void Registry::addTexture(osg::Texture* texture) +{ + if (texture==0L) return; + + osg::notify(osg::INFO) << "flt::Registry::addTexture("<< texture->className()<<")\n"; + + TextureList::iterator pitr = std::find(_textureList.begin(),_textureList.end(),texture); + if (pitr==_textureList.end()) + _textureList.push_back(texture); + else + osg::notify(osg::INFO) << "failed - flt::Registry::addTexture() - texture already exists"<<")\n"; +} + + +void Registry::removeTexture(osg::Texture* texture) +{ + if (texture==0L) return; + + osg::notify(osg::INFO) << "flt::Registry::removeTexture("<< texture->className()<<")\n"; + + TextureList::iterator itr = std::find(_textureList.begin(),_textureList.end(),texture); + if (itr!=_textureList.end()) + { + _textureList.erase(itr); + } +} + + +Registry::TextureList::iterator Registry::getTextureItr(const std::string name) +{ + for(TextureList::iterator itr=_textureList.begin(); + itr!=_textureList.end(); + ++itr) + { + osg::Image* image = (*itr)->getImage(); + if (image && name == image->getFileName()) + return itr; + } + + return _textureList.end(); +} + + +osg::Texture* Registry::getTexture(const std::string name) +{ + TextureList::iterator itr = getTextureItr(name); + if (itr==_textureList.end()) + return NULL; + + return *itr; +} + + +FltFile* Registry::getFltFile(const std::string& name) +{ + FltFileMap::iterator itr = _fltFileMap.find(name); + if (itr != _fltFileMap.end()) + return (*itr).second.get(); + else + return NULL; +} + +void Registry::addFltFile(const std::string& name, FltFile* file) +{ + _fltFileMap[name] = file; +} + diff --git a/src/osgPlugins/flt/Registry.h b/src/osgPlugins/flt/Registry.h index 0f8f2d1ed..31ae56e4c 100644 --- a/src/osgPlugins/flt/Registry.h +++ b/src/osgPlugins/flt/Registry.h @@ -1,22 +1,26 @@ #ifndef __FLT_REGISTRY_H #define __FLT_REGISTRY_H +#ifdef WIN32 +#pragma warning( disable : 4786 ) +#endif + +#include +#include +#include + +#include "FltFile.h" + +#include #include #include -#include "osg/Referenced" - -namespace osg { -class Node; -}; - namespace flt { // forward declare referenced classes to help avoid mutiple includes class Record; class Input; - /** Registry is a singleton factory which stores the Objects types available at runtime for loading, @@ -42,15 +46,20 @@ class Registry void addPrototype(Record* rec); void removePrototype(Record* rec); - Record* getRecordProto(const int opcode); -// bool apply(Record& rec); -// Record* readRecord(Input& fr); -// osg::Node* readNode(Input& fr); + + void addTexture(osg::Texture* texture); + void removeTexture(osg::Texture* texture); + osg::Texture* getTexture(const std::string name); + + void addFltFile(const std::string& name, FltFile* file); + FltFile* getFltFile(const std::string& name); private: typedef std::vector > RecordProtoList; + typedef std::vector TextureList; + typedef std::map > FltFileMap; /** constructor is private, as its a singleton, preventing construction other than via the instance() method and @@ -58,8 +67,11 @@ class Registry Registry(); RecordProtoList::iterator getRecordProtoItr(const int opcode); + TextureList::iterator getTextureItr(const std::string name); - RecordProtoList _recordProtoList; + RecordProtoList _recordProtoList; + TextureList _textureList; + FltFileMap _fltFileMap; }; diff --git a/src/osgPlugins/flt/SwitchRecord.cpp b/src/osgPlugins/flt/SwitchRecord.cpp index ba61207d6..a44d50ff2 100644 --- a/src/osgPlugins/flt/SwitchRecord.cpp +++ b/src/osgPlugins/flt/SwitchRecord.cpp @@ -1,6 +1,5 @@ // SwitchRecord.cpp - #include "flt.h" #include "Registry.h" #include "SwitchRecord.h" @@ -15,7 +14,6 @@ using namespace flt; RegisterRecordProxy g_SwitchProxy; - SwitchRecord::SwitchRecord() { } @@ -35,8 +33,3 @@ void SwitchRecord::endian() ENDIAN( pSSwitch->diWordsInMask ); ENDIAN( pSSwitch->diMasks ); } - - - - - diff --git a/src/osgPlugins/flt/SwitchRecord.h b/src/osgPlugins/flt/SwitchRecord.h index d5763455a..fb1ed5248 100644 --- a/src/osgPlugins/flt/SwitchRecord.h +++ b/src/osgPlugins/flt/SwitchRecord.h @@ -13,10 +13,10 @@ namespace flt { struct SSwitch { - SRecHeader RecHeader; - char szIdent[8]; // // 7 char ASCII ID; 0 terminates - uint8 reserved[4]; // Reserved - uint32 dwCurrentMask; // Current mask + SRecHeader RecHeader; + char szIdent[8]; // // 7 char ASCII ID; 0 terminates + uint8 reserved[4]; // Reserved + uint32 dwCurrentMask; // Current mask int32 diWordsInMask; // Number of 32 bit words required for each mask // (number of children / 32 + number of children modulo 32) int32 diMasks; // Number of masks diff --git a/src/osgPlugins/flt/TextureMappingPaletteRecord.cpp b/src/osgPlugins/flt/TextureMappingPaletteRecord.cpp index 011b86beb..01ec09910 100644 --- a/src/osgPlugins/flt/TextureMappingPaletteRecord.cpp +++ b/src/osgPlugins/flt/TextureMappingPaletteRecord.cpp @@ -6,17 +6,14 @@ using namespace flt; - //////////////////////////////////////////////////////////////////// // // TextureMappingPaletteRecord // //////////////////////////////////////////////////////////////////// - RegisterRecordProxy g_TextureMappingPaletteProxy; - TextureMappingPaletteRecord::TextureMappingPaletteRecord() { } @@ -31,7 +28,7 @@ TextureMappingPaletteRecord::~TextureMappingPaletteRecord() // virtual void TextureMappingPaletteRecord::endian() { - STextureMapping *pSMapping = (STextureMapping*)getData(); + STextureMapping *pSMapping = (STextureMapping*)getData(); if (pSMapping) { @@ -48,8 +45,3 @@ void TextureMappingPaletteRecord::endian() } } } - - - - - diff --git a/src/osgPlugins/flt/TextureMappingPaletteRecord.h b/src/osgPlugins/flt/TextureMappingPaletteRecord.h index 22e6e80cf..0103d87f8 100644 --- a/src/osgPlugins/flt/TextureMappingPaletteRecord.h +++ b/src/osgPlugins/flt/TextureMappingPaletteRecord.h @@ -14,7 +14,7 @@ namespace flt { struct STextureMapping { - SRecHeader RecHeader; + SRecHeader RecHeader; float32 reserved; // Reserved int32 diIndex; // Texture mapping index char szName[20]; // Texture mapping name diff --git a/src/osgPlugins/flt/TexturePaletteRecord.cpp b/src/osgPlugins/flt/TexturePaletteRecord.cpp index 7bb46d15f..174476d12 100644 --- a/src/osgPlugins/flt/TexturePaletteRecord.cpp +++ b/src/osgPlugins/flt/TexturePaletteRecord.cpp @@ -6,17 +6,14 @@ using namespace flt; - //////////////////////////////////////////////////////////////////// // // TexturePaletteRecord // //////////////////////////////////////////////////////////////////// - RegisterRecordProxy g_TexturePaletteProxy; - TexturePaletteRecord::TexturePaletteRecord() { } @@ -31,14 +28,9 @@ TexturePaletteRecord::~TexturePaletteRecord() // virtual void TexturePaletteRecord::endian() { - STexturePalette *pSTexture = (STexturePalette*)getData(); + STexturePalette *pSTexture = (STexturePalette*)getData(); ENDIAN( pSTexture->diIndex ); ENDIAN( pSTexture->diX ); ENDIAN( pSTexture->diY ); } - - - - - diff --git a/src/osgPlugins/flt/TexturePaletteRecord.h b/src/osgPlugins/flt/TexturePaletteRecord.h index 65f373ebd..bd1756e1d 100644 --- a/src/osgPlugins/flt/TexturePaletteRecord.h +++ b/src/osgPlugins/flt/TexturePaletteRecord.h @@ -14,11 +14,11 @@ namespace flt { typedef struct TexturePaletteTag { - SRecHeader RecHeader; - char szFilename[200]; // Filename of texture pattern - int32 diIndex; // Pattern index - int32 diX; // x location in texture palette - int32 diY; // y location in texture palette + SRecHeader RecHeader; + char szFilename[200]; // Filename of texture pattern + int32 diIndex; // Pattern index + int32 diX; // x location in texture palette + int32 diY; // y location in texture palette } STexturePalette; diff --git a/src/osgPlugins/flt/TransformationRecords.cpp b/src/osgPlugins/flt/TransformationRecords.cpp index 1fc58cdc6..388073540 100644 --- a/src/osgPlugins/flt/TransformationRecords.cpp +++ b/src/osgPlugins/flt/TransformationRecords.cpp @@ -1,13 +1,11 @@ // TransformationRecords.cpp - #include "flt.h" #include "Registry.h" #include "TransformationRecords.h" using namespace flt; - //////////////////////////////////////////////////////////////////// // // MatrixRecord @@ -16,7 +14,6 @@ using namespace flt; RegisterRecordProxy g_MatrixProxy; - MatrixRecord::MatrixRecord() { } @@ -45,7 +42,7 @@ void MatrixRecord::endian() } } - +#if 0 //////////////////////////////////////////////////////////////////// // // RotatAboutEdgeRecord @@ -54,7 +51,6 @@ void MatrixRecord::endian() RegisterRecordProxy g_RotatAboutEdgeProxy; - RotatAboutEdgeRecord::RotatAboutEdgeRecord() { } @@ -80,7 +76,6 @@ void RotatAboutEdgeRecord::endian() RegisterRecordProxy g_TranslateProxy; - TranslateRecord::TranslateRecord() { } @@ -106,7 +101,6 @@ void TranslateRecord::endian() RegisterRecordProxy g_ScaleProxy; - ScaleRecord::ScaleRecord() { } @@ -132,7 +126,6 @@ void ScaleRecord::endian() RegisterRecordProxy g_RotatAboutPointProxy; - RotatAboutPointRecord::RotatAboutPointRecord() { } @@ -144,7 +137,6 @@ RotatAboutPointRecord::~RotatAboutPointRecord() } - // virtual void RotatAboutPointRecord::endian() { @@ -159,7 +151,6 @@ void RotatAboutPointRecord::endian() RegisterRecordProxy g_RotatScaleToPointProxy; - RotatScaleToPointRecord::RotatScaleToPointRecord() { } @@ -185,7 +176,6 @@ void RotatScaleToPointRecord::endian() RegisterRecordProxy g_PutTransformProxy; - PutTransformRecord::PutTransformRecord() { } @@ -197,21 +187,20 @@ PutTransformRecord::~PutTransformRecord() } - // virtual void PutTransformRecord::endian() { - SPutTransform *pSPutTransform = (SPutTransform*)getData(); + SPutTransform *pSPutTransform = (SPutTransform*)getData(); - ENDIAN( pSPutTransform->tmp1 ); - pSPutTransform->FromOrigin.endian(); - pSPutTransform->FromAlign.endian(); - pSPutTransform->FromTrack.endian(); - pSPutTransform->ToOrigin.endian(); - pSPutTransform->ToAlign.endian(); - pSPutTransform->ToTrack.endian(); + ENDIAN( pSPutTransform->tmp1 ); + pSPutTransform->FromOrigin.endian(); + pSPutTransform->FromAlign.endian(); + pSPutTransform->FromTrack.endian(); + pSPutTransform->ToOrigin.endian(); + pSPutTransform->ToAlign.endian(); + pSPutTransform->ToTrack.endian(); } - +#endif //////////////////////////////////////////////////////////////////// // @@ -221,7 +210,6 @@ void PutTransformRecord::endian() RegisterRecordProxy g_GeneralMatrixProxy; - GeneralMatrixRecord::GeneralMatrixRecord() { } @@ -233,7 +221,6 @@ GeneralMatrixRecord::~GeneralMatrixRecord() } - // virtual void GeneralMatrixRecord::endian() { @@ -250,4 +237,3 @@ void GeneralMatrixRecord::endian() } } } - diff --git a/src/osgPlugins/flt/TransformationRecords.h b/src/osgPlugins/flt/TransformationRecords.h index 2436ca9a6..904d102ed 100644 --- a/src/osgPlugins/flt/TransformationRecords.h +++ b/src/osgPlugins/flt/TransformationRecords.h @@ -21,8 +21,8 @@ namespace flt { typedef struct MatrixTag { - SRecHeader RecHeader; - float32 sfMat[4][4]; // 4x4 Single Precision Matrix + SRecHeader RecHeader; + float32 sfMat[4][4]; // 4x4 Single Precision Matrix } SMatrix; // row major order @@ -46,7 +46,7 @@ class MatrixRecord : public AncillaryRecord virtual void endian(); }; - +#if 0 //////////////////////////////////////////////////////////////////// // // RotatAboutEdgeRecord @@ -55,7 +55,7 @@ class MatrixRecord : public AncillaryRecord typedef struct RotatAboutEdgeTag { - SRecHeader RecHeader; + SRecHeader RecHeader; int32 diReserved; float64x3 Point1; // first point on edge float64x3 Point2; // second point on edge @@ -91,13 +91,13 @@ class RotatAboutEdgeRecord : public AncillaryRecord //////////////////////////////////////////////////////////////////// -typedef struct TranslateTag +struct STranslate { - SRecHeader RecHeader; - int32 diReserved; + SRecHeader RecHeader; + int32 diReserved; float64x3 From; // reference FROM point float64x3 Delta; // Delta to translate node by -} STranslate; +}; class TranslateRecord : public AncillaryRecord @@ -120,6 +120,41 @@ class TranslateRecord : public AncillaryRecord virtual void endian(); }; +//////////////////////////////////////////////////////////////////// +// +// OldTranslateRecord +// +//////////////////////////////////////////////////////////////////// + + +struct SOldTranslate +{ + SRecHeader RecHeader; + int32 diReserved; + float64x3 From; // reference FROM point + float64x3 Delta; // Delta to translate node by +}; + + +class OldTranslateRecord : public AncillaryRecord +{ + public: + OldTranslateRecord(); + + virtual Record* clone() const { return new OldTranslateRecord(); } + virtual const char* className() const { return "OldTranslateRecord"; } + virtual int classOpcode() const { return OLD_TRANSLATE_OP; } + virtual int sizeofData() const { return sizeof(SOldTranslate); } + virtual void accept(RecordVisitor& rv) { rv.apply(*this); } +// virtual void traverse(RecordVisitor& rv); + + virtual SOldTranslate* getData() const { return (SOldTranslate*)_pData; } + + protected: + virtual ~OldTranslateRecord(); + + virtual void endian(); +}; //////////////////////////////////////////////////////////////////// // @@ -127,13 +162,13 @@ class TranslateRecord : public AncillaryRecord // //////////////////////////////////////////////////////////////////// -typedef struct ScaleTag +struct SScale { - SRecHeader RecHeader; + SRecHeader RecHeader; int32 Reserved; float64x3 center; float32x3 scale; -} SScale; +}; class ScaleRecord : public AncillaryRecord { @@ -164,7 +199,7 @@ class ScaleRecord : public AncillaryRecord typedef struct RotatAboutPointTag { - SRecHeader RecHeader; + SRecHeader RecHeader; // TODO } SRotatAboutPoint; @@ -197,7 +232,7 @@ class RotatAboutPointRecord : public AncillaryRecord typedef struct RotatScaleToPointTag { - SRecHeader RecHeader; + SRecHeader RecHeader; // TODO } SRotatScaleToPoint; @@ -228,16 +263,16 @@ class RotatScaleToPointRecord : public AncillaryRecord // //////////////////////////////////////////////////////////////////// -typedef struct PutTransformTag //follows normally a matrix record to -{ //make up the transformation - SRecHeader RecHeader; - int32 tmp1; //mismatch with spec! - float64x3 FromOrigin; - float64x3 FromAlign; - float64x3 FromTrack; - float64x3 ToOrigin; //mismatch !! - float64x3 ToAlign; - float64x3 ToTrack; +typedef struct PutTransformTag //follows normally a matrix record to +{ //make up the transformation + SRecHeader RecHeader; + int32 tmp1; //mismatch with spec! + float64x3 FromOrigin; + float64x3 FromAlign; + float64x3 FromTrack; + float64x3 ToOrigin; //mismatch !! + float64x3 ToAlign; + float64x3 ToTrack; } SPutTransform; @@ -260,7 +295,7 @@ class PutTransformRecord : public AncillaryRecord virtual void endian(); }; - +#endif //////////////////////////////////////////////////////////////////// // @@ -268,11 +303,11 @@ class PutTransformRecord : public AncillaryRecord // //////////////////////////////////////////////////////////////////// -typedef struct GeneralMatrixTag +struct SGeneralMatrix { - SRecHeader RecHeader; - float32 sfMat[4][4]; // 4x4 Single Precision Matrix -} SGeneralMatrix; // row major order + SRecHeader RecHeader; + float32 sfMat[4][4]; // 4x4 Single Precision Matrix +}; // row major order class GeneralMatrixRecord : public AncillaryRecord diff --git a/src/osgPlugins/flt/UnknownRecord.cpp b/src/osgPlugins/flt/UnknownRecord.cpp index 372e7ae70..4ec467f6a 100644 --- a/src/osgPlugins/flt/UnknownRecord.cpp +++ b/src/osgPlugins/flt/UnknownRecord.cpp @@ -6,7 +6,6 @@ using namespace flt; - //////////////////////////////////////////////////////////////////// // // UnknownRecord @@ -15,13 +14,12 @@ using namespace flt; RegisterRecordProxy g_UnknownProxy; - UnknownRecord::UnknownRecord() { } + // virtual UnknownRecord::~UnknownRecord() { } - diff --git a/src/osgPlugins/flt/VertexPoolRecords.cpp b/src/osgPlugins/flt/VertexPoolRecords.cpp index 8e04bb49f..ccb487bbd 100644 --- a/src/osgPlugins/flt/VertexPoolRecords.cpp +++ b/src/osgPlugins/flt/VertexPoolRecords.cpp @@ -4,10 +4,8 @@ #include "Registry.h" #include "VertexPoolRecords.h" - using namespace flt; - //////////////////////////////////////////////////////////////////// // // VertexPaletteRecord @@ -16,7 +14,6 @@ using namespace flt; RegisterRecordProxy g_VertexPaletteProxy; - VertexPaletteRecord::VertexPaletteRecord() { } @@ -28,25 +25,22 @@ VertexPaletteRecord::~VertexPaletteRecord() } - // virtual void VertexPaletteRecord::endian() { - SVertexTableHeader *pVertexTableHeader = (SVertexTableHeader*)getData(); + SVertexTableHeader *pVertexTableHeader = (SVertexTableHeader*)getData(); ENDIAN( pVertexTableHeader->diVertexTableLength ); } - ostream& operator << (ostream& output, const VertexPaletteRecord& rec) { - output << rec.className(); - return output; // to enable cascading + output << rec.className(); + return output; // to enable cascading } - //////////////////////////////////////////////////////////////////// // // VertexRecord @@ -55,7 +49,6 @@ ostream& operator << (ostream& output, const VertexPaletteRecord& rec) RegisterRecordProxy g_VertexProxy; - VertexRecord::VertexRecord() { } @@ -66,28 +59,28 @@ VertexRecord::~VertexRecord() { } + // virtual void VertexRecord::endian() { - SVertex *pVertex = (SVertex*)getData(); + SVertex *pVertex = (SVertex*)getData(); ENDIAN( pVertex->swColor ); - ENDIAN( pVertex->swFlags ); - pVertex->Coord.endian(); - ENDIAN( pVertex->dwVertexColorIndex ); + ENDIAN( pVertex->swFlags ); + pVertex->Coord.endian(); + ENDIAN( pVertex->dwVertexColorIndex ); } ostream& operator << (ostream& output, const VertexRecord& rec) { - output << rec.className() << " " - << rec.getData()->swFlags << " " - << rec.getData()->Coord; - return output; // to enable cascading + output << rec.className() << " " + << rec.getData()->swFlags << " " + << rec.getData()->Coord; + return output; // to enable cascading } - //////////////////////////////////////////////////////////////////// // // NormalVertexRecord @@ -96,7 +89,6 @@ ostream& operator << (ostream& output, const VertexRecord& rec) RegisterRecordProxy g_NormalVertexProxy; - NormalVertexRecord::NormalVertexRecord() { } @@ -107,27 +99,27 @@ NormalVertexRecord::~NormalVertexRecord() { } + // virtual void NormalVertexRecord::endian() { - SNormalVertex *pVertex = (SNormalVertex*)getData(); + SNormalVertex *pVertex = (SNormalVertex*)getData(); ENDIAN( pVertex->swColor ); - ENDIAN( pVertex->swFlags ); - pVertex->Coord.endian(); - pVertex->Normal.endian(); -// ENDIAN( pVertex->PackedColor ); - ENDIAN( pVertex->dwVertexColorIndex ); + ENDIAN( pVertex->swFlags ); + pVertex->Coord.endian(); + pVertex->Normal.endian(); + // ENDIAN( pVertex->PackedColor ); + ENDIAN( pVertex->dwVertexColorIndex ); } - ostream& operator << (ostream& output, const NormalVertexRecord& rec) { - output << rec.className() << " " - << rec.getData()->swFlags << " " - << rec.getData()->Coord; - return output; // to enable cascading + output << rec.className() << " " + << rec.getData()->swFlags << " " + << rec.getData()->Coord; + return output; // to enable cascading } @@ -139,7 +131,6 @@ ostream& operator << (ostream& output, const NormalVertexRecord& rec) RegisterRecordProxy g_TextureVertexProxy; - TextureVertexRecord::TextureVertexRecord() { } @@ -154,27 +145,26 @@ TextureVertexRecord::~TextureVertexRecord() // virtual void TextureVertexRecord::endian() { - STextureVertex *pVertex = (STextureVertex*)getData(); + STextureVertex *pVertex = (STextureVertex*)getData(); ENDIAN( pVertex->swColor ); - ENDIAN( pVertex->swFlags ); - pVertex->Coord.endian(); - pVertex->Texture.endian(); -// ENDIAN( pVertex->PackedColor ); - ENDIAN( pVertex->dwVertexColorIndex ); + ENDIAN( pVertex->swFlags ); + pVertex->Coord.endian(); + pVertex->Texture.endian(); + // ENDIAN( pVertex->PackedColor ); + ENDIAN( pVertex->dwVertexColorIndex ); } ostream& operator << (ostream& output, const TextureVertexRecord& rec) { - output << rec.className() << " " - << rec.getData()->swFlags << " " - << rec.getData()->Coord; - return output; // to enable cascading + output << rec.className() << " " + << rec.getData()->swFlags << " " + << rec.getData()->Coord; + return output; // to enable cascading } - //////////////////////////////////////////////////////////////////// // // NormalTextureVertexRecord @@ -183,7 +173,6 @@ ostream& operator << (ostream& output, const TextureVertexRecord& rec) RegisterRecordProxy g_NormalTextureVertexProxy; - NormalTextureVertexRecord::NormalTextureVertexRecord() { } @@ -194,27 +183,26 @@ NormalTextureVertexRecord::~NormalTextureVertexRecord() { } + // virtual void NormalTextureVertexRecord::endian() { - SNormalTextureVertex *pVertex = (SNormalTextureVertex*)getData(); + SNormalTextureVertex *pVertex = (SNormalTextureVertex*)getData(); - ENDIAN( pVertex->swColor ); - ENDIAN( pVertex->swFlags ); - pVertex->Coord.endian(); - pVertex->Normal.endian(); - pVertex->Texture.endian(); -// ENDIAN( pVertex->PackedColor ); - ENDIAN( pVertex->dwVertexColorIndex ); + ENDIAN( pVertex->swColor ); + ENDIAN( pVertex->swFlags ); + pVertex->Coord.endian(); + pVertex->Normal.endian(); + pVertex->Texture.endian(); + // ENDIAN( pVertex->PackedColor ); + ENDIAN( pVertex->dwVertexColorIndex ); } ostream& operator << (ostream& output, const NormalTextureVertexRecord& rec) { - output << rec.className() << " " - << rec.getData()->swFlags << " " - << rec.getData()->Coord; - return output; // to enable cascading + output << rec.className() << " " + << rec.getData()->swFlags << " " + << rec.getData()->Coord; + return output; // to enable cascading } - - diff --git a/src/osgPlugins/flt/VertexPoolRecords.h b/src/osgPlugins/flt/VertexPoolRecords.h index 592c3ed57..d2dffca11 100644 --- a/src/osgPlugins/flt/VertexPoolRecords.h +++ b/src/osgPlugins/flt/VertexPoolRecords.h @@ -18,16 +18,21 @@ using namespace std; namespace flt { +#define V_HARD_EDGE_BIT BIT15 +#define V_NORMAL_FROZEN_BIT BIT14 +#define V_NO_COLOR_BIT BIT13 +#define V_PACKED_COLOR_BIT BIT12 + //////////////////////////////////////////////////////////////////// // // VertexPaletteRecord // //////////////////////////////////////////////////////////////////// -typedef struct VertexTableHeaderTag //Vertex Palette Header record +typedef struct VertexTableHeaderTag //Vertex Palette Header record { - SRecHeader RecHeader; - int32 diVertexTableLength; //Length of this record plus pool + SRecHeader RecHeader; + int32 diVertexTableLength; //Length of this record plus pool } SVertexTableHeader; @@ -43,7 +48,7 @@ class VertexPaletteRecord : public AncillaryRecord virtual int sizeofData() const { return sizeof(SVertexTableHeader); } virtual void accept(RecordVisitor& rv) { rv.apply(*this); } // virtual void traverse(RecordVisitor& rv); - friend ostream& operator << (ostream& output, const VertexPaletteRecord& rec); + friend ostream& operator << (ostream& output, const VertexPaletteRecord& rec); protected: virtual ~VertexPaletteRecord(); @@ -58,19 +63,19 @@ class VertexPaletteRecord : public AncillaryRecord // //////////////////////////////////////////////////////////////////// -typedef struct VertexTag // Vertex with Color Record Format +typedef struct VertexTag // Vertex with Color Record Format { - SRecHeader RecHeader; - uint16 swColor; // Color Name Index - uint16 swFlags; // Flags (bits, from left to right) - // 0 = Start Hard Edge - // 1 = Normal frozen - // 2 = no Vertex Color - // 3 = Packed Color - // 4-15 Spare - float64x3 Coord; // x,y,z coordinate - color32 PackedColor; // Packed color (A, B, G, R) - uint32 dwVertexColorIndex; + SRecHeader RecHeader; + uint16 swColor; // Color Name Index + uint16 swFlags; // Flags (bits, from left to right) + // 0 = Start Hard Edge + // 1 = Normal frozen + // 2 = no Vertex Color + // 3 = Packed Color + // 4-15 Spare + float64x3 Coord; // x,y,z coordinate + color32 PackedColor; // Packed color (A, B, G, R) + uint32 dwVertexColorIndex; } SVertex; @@ -85,7 +90,7 @@ class VertexRecord : public AncillaryRecord virtual void accept(RecordVisitor& rv) { rv.apply(*this); } // virtual void traverse(RecordVisitor& rv); virtual SVertex* getData() const { return (SVertex*)_pData; } - friend ostream& operator << (ostream& output, const VertexRecord& rec); + friend ostream& operator << (ostream& output, const VertexRecord& rec); protected: virtual ~VertexRecord(); @@ -101,20 +106,20 @@ class VertexRecord : public AncillaryRecord //////////////////////////////////////////////////////////////////// -typedef struct NormalVertexTag // Vertex with Normal Record Format +typedef struct NormalVertexTag // Vertex with Normal Record Format { - SRecHeader RecHeader; - uint16 swColor; // Color Name Index - uint16 swFlags; // Flags (bits, from left to right) - // 0 = Start Hard Edge - // 1 = Normal frozen - // 2 = no Vertex Color - // 3 = Packed Color - // 4-15 Spare - float64x3 Coord; // x,y,z coordinate - float32x3 Normal; // Vertex normal - color32 PackedColor; // Packed color (A, B, G, R) - uint32 dwVertexColorIndex; + SRecHeader RecHeader; + uint16 swColor; // Color Name Index + uint16 swFlags; // Flags (bits, from left to right) + // 0 = Start Hard Edge + // 1 = Normal frozen + // 2 = no Vertex Color + // 3 = Packed Color + // 4-15 Spare + float64x3 Coord; // x,y,z coordinate + float32x3 Normal; // Vertex normal + color32 PackedColor; // Packed color (A, B, G, R) + uint32 dwVertexColorIndex; } SNormalVertex; @@ -129,7 +134,7 @@ class NormalVertexRecord : public AncillaryRecord virtual void accept(RecordVisitor& rv) { rv.apply(*this); } // virtual void traverse(RecordVisitor& rv); virtual SNormalVertex* getData() const { return (SNormalVertex*)_pData; } - friend ostream& operator << (ostream& output, const NormalVertexRecord& rec); + friend ostream& operator << (ostream& output, const NormalVertexRecord& rec); protected: virtual ~NormalVertexRecord(); @@ -144,20 +149,20 @@ class NormalVertexRecord : public AncillaryRecord // //////////////////////////////////////////////////////////////////// -typedef struct TextureVertexTag // Vertex with Texture Record Format +typedef struct TextureVertexTag // Vertex with Texture Record Format { - SRecHeader RecHeader; - uint16 swColor; // Color Name Index - uint16 swFlags; // Flags (bits, from left to right) - // 0 = Start Hard Edge - // 1 = Normal frozen - // 2 = no Vertex Color - // 3 = Packed Color - // 4-15 Spare - float64x3 Coord; // x,y,z coordinate - float32x2 Texture; // Texture (u,v) - color32 PackedColor; // Packed color (A, B, G, R) - uint32 dwVertexColorIndex; + SRecHeader RecHeader; + uint16 swColor; // Color Name Index + uint16 swFlags; // Flags (bits, from left to right) + // 0 = Start Hard Edge + // 1 = Normal frozen + // 2 = no Vertex Color + // 3 = Packed Color + // 4-15 Spare + float64x3 Coord; // x,y,z coordinate + float32x2 Texture; // Texture (u,v) + color32 PackedColor; // Packed color (A, B, G, R) + uint32 dwVertexColorIndex; } STextureVertex; @@ -172,7 +177,7 @@ class TextureVertexRecord : public AncillaryRecord virtual void accept(RecordVisitor& rv) { rv.apply(*this); } // virtual void traverse(RecordVisitor& rv); virtual STextureVertex* getData() const { return (STextureVertex*)_pData; } - friend ostream& operator << (ostream& output, const TextureVertexRecord& rec); + friend ostream& operator << (ostream& output, const TextureVertexRecord& rec); protected: virtual ~TextureVertexRecord(); @@ -187,21 +192,21 @@ class TextureVertexRecord : public AncillaryRecord // //////////////////////////////////////////////////////////////////// -typedef struct NormalTextureVertexTag //Vertex with Normal and Texture Format +typedef struct NormalTextureVertexTag //Vertex with Normal and Texture Format { - SRecHeader RecHeader; - uint16 swColor; // Color Name Index - uint16 swFlags; // Flags (bits, from left to right) - // 0 = Start Hard Edge - // 1 = Normal frozen - // 2 = no Vertex Color - // 3 = Packed Color - // 4-15 Spare - float64x3 Coord; // x,y,z coordinate - float32x3 Normal; // Vertex normal - float32x2 Texture; // Texture (u,v) - color32 PackedColor; // Packed color (A, B, G, R) - uint32 dwVertexColorIndex; + SRecHeader RecHeader; + uint16 swColor; // Color Name Index + uint16 swFlags; // Flags (bits, from left to right) + // 0 = Start Hard Edge + // 1 = Normal frozen + // 2 = no Vertex Color + // 3 = Packed Color + // 4-15 Spare + float64x3 Coord; // x,y,z coordinate + float32x3 Normal; // Vertex normal + float32x2 Texture; // Texture (u,v) + color32 PackedColor; // Packed color (A, B, G, R) + uint32 dwVertexColorIndex; } SNormalTextureVertex; @@ -216,7 +221,7 @@ class NormalTextureVertexRecord : public AncillaryRecord virtual void accept(RecordVisitor& rv) { rv.apply(*this); } // virtual void traverse(RecordVisitor& rv); virtual SNormalTextureVertex* getData() const { return (SNormalTextureVertex*)_pData; } - friend ostream& operator << (ostream& output, const NormalTextureVertexRecord& rec); + friend ostream& operator << (ostream& output, const NormalTextureVertexRecord& rec); protected: virtual ~NormalTextureVertexRecord(); diff --git a/src/osgPlugins/flt/flt.cpp b/src/osgPlugins/flt/flt.cpp index f0464fb05..af106ffd9 100644 --- a/src/osgPlugins/flt/flt.cpp +++ b/src/osgPlugins/flt/flt.cpp @@ -2,7 +2,6 @@ #include "flt.h" - using namespace flt; //////////////////////////////////////////////////////////////////// @@ -14,32 +13,31 @@ int flt::isLittleEndianMachine() } -void flt::endian2(void* pSrc, int nSrc, void* pDst, int nDst) + /*nDst*/ +void flt::endian2(void* pSrc, int nSrc, void* pDst, int ) { - if (nSrc == 2) - { - short tmp1; - tmp1 = *(short *)pSrc; - tmp1 = (tmp1 << 8) | ((tmp1 >> 8) & 0xff); - *(short *)pDst = tmp1; - } - else if (nSrc == 4) - { - long tmp1; - tmp1 = *(long *)pSrc; - tmp1 = (tmp1 << 24) | ((tmp1 << 8) & 0xff0000) | ((tmp1 >> 8) & 0xff00) | ((tmp1 >> 24) & 0xff); - *(long *)pDst = tmp1; - } - else if (nSrc == 8) - { - long tmp1, tmp2; - tmp1 = *(long *)pSrc; - tmp2 = *(1 + (long *)pSrc); - tmp1 = (tmp1 << 24) | ((tmp1 << 8) & 0xff0000) | ((tmp1 >> 8) & 0xff00) | ((tmp1 >> 24) & 0xff); - tmp2 = (tmp2 << 24) | ((tmp2 << 8) & 0xff0000) | ((tmp2 >> 8) & 0xff00) | ((tmp2 >> 24) & 0xff); - *(long *)pDst = tmp2; - *(1 + (long *)pDst) = tmp1; - } + if (nSrc == 2) + { + short tmp1; + tmp1 = *(short *)pSrc; + tmp1 = (tmp1 << 8) | ((tmp1 >> 8) & 0xff); + *(short *)pDst = tmp1; + } + else if (nSrc == 4) + { + long tmp1; + tmp1 = *(long *)pSrc; + tmp1 = (tmp1 << 24) | ((tmp1 << 8) & 0xff0000) | ((tmp1 >> 8) & 0xff00) | ((tmp1 >> 24) & 0xff); + *(long *)pDst = tmp1; + } + else if (nSrc == 8) + { + long tmp1, tmp2; + tmp1 = *(long *)pSrc; + tmp2 = *(1 + (long *)pSrc); + tmp1 = (tmp1 << 24) | ((tmp1 << 8) & 0xff0000) | ((tmp1 >> 8) & 0xff00) | ((tmp1 >> 24) & 0xff); + tmp2 = (tmp2 << 24) | ((tmp2 << 8) & 0xff0000) | ((tmp2 >> 8) & 0xff00) | ((tmp2 >> 24) & 0xff); + *(long *)pDst = tmp2; + *(1 + (long *)pDst) = tmp1; + } } - - diff --git a/src/osgPlugins/flt/flt.h b/src/osgPlugins/flt/flt.h index 095d51820..6b302b794 100644 --- a/src/osgPlugins/flt/flt.h +++ b/src/osgPlugins/flt/flt.h @@ -53,7 +53,7 @@ extern void endian2( void* pSrc, int nSrc, void* pDst, int nDst ); struct float32x2 { - float32 _v[2]; + float32 _v[2]; inline float32 x() { return _v[0]; } inline float32 y() { return _v[1]; } @@ -63,18 +63,18 @@ struct float32x2 ENDIAN( _v[1] ); } - friend inline ostream& operator << (ostream& output, const float32x2& f) - { - output << f._v[0] << " " + friend inline ostream& operator << (ostream& output, const float32x2& f) + { + output << f._v[0] << " " << f._v[1]; - return output; // to enable cascading - } + return output; // to enable cascading + } }; struct float32x3 { - float32 _v[3]; + float32 _v[3]; inline float32 x() { return _v[0]; } inline float32 y() { return _v[1]; } inline float32 z() { return _v[2]; } @@ -85,19 +85,19 @@ struct float32x3 ENDIAN( _v[2] ); } - friend inline ostream& operator << (ostream& output, const float32x3& f) - { - output << f._v[0] << " " + friend inline ostream& operator << (ostream& output, const float32x3& f) + { + output << f._v[0] << " " << f._v[1] << " " << f._v[2]; - return output; // to enable cascading - } + return output; // to enable cascading + } }; struct float64x2 { - float64 _v[2]; + float64 _v[2]; inline float64 x() { return _v[0]; } inline float64 y() { return _v[1]; } inline float64 operator [] (int i) { return _v[i]; } @@ -106,12 +106,12 @@ struct float64x2 ENDIAN( _v[1] ); } - friend inline ostream& operator << (ostream& output, const float64x2& f) - { - output << f._v[0] << " " + friend inline ostream& operator << (ostream& output, const float64x2& f) + { + output << f._v[0] << " " << f._v[1]; - return output; // to enable cascading - } + return output; // to enable cascading + } }; @@ -131,10 +131,10 @@ struct float64x3 friend inline ostream& operator << (ostream& output, const float64x3& f) { - output << f._v[0] << " " + output << f._v[0] << " " << f._v[1] << " " << f._v[2]; - return output; // to enable cascading + return output; // to enable cascading } }; @@ -154,10 +154,23 @@ struct color32 }; +struct color48 // version 11, 12 & 13 +{ + uint16 _red; + uint16 _green; + uint16 _blue; + + inline float red() { return (float)_red/255; } + inline float green() { return (float)_green/255; } + inline float blue() { return (float)_blue/255; } + inline osg::Vec4 get() + { return osg::Vec4( red(), green(), blue(), 1); } +}; + struct SRecHeader { - uint16 _wOpcode; // identifies record type - uint16 _wLength; // total length of record + uint16 _wOpcode; // identifies record type + uint16 _wLength; // total length of record inline int opcode() { return (int)_wOpcode; } inline int length() { return (int)_wLength; } diff --git a/src/osgPlugins/flt/flt2osg.cpp b/src/osgPlugins/flt/flt2osg.cpp index 2d9e60def..8eca12d19 100644 --- a/src/osgPlugins/flt/flt2osg.cpp +++ b/src/osgPlugins/flt/flt2osg.cpp @@ -3,16 +3,12 @@ #include #include "osg/GL" -#include #include -#include #include -#include +#include #include -#include #include #include -#include #include #include #include @@ -20,10 +16,12 @@ #include #include #include -#include -#include #include -#include + +#include +#include +#include +#include #include "opcodes.h" #include "flt.h" @@ -33,6 +31,7 @@ #include "HeaderRecord.h" #include "ColorPaletteRecord.h" #include "MaterialPaletteRecord.h" +#include "OldMaterialPaletteRecord.h" #include "TexturePaletteRecord.h" #include "VertexPoolRecords.h" #include "GroupRecord.h" @@ -48,10 +47,8 @@ #include "GeoSetBuilder.h" #include "LongIDRecord.h" - using namespace flt; - ConvertFromFLT::ConvertFromFLT(FltFile* pFltFile) { _pFltFile = pFltFile; @@ -59,6 +56,8 @@ ConvertFromFLT::ConvertFromFLT(FltFile* pFltFile) _diCurrentOffset = 0; _wObjTransparency = 0; _nSubfaceLevel = 0; + _sfHdrUnitScale = 1; + _bHdrRgbMode = false; } @@ -76,7 +75,6 @@ osg::Node* ConvertFromFLT::convert(Record* rec) //////////////////////////////////////////////////////////////////// - Record* ConvertFromFLT::getVertexFromPool(int nOffset) { VertexPaletteOffsetMap::iterator fitr = _VertexPaletteOffsetMap.find(nOffset); @@ -94,7 +92,6 @@ void ConvertFromFLT::regisiterVertex(int nOffset, Record* pRec) } - //////////////////////////////////////////////////////////////////// osg::Node* ConvertFromFLT::visitNode(osg::Group* osgParent, Record* rec) @@ -104,6 +101,7 @@ osg::Node* ConvertFromFLT::visitNode(osg::Group* osgParent, Record* rec) if (rec->isOfType(HEADER_OP)) return visitHeader(osgParent, (HeaderRecord*)rec); else if (rec->isOfType(COLOR_PALETTE_OP)) return visitColorPalette(osgParent, (ColorPaletteRecord*)rec); else if (rec->isOfType(MATERIAL_PALETTE_OP)) return visitMaterialPalette(osgParent, (MaterialPaletteRecord*)rec); + else if (rec->isOfType(OLD_MATERIAL_PALETTE_OP))return visitOldMaterialPalette(osgParent, (OldMaterialPaletteRecord*)rec); else if (rec->isOfType(TEXTURE_PALETTE_OP)) return visitTexturePalette(osgParent, (TexturePaletteRecord*)rec); else if (rec->isOfType(VERTEX_PALETTE_OP)) return visitVertexPalette(osgParent, (VertexPaletteRecord*)rec); else if (rec->isOfType(VERTEX_C_OP)) return visitVertex(osgParent, (VertexRecord*)rec); @@ -127,7 +125,7 @@ osg::Node* ConvertFromFLT::visitNode(osg::Group* osgParent, Record* rec) osg::Node* ConvertFromFLT::visitAncillary(osg::Group* osgParent, PrimNodeRecord* rec) { osg::Node* node = NULL; - + // Visit for(int i=0; i < rec->getNumChildren(); i++) { @@ -148,7 +146,7 @@ osg::Node* ConvertFromFLT::visitPrimaryNode(osg::Group* osgParent, PrimNodeRecor { osg::Node* node = NULL; GeoSetBuilder geoSetBuilder(_pFltFile); - + // Visit for(int i=0; i < rec->getNumChildren(); i++) { @@ -187,12 +185,20 @@ osg::Node* ConvertFromFLT::visitHeader(osg::Group* osgParent, HeaderRecord* rec) { SHeader *pSHeader = (SHeader*)rec->getData(); - osg::Group* group = new osg::Group; - + // Version _diOpenFlightVersion = pSHeader->diFormatRevLev; - osg::notify(osg::INFO) << "Version " << _diOpenFlightVersion << endl; + // Unit scale + if (pSHeader->iMultDivUnit < 0) + _sfHdrUnitScale = 1.f / -pSHeader->iMultDivUnit; + else if (pSHeader->iMultDivUnit > 0) + _sfHdrUnitScale = pSHeader->iMultDivUnit; + + _bHdrRgbMode = (pSHeader->dwFlags & 0x40000000) ? true : false; // RGB space (=packed color) + + // Create root group node + osg::Group* group = new osg::Group; if (group) { visitAncillary(osgParent, rec); @@ -206,40 +212,96 @@ osg::Node* ConvertFromFLT::visitHeader(osg::Group* osgParent, HeaderRecord* rec) } -osg::Node* ConvertFromFLT::visitColorPalette(osg::Group* osgParent, ColorPaletteRecord* rec) + /*osgParent*/ +osg::Node* ConvertFromFLT::visitColorPalette(osg::Group* , ColorPaletteRecord* rec) { - SColorPalette* pCol = (SColorPalette*)rec->getData(); - ColorPool* pColorPool = _pFltFile->getColorPool(); - if (pCol && pColorPool) + if (pColorPool == NULL) { - for (int n=0; n<1024; n++) - pColorPool->regisiterColor(n, pCol->Colors[n].get()); + _pFltFile->useLocalColorPool(); + pColorPool = _pFltFile->getColorPool(); + } + + if (rec->getSize() > sizeof(SOldColorPalette)) + { + SColorPalette* pCol = (SColorPalette*)rec->getData(); + for (int i=0; i < 1024; i++) + pColorPool->addColor(i, pCol->Colors[i].get()); + } + else // version 11, 12 & 13 + { + SOldColorPalette* pSColor = (SOldColorPalette*)rec->getData(); + unsigned int i; + for (i=0; i < sizeof(pSColor->Colors)/sizeof(pSColor->Colors[0]); i++) + { + pColorPool->addColor(i, pSColor->Colors[i].get()); + } + + for (i=0; i < sizeof(pSColor->FixedColors)/sizeof(pSColor->FixedColors[0]); i++) + { + pColorPool->addColor(i+4096, pSColor->FixedColors[i].get()); + } + } + + return NULL; +} + + + /*osgParent*/ +osg::Node* ConvertFromFLT::visitMaterialPalette(osg::Group* , MaterialPaletteRecord* rec) +{ + SMaterial* pSMaterial = (SMaterial*)rec->getData(); + MaterialPool* pMaterialPool = _pFltFile->getMaterialPool(); + + if (pSMaterial && pMaterialPool ) + { + PoolMaterial* pPoolMat = new PoolMaterial; + + pPoolMat->Ambient = pSMaterial->Ambient; + pPoolMat->Diffuse = pSMaterial->Diffuse; + pPoolMat->Specular = pSMaterial->Specular; + pPoolMat->Emissive = pSMaterial->Emissive; + pPoolMat->sfShininess = pSMaterial->sfShininess; + pPoolMat->sfAlpha = pSMaterial->sfAlpha; + + pMaterialPool->addMaterial((int)pSMaterial->diIndex, pPoolMat); } return NULL; } - -osg::Node* ConvertFromFLT::visitMaterialPalette(osg::Group* osgParent, MaterialPaletteRecord* rec) + /*osgParent*/ +osg::Node* ConvertFromFLT::visitOldMaterialPalette(osg::Group* , OldMaterialPaletteRecord* rec) { - SMaterial* pSMaterial = (SMaterial*)rec->getData(); - + SOldMaterial* pSMaterial = (SOldMaterial*)rec->getData(); MaterialPool* pMaterialPool = _pFltFile->getMaterialPool(); - if (pSMaterial && pMaterialPool /* && (pMaterial->diFlags & BIT0) */) - pMaterialPool->regisiterMaterial((int)pSMaterial->diIndex, pSMaterial); + + if (pSMaterial && pMaterialPool ) + { + for (int i=0; i < 64; i++) + { + PoolMaterial* pPoolMat = new PoolMaterial; + + pPoolMat->Ambient = pSMaterial->mat[i].Ambient; + pPoolMat->Diffuse = pSMaterial->mat[i].Diffuse; + pPoolMat->Specular = pSMaterial->mat[i].Specular; + pPoolMat->Emissive = pSMaterial->mat[i].Emissive; + pPoolMat->sfShininess = pSMaterial->mat[i].sfShininess; + pPoolMat->sfAlpha = pSMaterial->mat[i].sfAlpha; + + pMaterialPool->addMaterial(i, pPoolMat); + } + } return NULL; } - -osg::Node* ConvertFromFLT::visitTexturePalette(osg::Group* osgParent, TexturePaletteRecord* rec) + /*osgParent*/ +osg::Node* ConvertFromFLT::visitTexturePalette(osg::Group* , TexturePaletteRecord* rec) { STexturePalette* pTexture = (STexturePalette*)rec->getData(); if (pTexture) { - osg::notify(osg::INFO) << "Texture" << pTexture->diIndex << " = " << pTexture->szFilename << endl; - - osg::ref_ptr image = osg::Registry::instance()->readImage(pTexture->szFilename); + osg::ref_ptr image = osgDB::readImageFile(pTexture->szFilename); if (image.valid()) { osg::Texture *osgTexture = new osg::Texture; @@ -249,22 +311,23 @@ osg::Node* ConvertFromFLT::visitTexturePalette(osg::Group* osgParent, TexturePal osgTexture->setWrap( osg::Texture::WRAP_S, osg::Texture::REPEAT ); osgTexture->setWrap( osg::Texture::WRAP_T, osg::Texture::REPEAT ); osgTexture->setImage(image.get()); - pTexturePool->regisiterTexture((int)pTexture->diIndex, osgTexture); + pTexturePool->addTexture((int)pTexture->diIndex, osgTexture); } } } return NULL; } - -osg::Node* ConvertFromFLT::visitVertexPalette(osg::Group* osgParent, VertexPaletteRecord* rec) + /*osgParent*/ +osg::Node* ConvertFromFLT::visitVertexPalette(osg::Group* , VertexPaletteRecord* rec) { _diCurrentOffset = rec->getSize(); return NULL; } -osg::Node* ConvertFromFLT::visitVertex(osg::Group* osgParent, VertexRecord* rec) + /*osgParent*/ +osg::Node* ConvertFromFLT::visitVertex(osg::Group* , VertexRecord* rec) { regisiterVertex(_diCurrentOffset, rec); _diCurrentOffset += rec->getSize(); @@ -272,7 +335,8 @@ osg::Node* ConvertFromFLT::visitVertex(osg::Group* osgParent, VertexRecord* rec) } -osg::Node* ConvertFromFLT::visitNormalVertex(osg::Group* osgParent, NormalVertexRecord* rec) + /*osgParent*/ +osg::Node* ConvertFromFLT::visitNormalVertex(osg::Group* , NormalVertexRecord* rec) { regisiterVertex(_diCurrentOffset, rec); _diCurrentOffset += rec->getSize(); @@ -280,7 +344,8 @@ osg::Node* ConvertFromFLT::visitNormalVertex(osg::Group* osgParent, NormalVertex } -osg::Node* ConvertFromFLT::visitTextureVertex(osg::Group* osgParent, TextureVertexRecord* rec) + /*osgParent*/ +osg::Node* ConvertFromFLT::visitTextureVertex(osg::Group* , TextureVertexRecord* rec) { regisiterVertex(_diCurrentOffset, rec); _diCurrentOffset += rec->getSize(); @@ -288,7 +353,8 @@ osg::Node* ConvertFromFLT::visitTextureVertex(osg::Group* osgParent, TextureVert } -osg::Node* ConvertFromFLT::visitNormalTextureVertex(osg::Group* osgParent, NormalTextureVertexRecord* rec) + /*osgParent*/ +osg::Node* ConvertFromFLT::visitNormalTextureVertex(osg::Group* , NormalTextureVertexRecord* rec) { regisiterVertex(_diCurrentOffset, rec); _diCurrentOffset += rec->getSize(); @@ -304,9 +370,9 @@ osg::Node* ConvertFromFLT::visitGroup(osg::Group* osgParent, GroupRecord* rec) osg::Node* node = visitAncillary(osgParent, rec); if (node) osgParent = (osg::Group*)node; - visitPrimaryNode(group, (PrimNodeRecord*)rec); group->setName(rec->getData()->szIdent); osgParent->addChild( group ); + visitPrimaryNode(group, (PrimNodeRecord*)rec); } return (osg::Node*)group; @@ -339,37 +405,54 @@ osg::Node* ConvertFromFLT::visitLOD(osg::Group* osgParent, LodRecord* rec) osg::Node* ConvertFromFLT::visitOldLOD(osg::Group* osgParent, OldLodRecord* rec) { + SOldLOD* pSLOD = (SOldLOD*)rec->getData(); + osg::LOD* lod = new osg::LOD; osg::Group* group = new osg::Group; - if (group) + if (lod && group) { osg::Node* node = visitAncillary(osgParent, rec); if (node) osgParent = (osg::Group*)node; visitPrimaryNode(group, (PrimNodeRecord*)rec); - group->setName(rec->getData()->szIdent); - osgParent->addChild( group ); + lod->addChild(group); + lod->setCenter(osg::Vec3( + (float)pSLOD->Center[0], + (float)pSLOD->Center[1], + (float)pSLOD->Center[2])); + lod->setRange(0, (float)pSLOD->dwSwitchOutDist); + lod->setRange(1, (float)pSLOD->dwSwitchInDist); + lod->setName(pSLOD->szIdent); + osgParent->addChild( lod ); } - return (osg::Node*)group; + return (osg::Node*)lod; } // TODO: DOF node implemented as Group. +// Converted DOF to use transform - jtracy@ist.ucf.edu osg::Node* ConvertFromFLT::visitDOF(osg::Group* osgParent, DofRecord* rec) { - osg::Group* group = new osg::Group; + osg::Transform* transform = new osg::Transform; - if (group) + if (transform) { osg::Node* node = visitAncillary(osgParent, rec); if (node) osgParent = (osg::Group*)node; - visitPrimaryNode(group, (PrimNodeRecord*)rec); - group->setName(rec->getData()->szIdent); - osgParent->addChild( group ); + visitPrimaryNode(transform, (PrimNodeRecord*)rec); + transform->setName(rec->getData()->szIdent); + + // note for Judd (and others) shouldn't there be code in here to set up the transform matrix? + // as a transform with an identity matrix is effectively only a + // a Group... I will leave for other more familiar with the + // DofRecord to create the matrix as I don't have any Open Flight + // documentation. RO August 2001. + + osgParent->addChild( transform ); } - return (osg::Node*)group; + return (osg::Node*)transform; } @@ -384,15 +467,15 @@ osg::Node* ConvertFromFLT::visitSwitch(osg::Group* osgParent, SwitchRecord* rec) visitPrimaryNode(switc, (PrimNodeRecord*)rec); switc->setName(rec->getData()->szIdent); - switc->setVal(rec->getData()->dwCurrentMask); + switc->setValue(rec->getData()->dwCurrentMask); osgParent->addChild( switc ); -/* - TODO: - mask_bit = 1 << (child_num % 32) - mask_word = mask_words [mask_num * num_words + child_num / 32] - child_selected = mask_word & mask_bit -*/ + /* + TODO: + mask_bit = 1 << (child_num % 32) + mask_word = mask_words [mask_num * num_words + child_num / 32] + child_selected = mask_word & mask_bit + */ } return (osg::Node*)switc; @@ -426,69 +509,103 @@ void ConvertFromFLT::visitFace(GeoSetBuilder* pBuilder, FaceRecord* rec) osg::Vec4 color(1,1,1,1); // Cull face & wireframe - int drawMode = pSFace->swDrawFlag & (BIT0 | BIT1); + int drawMode = pSFace->swDrawFlag & (BIT0 | BIT1); switch(drawMode) { - case FaceRecord::SOLID_BACKFACED: - pBuilder->setCullface(true); - break; - case FaceRecord::SOLID_NO_BACKFACE: - pBuilder->setCullface(false); - break; - case FaceRecord::WIREFRAME_NOT_CLOSED: - pBuilder->setPrimType(osg::GeoSet::LINE_STRIP); - break; - case FaceRecord::WIREFRAME_CLOSED: - pBuilder->setPrimType(osg::GeoSet::LINE_LOOP); - break; + case FaceRecord::SOLID_BACKFACED: + pBuilder->setCullface(true); + break; + case FaceRecord::SOLID_NO_BACKFACE: + pBuilder->setCullface(false); + break; + case FaceRecord::WIREFRAME_NOT_CLOSED: + pBuilder->setPrimType(osg::GeoSet::LINE_STRIP); + break; + case FaceRecord::WIREFRAME_CLOSED: + pBuilder->setPrimType(osg::GeoSet::LINE_LOOP); + break; } -/* - TODO: + /* + TODO: - int directionalLight = pSFace->swDrawFlag & (BIT3 | BIT4); - switch(directionalLight) - { - case FaceRecord::OMNIDIRECTIONAL_LIGHT: - break; - case FaceRecord::UNIDIRECTIONAL_LIGHT: - break; - case FaceRecord::BIDIRECTIONAL_LIGHT: - break; - } -*/ + int directionalLight = pSFace->swDrawFlag & (BIT3 | BIT4); + switch(directionalLight) + { + case FaceRecord::OMNIDIRECTIONAL_LIGHT: + break; + case FaceRecord::UNIDIRECTIONAL_LIGHT: + break; + case FaceRecord::BIDIRECTIONAL_LIGHT: + break; + } + */ // Lighting - switch(pSFace->swLightMode) + if (_diOpenFlightVersion > 13) { - case FaceRecord::FACE_COLOR: - case FaceRecord::VERTEX_COLOR: - pBuilder->setLighting(false); - break; - case FaceRecord::FACE_COLOR_LIGHTING: - case FaceRecord::VERTEX_COLOR_LIGHTING: - pBuilder->setLighting(true); - break; + switch(pSFace->swLightMode) + { + case FaceRecord::FACE_COLOR: + case FaceRecord::VERTEX_COLOR: + pBuilder->setLighting(false); + break; + case FaceRecord::FACE_COLOR_LIGHTING: + case FaceRecord::VERTEX_COLOR_LIGHTING: + pBuilder->setLighting(true); + break; + } } // Color - switch(pSFace->swLightMode) { - case FaceRecord::FACE_COLOR: - case FaceRecord::FACE_COLOR_LIGHTING: - case FaceRecord::VERTEX_COLOR: - case FaceRecord::VERTEX_COLOR_LIGHTING: - if (!(pSFace->diFlags & BIT1)) // face color bit + ColorPool* pColorPool = _pFltFile->getColorPool(); + + if (_diOpenFlightVersion > 13) + { + if (!(pSFace->dwFlags & FaceRecord::NO_COLOR_BIT)) + { + float alpha; + bool bPackedColor = + _bHdrRgbMode || + (pSFace->dwFlags & FaceRecord::PACKED_COLOR_BIT) || + (pColorPool == NULL); + + if (bPackedColor) + color = pSFace->PrimaryPackedColor.get(); + else + color = pColorPool->getColor(pSFace->dwPrimaryColorIndex); + + alpha = 1.0f - (float)pSFace->wTransparency / 65535.0f; + color[3] = alpha; + + if (alpha < 1.0f) + pBuilder->setTransparency(true); + + pBuilder->setFaceColor(color); + + switch(pSFace->swLightMode) + { + case FaceRecord::FACE_COLOR: + case FaceRecord::FACE_COLOR_LIGHTING: + pBuilder->setColorBinding(osg::GeoSet::BIND_OVERALL); + break; + + case FaceRecord::VERTEX_COLOR: + case FaceRecord::VERTEX_COLOR_LIGHTING: + pBuilder->setColorBinding(osg::GeoSet::BIND_PERVERTEX); + break; + } + } + } + else // Version 11, 12 & 13 { float alpha; + bool bPackedColor = _bHdrRgbMode || (pColorPool == NULL); - if (pSFace->diFlags & BIT3) // Packed color bit + if (bPackedColor) color = pSFace->PrimaryPackedColor.get(); else - { - ColorPool* pColorPool = _pFltFile->getColorPool(); - if (pColorPool) - color = pColorPool->getColor(pSFace->dwPrimaryColorIndex); - } + color = pColorPool->getColor(pSFace->wPrimaryNameIndex); alpha = 1.0f - (float)pSFace->wTransparency / 65535.0f; color[3] = alpha; @@ -497,16 +614,15 @@ void ConvertFromFLT::visitFace(GeoSetBuilder* pBuilder, FaceRecord* rec) pBuilder->setTransparency(true); pBuilder->setColorBinding(osg::GeoSet::BIND_OVERALL); - pBuilder->setColor(color); + pBuilder->setFaceColor(color); } - break; } // Material MaterialPool* pMaterialPool = _pFltFile->getMaterialPool(); if (pMaterialPool) { - SMaterial* pSMaterial = pMaterialPool->getMaterial((int)pSFace->iMaterial); + PoolMaterial* pSMaterial = pMaterialPool->getMaterial((int)pSFace->iMaterial); if (pSMaterial) { @@ -540,16 +656,27 @@ void ConvertFromFLT::visitFace(GeoSetBuilder* pBuilder, FaceRecord* rec) emissiv[2] = pSMaterial->Emissive[2]; emissiv[3] = alpha; - osgMaterial->setAmbient(osg::Material::FACE_FRONT_AND_BACK, ambient); - osgMaterial->setDiffuse(osg::Material::FACE_FRONT_AND_BACK, diffuse); - osgMaterial->setSpecular(osg::Material::FACE_FRONT_AND_BACK, specular); - osgMaterial->setEmission(osg::Material::FACE_FRONT_AND_BACK, emissiv); - osgMaterial->setShininess(osg::Material::FACE_FRONT_AND_BACK, pSMaterial->sfShininess/128.0f); - osgMaterial->setColorMode(osg::Material::OFF); + osgMaterial->setAmbient(osg::Material::FRONT_AND_BACK, ambient); + osgMaterial->setDiffuse(osg::Material::FRONT_AND_BACK, diffuse); + osgMaterial->setSpecular(osg::Material::FRONT_AND_BACK, specular); + osgMaterial->setEmission(osg::Material::FRONT_AND_BACK, emissiv); + osgMaterial->setAlpha(osg::Material::FRONT_AND_BACK, alpha); + osgMaterial->setShininess(osg::Material::FRONT_AND_BACK, pSMaterial->sfShininess/128.0f); if (alpha < 1.0f) pBuilder->setTransparency(true); + switch (pSFace->swLightMode) + { + case FaceRecord::VERTEX_COLOR: + case FaceRecord::VERTEX_COLOR_LIGHTING: + osgMaterial->setColorMode(osg::Material::AMBIENT_AND_DIFFUSE); + break; + + default: + osgMaterial->setColorMode(osg::Material::OFF); + } + pBuilder->setMaterial(osgMaterial); } } @@ -572,10 +699,10 @@ void ConvertFromFLT::visitFace(GeoSetBuilder* pBuilder, FaceRecord* rec) { switch (image->pixelFormat()) { - case GL_LUMINANCE_ALPHA: - case GL_RGBA: - pBuilder->setTransparency(true); - break; + case GL_LUMINANCE_ALPHA: + case GL_RGBA: + pBuilder->setTransparency(true); + break; } } pBuilder->setTexture(osgTexture); @@ -583,7 +710,8 @@ void ConvertFromFLT::visitFace(GeoSetBuilder* pBuilder, FaceRecord* rec) } // Visit vertices - for(int i=0; i < rec->getNumChildren(); i++) + int i; + for(i=0; i < rec->getNumChildren(); i++) { Record* child = rec->getChild(i); @@ -592,16 +720,24 @@ void ConvertFromFLT::visitFace(GeoSetBuilder* pBuilder, FaceRecord* rec) int op = child->getOpcode(); switch (op) { - case VERTEX_LIST_OP: - visitVertexList(pBuilder, (VertexListRecord*)child); - break; + case VERTEX_LIST_OP: + visitVertexList(pBuilder, (VertexListRecord*)child); + break; - case OLD_VERTEX_OP: - case OLD_VERTEX_COLOR_OP: - case OLD_VERTEX_COLOR_NORMAL_OP: - pBuilder->addVertex(child); - break; + case OLD_VERTEX_OP: + pBuilder->addVertex(child); + break; + case OLD_VERTEX_COLOR_OP: + pBuilder->setColorBinding(osg::GeoSet::BIND_PERVERTEX); + pBuilder->addVertex(child); + break; + + case OLD_VERTEX_COLOR_NORMAL_OP: + pBuilder->setColorBinding(osg::GeoSet::BIND_PERVERTEX); + pBuilder->addVertex(child); + pBuilder->setLighting(true); + break; } } } @@ -609,7 +745,7 @@ void ConvertFromFLT::visitFace(GeoSetBuilder* pBuilder, FaceRecord* rec) // Add primitive to GeoSet and prepare for next. pBuilder->addPrimitive(); - // Look for sufbfaces + // Look for subfaces _nSubfaceLevel++; for(i=0; i < rec->getNumChildren(); i++) { @@ -657,7 +793,7 @@ osg::Node* ConvertFromFLT::visitMatrix(osg::Group* osgParent, MatrixRecord* rec) { SMatrix* pSMatrix = (SMatrix*)rec->getData(); - osg::DCS* dcs = new osg::DCS; + osg::Transform* dcs = new osg::Transform; if (dcs) { osg::Matrix m; @@ -677,10 +813,9 @@ osg::Node* ConvertFromFLT::visitMatrix(osg::Group* osgParent, MatrixRecord* rec) } - osg::Node* ConvertFromFLT::visitExternal(osg::Group* osgParent, ExternalRecord* rec) { - SExternalReference *pSExternal = (SExternalReference*)rec->getData(); + // SExternalReference *pSExternal = (SExternalReference*)rec->getData(); if (osgParent) { @@ -705,7 +840,7 @@ osg::Node* ConvertFromFLT::visitExternal(osg::Group* osgParent, ExternalRecord* void ConvertFromFLT::visitLightPoint(GeoSetBuilder* pBuilder, LightPointRecord* rec) { - SLightPoint *pSLightPoint = (SLightPoint*)rec->getData(); + // SLightPoint *pSLightPoint = (SLightPoint*)rec->getData(); // Visit vertices for(int i=0; i < rec->getNumChildren(); i++) @@ -717,22 +852,23 @@ void ConvertFromFLT::visitLightPoint(GeoSetBuilder* pBuilder, LightPointRecord* int op = child->getOpcode(); switch (op) { - case VERTEX_LIST_OP: - pBuilder->setPrimType(osg::GeoSet::POINTS); - visitVertexList(pBuilder, (VertexListRecord*)child); - break; + case VERTEX_LIST_OP: + pBuilder->setPrimType(osg::GeoSet::POINTS); + visitVertexList(pBuilder, (VertexListRecord*)child); + break; - case OLD_VERTEX_OP: - case OLD_VERTEX_COLOR_OP: - case OLD_VERTEX_COLOR_NORMAL_OP: - pBuilder->setColorBinding(osg::GeoSet::BIND_PERVERTEX); - pBuilder->addVertex(child); - pBuilder->addPrimitive(); - break; + case OLD_VERTEX_OP: + pBuilder->addVertex(child); + pBuilder->addPrimitive(); + break; + + case OLD_VERTEX_COLOR_OP: + case OLD_VERTEX_COLOR_NORMAL_OP: + pBuilder->setColorBinding(osg::GeoSet::BIND_PERVERTEX); + pBuilder->addVertex(child); + pBuilder->addPrimitive(); + break; } } } } - - - diff --git a/src/osgPlugins/flt/flt2osg.h b/src/osgPlugins/flt/flt2osg.h index 1b549ee2b..853ab9e55 100644 --- a/src/osgPlugins/flt/flt2osg.h +++ b/src/osgPlugins/flt/flt2osg.h @@ -30,6 +30,7 @@ class Record; class HeaderRecord; class ColorPaletteRecord; class MaterialPaletteRecord; +class OldMaterialPaletteRecord; class TexturePaletteRecord; class VertexPaletteRecord; class VertexRecord; @@ -73,6 +74,7 @@ public: osg::Node* visitHeader(osg::Group* osgParent, HeaderRecord* rec); osg::Node* visitColorPalette(osg::Group* osgParent, ColorPaletteRecord* rec); osg::Node* visitMaterialPalette(osg::Group* osgParent, MaterialPaletteRecord* rec); + osg::Node* visitOldMaterialPalette(osg::Group* osgParent, OldMaterialPaletteRecord* rec); osg::Node* visitTexturePalette(osg::Group* osgParent, TexturePaletteRecord* rec); osg::Node* visitVertexPalette(osg::Group* osgParent, VertexPaletteRecord* rec); osg::Node* visitVertex(osg::Group* osgParent, VertexRecord* rec); @@ -106,6 +108,8 @@ private: int _diCurrentOffset; unsigned short _wObjTransparency; int _nSubfaceLevel; + float _sfHdrUnitScale; // iMultDivUnit + bool _bHdrRgbMode; }; diff --git a/src/osgPlugins/flt/opcodes.h b/src/osgPlugins/flt/opcodes.h index a16ce960b..1d16dd7b9 100644 --- a/src/osgPlugins/flt/opcodes.h +++ b/src/osgPlugins/flt/opcodes.h @@ -8,46 +8,53 @@ #define UNKNOWN_OP 0 -#define HEADER_OP 1 -#define GROUP_OP 2 +#define HEADER_OP 1 +#define GROUP_OP 2 #define OLD_LOD_OP 3 -#define OBJECT_OP 4 -#define FACE_OP 5 +#define OBJECT_OP 4 +#define FACE_OP 5 #define OLD_VERTEX_OP 7 #define OLD_VERTEX_COLOR_OP 8 #define OLD_VERTEX_COLOR_NORMAL_OP 9 -#define PUSH_LEVEL_OP 10 -#define POP_LEVEL_OP 11 -#define DOF_OP 14 +#define PUSH_LEVEL_OP 10 +#define POP_LEVEL_OP 11 +#define DOF_OP 14 #define PUSH_SUBFACE_OP 19 #define POP_SUBFACE_OP 20 #define PUSH_EXTENSION_OP 21 #define POP_EXTENSION_OP 22 -#define COMMENT_OP 31 -#define COLOR_PALETTE_OP 32 +#define COMMENT_OP 31 +#define COLOR_PALETTE_OP 32 #define LONG_ID_OP 33 - // Opcodes 40 to 48 are obsolete -#define MATRIX_OP 49 +/* +Ignore 40-48 +#define OLD_TRANSLATE_OP 44 +*/ +#define MATRIX_OP 49 #define VECTOR_OP 50 -#define REPLICATE_OP 60 -#define INSTANCE_REFERENCE_OP 61 -#define INSTANCE_DEFINITION_OP 62 -#define EXTERNAL_REFERENCE_OP 63 -#define TEXTURE_PALETTE_OP 64 -#define VERTEX_PALETTE_OP 67 +#define REPLICATE_OP 60 +#define INSTANCE_REFERENCE_OP 61 +#define INSTANCE_DEFINITION_OP 62 +#define EXTERNAL_REFERENCE_OP 63 +#define TEXTURE_PALETTE_OP 64 +#define OLD_MATERIAL_PALETTE_OP 66 +#define VERTEX_PALETTE_OP 67 #define VERTEX_C_OP 68 #define VERTEX_CN_OP 69 #define VERTEX_CNT_OP 70 #define VERTEX_CT_OP 71 #define VERTEX_LIST_OP 72 -#define LOD_OP 73 +#define LOD_OP 73 #define BOUNDING_BOX_OP 74 +/* +Ignore 76-82 #define ROTATE_ABOUT_EDGE_OP 76 #define TRANSLATE_OP 78 #define SCALE_OP 79 #define ROTATE_ABOUT_POINT_OP 80 #define ROTATE_SCALE_TO_POINT_OP 81 #define PUT_TRANSFORM_OP 82 +*/ #define ROAD_ZONE_OP 88 #define MORPH_VERTEX_LIST_OP 89 #define GENERAL_MATRIX_OP 94 diff --git a/src/osgPlugins/gif/Makefile b/src/osgPlugins/gif/Makefile index ca33b997e..1c141e85f 100644 --- a/src/osgPlugins/gif/Makefile +++ b/src/osgPlugins/gif/Makefile @@ -11,7 +11,7 @@ TARGET_LOADER_FILES = osgPlugins/osgdb_gif.so LIBS = -lungif C++FLAGS += -I. -I../../../include -LDFLAGS += -L../../../lib +LDFLAGS += -L../../../lib $(FREEBSD_LOCALLIBS) include ../../../Make/makerules diff --git a/src/osgPlugins/gif/ReaderWriterGIF.cpp b/src/osgPlugins/gif/ReaderWriterGIF.cpp index 50e0b916a..2be1b9e59 100644 --- a/src/osgPlugins/gif/ReaderWriterGIF.cpp +++ b/src/osgPlugins/gif/ReaderWriterGIF.cpp @@ -1,27 +1,26 @@ #include -#include -#include -#include #include -#include #include - #include +#include +#include + + /**************************************************************************** * * Follows is code extracted from the simage library. Original Authors: * - * Systems in Motion, + * Systems in Motion, * - * + * * Peder Blekken * Morten Eriksen - * Marius Bugge Monsen + * Marius Bugge Monsen * - * The original COPYING notice + * The original COPYING notice * - * All files in this library are public domain, except simage_rgb.cpp which is + * All files in this library are public domain, except simage_rgb.cpp which is * Copyright (c) Mark J Kilgard . I will contact Mark * very soon to hear if this source also can become public domain. * @@ -45,8 +44,9 @@ #include #include -extern "C" { -#include +extern "C" +{ + #include }; #define ERR_NO_ERROR 0 @@ -61,247 +61,266 @@ static int giferror = ERR_NO_ERROR; int simage_gif_error(char * buffer, int buflen) { - switch (giferror) { - case ERR_OPEN: - strncpy(buffer, "GIF loader: Error opening file", buflen); - break; - case ERR_READ: - strncpy(buffer, "GIF loader: Error reading file", buflen); - break; - case ERR_MEM: - strncpy(buffer, "GIF loader: Out of memory error", buflen); - break; - } - return giferror; + switch (giferror) + { + case ERR_OPEN: + strncpy(buffer, "GIF loader: Error opening file", buflen); + break; + case ERR_READ: + strncpy(buffer, "GIF loader: Error reading file", buflen); + break; + case ERR_MEM: + strncpy(buffer, "GIF loader: Out of memory error", buflen); + break; + } + return giferror; } -int -simage_gif_identify(const char *filename, - const unsigned char *header, - int headerlen) + +int +simage_gif_identify(const char *, +const unsigned char *header, +int headerlen) { - static unsigned char gifcmp[] = {'G', 'I', 'F'}; - if (headerlen < 3) return 0; - if (memcmp((const void*)header, - (const void*)gifcmp, 3) == 0) return 1; - return 0; + static unsigned char gifcmp[] = {'G', 'I', 'F'}; + if (headerlen < 3) return 0; + if (memcmp((const void*)header, + (const void*)gifcmp, 3) == 0) return 1; + return 0; } + static void -decode_row(GifFileType * giffile, - unsigned char * buffer, - unsigned char * rowdata, - int x, int y, int len, - int transparent) +decode_row(GifFileType * giffile, +unsigned char * buffer, +unsigned char * rowdata, +int x, int y, int len, +int transparent) { - GifColorType * cmentry; - ColorMapObject * colormap; - int colormapsize; - unsigned char col; - unsigned char * ptr; - y = giffile->SHeight - (y+1); - ptr = buffer + (giffile->SWidth * y + x) * 4; + GifColorType * cmentry; + ColorMapObject * colormap; + int colormapsize; + unsigned char col; + unsigned char * ptr; + y = giffile->SHeight - (y+1); + ptr = buffer + (giffile->SWidth * y + x) * 4; - colormap = (giffile->Image.ColorMap - ? giffile->Image.ColorMap - : giffile->SColorMap); - colormapsize = colormap ? colormap->ColorCount : 255; - - while (len--) { - col = *rowdata++; - if (col >= colormapsize) col = 0; /* just in case */ - cmentry = colormap ? &colormap->Colors[col] : NULL; - if (cmentry) { - *ptr++ = cmentry->Red; - *ptr++ = cmentry->Green; - *ptr++ = cmentry->Blue; + colormap = (giffile->Image.ColorMap + ? giffile->Image.ColorMap + : giffile->SColorMap); + colormapsize = colormap ? colormap->ColorCount : 255; + + while (len--) + { + col = *rowdata++; + /* just in case */ + if (col >= colormapsize) col = 0; + cmentry = colormap ? &colormap->Colors[col] : NULL; + if (cmentry) + { + *ptr++ = cmentry->Red; + *ptr++ = cmentry->Green; + *ptr++ = cmentry->Blue; + } + else + { + *ptr++ = col; + *ptr++ = col; + *ptr++ = col; + } + *ptr++ = (col == transparent ? 0x00 : 0xff); } - else { - *ptr++ = col; - *ptr++ = col; - *ptr++ = col; - } - *ptr++ = (col == transparent ? 0x00 : 0xff); - } } + unsigned char * simage_gif_load(const char *filename, - int *width_ret, - int *height_ret, - int *numComponents_ret) +int *width_ret, +int *height_ret, +int *numComponents_ret) { - int i, j, n, row, col, width, height, extcode; - unsigned char * rowdata; - unsigned char * buffer, * ptr; - unsigned char bg; - int transparent; - GifRecordType recordtype; - GifByteType * extension; - GifFileType * giffile; - GifColorType * bgcol; - - /* The way an interlaced image should be read - offsets and jumps */ - int interlacedoffset[] = { 0, 4, 2, 1 }; - int interlacedjumps[] = { 8, 8, 4, 2 }; - - giffile = DGifOpenFileName(filename); - if (!giffile) { - giferror = ERR_OPEN; - return NULL; - } - - transparent = -1; /* no transparent color by default */ - - n = giffile->SHeight * giffile->SWidth; - buffer = (unsigned char *)malloc(n * 4); - if (!buffer) { - giferror = ERR_MEM; - return NULL; - } - rowdata = (unsigned char *)malloc(giffile->SWidth); - if (!rowdata) { - giferror = ERR_MEM; - free(buffer); - return NULL; - } - - bg = giffile->SBackGroundColor; - if (giffile->SColorMap && bg < giffile->SColorMap->ColorCount) { - bgcol = &giffile->SColorMap->Colors[bg]; - } - else bgcol = NULL; - ptr = buffer; - for (i = 0; i < n; i++) { - if (bgcol) { - *ptr++ = bgcol->Red; - *ptr++ = bgcol->Green; - *ptr++ = bgcol->Blue; - *ptr++ = 0xff; - } - else { - *ptr++ = 0x00; - *ptr++ = 0x00; - *ptr++ = 0x00; - *ptr++ = 0xff; - } - } - - /* Scan the content of the GIF file and load the image(s) in: */ - do { - if (DGifGetRecordType(giffile, &recordtype) == GIF_ERROR) { - giferror = ERR_READ; - free(buffer); - free(rowdata); - return NULL; - } - switch (recordtype) { - case IMAGE_DESC_RECORD_TYPE: - if (DGifGetImageDesc(giffile) == GIF_ERROR) { - giferror = ERR_READ; - free(buffer); - free(rowdata); + int i, j, n, row, col, width, height, extcode; + unsigned char * rowdata; + unsigned char * buffer, * ptr; + unsigned char bg; + int transparent; + GifRecordType recordtype; + GifByteType * extension; + GifFileType * giffile; + GifColorType * bgcol; + + /* The way an interlaced image should be read - offsets and jumps */ + int interlacedoffset[] = { 0, 4, 2, 1 }; + int interlacedjumps[] = { 8, 8, 4, 2 }; + + giffile = DGifOpenFileName(filename); + if (!giffile) + { + giferror = ERR_OPEN; return NULL; - } - row = giffile->Image.Top; /* subimage position in composite image */ - col = giffile->Image.Left; - width = giffile->Image.Width; - height = giffile->Image.Height; - if (giffile->Image.Left + giffile->Image.Width > giffile->SWidth || - giffile->Image.Top + giffile->Image.Height > giffile->SHeight) { - /* image is not confined to screen dimension */ - giferror = ERR_READ; - free(buffer); - free(rowdata); + } + + transparent = -1; /* no transparent color by default */ + + n = giffile->SHeight * giffile->SWidth; + buffer = (unsigned char *)malloc(n * 4); + if (!buffer) + { + giferror = ERR_MEM; return NULL; - } - if (giffile->Image.Interlace) { - fprintf(stderr,"interlace\n"); - /* Need to perform 4 passes on the images: */ - for (i = 0; i < 4; i++) { - for (j = row + interlacedoffset[i]; j < row + height; - j += interlacedjumps[i]) { - if (DGifGetLine(giffile, rowdata, width) == GIF_ERROR) { - giferror = ERR_READ; - free(buffer); - free(rowdata); - return NULL; - } - else decode_row(giffile, buffer, rowdata, col, j, width, transparent); - } + } + rowdata = (unsigned char *)malloc(giffile->SWidth); + if (!rowdata) + { + giferror = ERR_MEM; + free(buffer); + return NULL; + } + + bg = giffile->SBackGroundColor; + if (giffile->SColorMap && bg < giffile->SColorMap->ColorCount) + { + bgcol = &giffile->SColorMap->Colors[bg]; + } + else bgcol = NULL; + ptr = buffer; + for (i = 0; i < n; i++) + { + if (bgcol) + { + *ptr++ = bgcol->Red; + *ptr++ = bgcol->Green; + *ptr++ = bgcol->Blue; + *ptr++ = 0xff; } - } - else { - for (i = 0; i < height; i++, row++) { - if (DGifGetLine(giffile, rowdata, width) == GIF_ERROR) { + else + { + *ptr++ = 0x00; + *ptr++ = 0x00; + *ptr++ = 0x00; + *ptr++ = 0xff; + } + } + + /* Scan the content of the GIF file and load the image(s) in: */ + do + { + if (DGifGetRecordType(giffile, &recordtype) == GIF_ERROR) + { giferror = ERR_READ; free(buffer); free(rowdata); return NULL; - } - else decode_row(giffile, buffer, rowdata, col, row, width, transparent); } - } - break; - case EXTENSION_RECORD_TYPE: - /* Skip any extension blocks in file: */ - if (DGifGetExtension(giffile, &extcode, &extension) == GIF_ERROR) { - giferror = ERR_READ; - free(buffer); - free(rowdata); - return NULL; - } - /* transparent test from the gimp gif-plugin. Open Source rulez! */ - else if (extcode == 0xf9) { - if (extension[0] >= 4 && extension[1] & 0x1) transparent = extension[4]; - else transparent = -1; - } - while (extension != NULL) { - if (DGifGetExtensionNext(giffile, &extension) == GIF_ERROR) { - giferror = ERR_READ; - free(buffer); - free(rowdata); - return NULL; + switch (recordtype) + { + case IMAGE_DESC_RECORD_TYPE: + if (DGifGetImageDesc(giffile) == GIF_ERROR) + { + giferror = ERR_READ; + free(buffer); + free(rowdata); + return NULL; + } + /* subimage position in composite image */ + row = giffile->Image.Top; + col = giffile->Image.Left; + width = giffile->Image.Width; + height = giffile->Image.Height; + if (giffile->Image.Left + giffile->Image.Width > giffile->SWidth || + giffile->Image.Top + giffile->Image.Height > giffile->SHeight) + { + /* image is not confined to screen dimension */ + giferror = ERR_READ; + free(buffer); + free(rowdata); + return NULL; + } + if (giffile->Image.Interlace) + { + fprintf(stderr,"interlace\n"); + /* Need to perform 4 passes on the images: */ + for (i = 0; i < 4; i++) + { + for (j = row + interlacedoffset[i]; j < row + height; + j += interlacedjumps[i]) + { + if (DGifGetLine(giffile, rowdata, width) == GIF_ERROR) + { + giferror = ERR_READ; + free(buffer); + free(rowdata); + return NULL; + } + else decode_row(giffile, buffer, rowdata, col, j, width, transparent); + } + } + } + else + { + for (i = 0; i < height; i++, row++) + { + if (DGifGetLine(giffile, rowdata, width) == GIF_ERROR) + { + giferror = ERR_READ; + free(buffer); + free(rowdata); + return NULL; + } + else decode_row(giffile, buffer, rowdata, col, row, width, transparent); + } + } + break; + case EXTENSION_RECORD_TYPE: + /* Skip any extension blocks in file: */ + if (DGifGetExtension(giffile, &extcode, &extension) == GIF_ERROR) + { + giferror = ERR_READ; + free(buffer); + free(rowdata); + return NULL; + } + /* transparent test from the gimp gif-plugin. Open Source rulez! */ + else if (extcode == 0xf9) + { + if (extension[0] >= 4 && extension[1] & 0x1) transparent = extension[4]; + else transparent = -1; + } + while (extension != NULL) + { + if (DGifGetExtensionNext(giffile, &extension) == GIF_ERROR) + { + giferror = ERR_READ; + free(buffer); + free(rowdata); + return NULL; + } + } + break; + case TERMINATE_RECORD_TYPE: + break; + default: /* Should be trapped by DGifGetRecordType. */ + break; } - } - break; - case TERMINATE_RECORD_TYPE: - break; - default: /* Should be trapped by DGifGetRecordType. */ - break; } - } - while (recordtype != TERMINATE_RECORD_TYPE); + while (recordtype != TERMINATE_RECORD_TYPE); - free(rowdata); - *width_ret = giffile->SWidth; - *height_ret = giffile->SHeight; - *numComponents_ret = 4; - DGifCloseFile(giffile); - return buffer; + free(rowdata); + *width_ret = giffile->SWidth; + *height_ret = giffile->SHeight; + *numComponents_ret = 4; + DGifCloseFile(giffile); + return buffer; } - -class ReaderWriterGIF : public osg::ReaderWriter +class ReaderWriterGIF : public osgDB::ReaderWriter { public: virtual const char* className() { return "GIF Image Reader"; } - virtual bool acceptsExtension(const std::string& extension) { return extension=="gif"; } - - virtual osg::Node* readNode(const std::string& fileName) + virtual bool acceptsExtension(const std::string& extension) { - osg::Image* image = readImage(fileName); - if (image) - { - osg::Geode* geode = osg::createGeodeForImage(image); - if (geode==NULL) image->unref(); - return geode; - } - else - { - return NULL; - } + return osgDB::equalCaseInsensitive(extension,"gif"); } virtual osg::Image* readImage(const std::string& fileName) @@ -313,7 +332,7 @@ class ReaderWriterGIF : public osg::ReaderWriter int numComponents_ret; imageData = simage_gif_load(fileName.c_str(),&width_ret,&height_ret,&numComponents_ret); - + if (imageData==NULL) return NULL; int s = width_ret; @@ -324,19 +343,19 @@ class ReaderWriterGIF : public osg::ReaderWriter unsigned int pixelFormat = numComponents_ret == 1 ? GL_LUMINANCE : - numComponents_ret == 2 ? GL_LUMINANCE_ALPHA : - numComponents_ret == 3 ? GL_RGB : - numComponents_ret == 4 ? GL_RGBA : (GLenum)-1; + numComponents_ret == 2 ? GL_LUMINANCE_ALPHA : + numComponents_ret == 3 ? GL_RGB : + numComponents_ret == 4 ? GL_RGBA : (GLenum)-1; unsigned int dataType = GL_UNSIGNED_BYTE; osg::Image* pOsgImage = new osg::Image; pOsgImage->setFileName(fileName.c_str()); - pOsgImage->setImage(s,t,r, - internalFormat, - pixelFormat, - dataType, - imageData); + pOsgImage->setImage(s,t,r, + internalFormat, + pixelFormat, + dataType, + imageData); return pOsgImage; @@ -345,4 +364,4 @@ class ReaderWriterGIF : public osg::ReaderWriter // now register with Registry to instantiate the above // reader/writer. -osg::RegisterReaderWriterProxy g_readerWriter_GIF_Proxy; +osgDB::RegisterReaderWriterProxy g_readerWriter_GIF_Proxy; diff --git a/src/osgPlugins/jpeg/Makefile b/src/osgPlugins/jpeg/Makefile index d8691dc1a..736afff13 100644 --- a/src/osgPlugins/jpeg/Makefile +++ b/src/osgPlugins/jpeg/Makefile @@ -4,13 +4,13 @@ include ../../../Make/makedefs C++FILES = \ ReaderWriterJPEG.cpp\ -LIB = ../../../lib/osgPlugins/osgdb_jpg.so +LIB = ../../../lib/osgPlugins/osgdb_jpeg.so -TARGET_LOADER_FILES = osgPlugins/osgdb_jpg.so +TARGET_LOADER_FILES = osgPlugins/osgdb_jpeg.so -LIBS = -ljpeg +LIBS = -ljpeg C++FLAGS += -I. -I../../../include -LDFLAGS += -L../../../lib +LDFLAGS += -L../../../lib $(FREEBSD_LOCALLIBS) include ../../../Make/makerules diff --git a/src/osgPlugins/jpeg/ReaderWriterJPEG.cpp b/src/osgPlugins/jpeg/ReaderWriterJPEG.cpp index ca3a34754..56f6a7cbb 100644 --- a/src/osgPlugins/jpeg/ReaderWriterJPEG.cpp +++ b/src/osgPlugins/jpeg/ReaderWriterJPEG.cpp @@ -1,28 +1,25 @@ #include -#include -#include -#include #include -#include #include - #include +#include +#include /**************************************************************************** * * Follows is code extracted from the simage library. Original Authors: * - * Systems in Motion, + * Systems in Motion, * - * + * * Peder Blekken * Morten Eriksen - * Marius Bugge Monsen + * Marius Bugge Monsen * - * The original COPYING notice + * The original COPYING notice * - * All files in this library are public domain, except simage_rgb.cpp which is + * All files in this library are public domain, except simage_rgb.cpp which is * Copyright (c) Mark J Kilgard . I will contact Mark * very soon to hear if this source also can become public domain. * @@ -45,8 +42,9 @@ #include -extern "C" { -#include +extern "C" +{ + #include }; #include @@ -64,250 +62,250 @@ static int jpegerror = ERR_NO_ERROR; int simage_jpeg_error(char * buffer, int buflen) { - switch (jpegerror) { - case ERR_OPEN: - strncpy(buffer, "JPEG loader: Error opening file", buflen); - break; - case ERR_MEM: - strncpy(buffer, "JPEG loader: Out of memory error", buflen); - break; - case ERR_JPEGLIB: - strncpy(buffer, "JPEG loader: Illegal jpeg file", buflen); - break; - } - return jpegerror; + switch (jpegerror) + { + case ERR_OPEN: + strncpy(buffer, "JPEG loader: Error opening file", buflen); + break; + case ERR_MEM: + strncpy(buffer, "JPEG loader: Out of memory error", buflen); + break; + case ERR_JPEGLIB: + strncpy(buffer, "JPEG loader: Illegal jpeg file", buflen); + break; + } + return jpegerror; } -struct my_error_mgr { - struct jpeg_error_mgr pub; /* "public" fields */ - jmp_buf setjmp_buffer; /* for return to caller */ +struct my_error_mgr +{ + struct jpeg_error_mgr pub; /* "public" fields */ + + jmp_buf setjmp_buffer; /* for return to caller */ }; - typedef struct my_error_mgr * my_error_ptr; -static void +static void my_error_exit (j_common_ptr cinfo) { - /* cinfo->err really points to a my_error_mgr struct, so coerce pointer */ - my_error_ptr myerr = (my_error_ptr) cinfo->err; + /* cinfo->err really points to a my_error_mgr struct, so coerce pointer */ + my_error_ptr myerr = (my_error_ptr) cinfo->err; - /* Always display the message. */ - /* We could postpone this until after returning, if we chose. */ - /*(*cinfo->err->output_message) (cinfo);*/ + /* Always display the message. */ + /* We could postpone this until after returning, if we chose. */ + /*(*cinfo->err->output_message) (cinfo);*/ - /* FIXME: get error messahe from jpeglib */ + /* FIXME: get error messahe from jpeglib */ - /* Return control to the setjmp point */ - longjmp(myerr->setjmp_buffer, 1); + /* Return control to the setjmp point */ + longjmp(myerr->setjmp_buffer, 1); } -int -simage_jpeg_identify(const char * ptr, - const unsigned char *header, - int headerlen) + +int +simage_jpeg_identify(const char *, +const unsigned char *header, +int headerlen) { - static unsigned char jpgcmp[] = {'J', 'F', 'I', 'F' }; - if (headerlen < 4) return 0; - if (memcmp((const void*)&header[6], - (const void*)jpgcmp, 4) == 0) return 1; - return 0; + static unsigned char jpgcmp[] = {'J', 'F', 'I', 'F' }; + if (headerlen < 4) return 0; + if (memcmp((const void*)&header[6], + (const void*)jpgcmp, 4) == 0) return 1; + return 0; } static unsigned char* copyScanline(unsigned char *currPtr, unsigned char *from, int cnt) { - memcpy((void*)currPtr, (void*)from, cnt); - currPtr -= cnt; - return currPtr; + memcpy((void*)currPtr, (void*)from, cnt); + currPtr -= cnt; + return currPtr; } - + unsigned char * simage_jpeg_load(const char *filename, - int *width_ret, - int *height_ret, - int *numComponents_ret) +int *width_ret, +int *height_ret, +int *numComponents_ret) { - int width; - int height; - unsigned char *currPtr; - int format; - unsigned char *buffer; - /* This struct contains the JPEG decompression parameters and pointers to - * working space (which is allocated as needed by the JPEG library). - */ - struct jpeg_decompress_struct cinfo; - /* We use our private extension JPEG error handler. - * Note that this struct must live as long as the main JPEG parameter - * struct, to avoid dangling-pointer problems. - */ - struct my_error_mgr jerr; - /* More stuff */ - FILE * infile; /* source file */ - JSAMPARRAY rowbuffer; /* Output row buffer */ - int row_stride; /* physical row width in output buffer */ - - jpegerror = ERR_NO_ERROR; - - /* In this example we want to open the input file before doing anything else, - * so that the setjmp() error recovery below can assume the file is open. - * VERY IMPORTANT: use "b" option to fopen() if you are on a machine that - * requires it in order to read binary files. - */ - - if ((infile = fopen(filename, "rb")) == NULL) { - jpegerror = ERR_OPEN; - return NULL; - } - - /* Step 1: allocate and initialize JPEG decompression object */ - - buffer = NULL; - - /* We set up the normal JPEG error routines, then override error_exit. */ - cinfo.err = jpeg_std_error(&jerr.pub); - jerr.pub.error_exit = my_error_exit; - /* Establish the setjmp return context for my_error_exit to use. */ - if (setjmp(jerr.setjmp_buffer)) { - /* If we get here, the JPEG code has signaled an error. - * We need to clean up the JPEG object, close the input file, and return. + int width; + int height; + unsigned char *currPtr; + int format; + unsigned char *buffer; + /* This struct contains the JPEG decompression parameters and pointers to + * working space (which is allocated as needed by the JPEG library). */ - jpegerror = ERR_JPEGLIB; - jpeg_destroy_decompress(&cinfo); - fclose(infile); - if (buffer) free(buffer); - return NULL; - } - /* Now we can initialize the JPEG decompression object. */ - jpeg_create_decompress(&cinfo); + struct jpeg_decompress_struct cinfo; + /* We use our private extension JPEG error handler. + * Note that this struct must live as long as the main JPEG parameter + * struct, to avoid dangling-pointer problems. + */ + struct my_error_mgr jerr; + /* More stuff */ + FILE * infile; /* source file */ + JSAMPARRAY rowbuffer; /* Output row buffer */ + int row_stride; /* physical row width in output buffer */ - /* Step 2: specify data source (eg, a file) */ + jpegerror = ERR_NO_ERROR; - jpeg_stdio_src(&cinfo, infile); + /* In this example we want to open the input file before doing anything else, + * so that the setjmp() error recovery below can assume the file is open. + * VERY IMPORTANT: use "b" option to fopen() if you are on a machine that + * requires it in order to read binary files. + */ - /* Step 3: read file parameters with jpeg_read_header() */ - - (void) jpeg_read_header(&cinfo, TRUE); - /* We can ignore the return value from jpeg_read_header since - * (a) suspension is not possible with the stdio data source, and - * (b) we passed TRUE to reject a tables-only JPEG file as an error. - * See libjpeg.doc for more info. - */ - - /* Step 4: set parameters for decompression */ - /* In this example, we don't need to change any of the defaults set by - * jpeg_read_header(), so we do nothing here. - */ - - /* Step 5: Start decompressor */ - if (cinfo.jpeg_color_space == JCS_GRAYSCALE) { - format = 1; - cinfo.out_color_space = JCS_GRAYSCALE; - } - else { /* use rgb */ - format = 3; - cinfo.out_color_space = JCS_RGB; - } - - (void) jpeg_start_decompress(&cinfo); - /* We can ignore the return value since suspension is not possible - * with the stdio data source. - */ - - /* We may need to do some setup of our own at this point before reading - * the data. After jpeg_start_decompress() we have the correct scaled - * output image dimensions available, as well as the output colormap - * if we asked for color quantization. - * In this example, we need to make an output work buffer of the right size. - */ - /* JSAMPLEs per row in output buffer */ - row_stride = cinfo.output_width * cinfo.output_components; - /* Make a one-row-high sample array that will go away when done with image */ - rowbuffer = (*cinfo.mem->alloc_sarray) - ((j_common_ptr) &cinfo, JPOOL_IMAGE, row_stride, 1); - width = cinfo.output_width; - height = cinfo.output_height; - buffer = currPtr = (unsigned char*) - malloc(width*height*cinfo.output_components); - - /* Step 6: while (scan lines remain to be read) */ - /* jpeg_read_scanlines(...); */ - - /* Here we use the library's state variable cinfo.output_scanline as the - * loop counter, so that we don't have to keep track ourselves. - */ - - /* flip image upside down */ - if (buffer) { - currPtr = buffer + row_stride * (cinfo.output_height-1); - - while (cinfo.output_scanline < cinfo.output_height) { - /* jpeg_read_scanlines expects an array of pointers to scanlines. - * Here the array is only one element long, but you could ask for - * more than one scanline at a time if that's more convenient. - */ - (void) jpeg_read_scanlines(&cinfo, rowbuffer, 1); - /* Assume put_scanline_someplace wants a pointer and sample count. */ - currPtr = copyScanline(currPtr, rowbuffer[0], row_stride); + if ((infile = fopen(filename, "rb")) == NULL) + { + jpegerror = ERR_OPEN; + return NULL; } - } - /* Step 7: Finish decompression */ - (void) jpeg_finish_decompress(&cinfo); - /* We can ignore the return value since suspension is not possible - * with the stdio data source. - */ + /* Step 1: allocate and initialize JPEG decompression object */ - /* Step 8: Release JPEG decompression object */ + buffer = NULL; - /* This is an important step since it will release a good deal of memory. */ - jpeg_destroy_decompress(&cinfo); + /* We set up the normal JPEG error routines, then override error_exit. */ + cinfo.err = jpeg_std_error(&jerr.pub); + jerr.pub.error_exit = my_error_exit; + /* Establish the setjmp return context for my_error_exit to use. */ + if (setjmp(jerr.setjmp_buffer)) + { + /* If we get here, the JPEG code has signaled an error. + * We need to clean up the JPEG object, close the input file, and return. + */ + jpegerror = ERR_JPEGLIB; + jpeg_destroy_decompress(&cinfo); + fclose(infile); + if (buffer) free(buffer); + return NULL; + } + /* Now we can initialize the JPEG decompression object. */ + jpeg_create_decompress(&cinfo); - /* After finish_decompress, we can close the input file. - * Here we postpone it until after no more JPEG errors are possible, - * so as to simplify the setjmp error logic above. (Actually, I don't - * think that jpeg_destroy can do an error exit, but why assume anything...) - */ - fclose(infile); + /* Step 2: specify data source (eg, a file) */ - /* At this point you may want to check to see whether any corrupt-data - * warnings occurred (test whether jerr.pub.num_warnings is nonzero). - */ + jpeg_stdio_src(&cinfo, infile); - /* And we're done! */ - if (buffer) { - *width_ret = width; - *height_ret = height; - *numComponents_ret = format; - } - else { - jpegerror = ERR_MEM; - } - return buffer; + /* Step 3: read file parameters with jpeg_read_header() */ + + (void) jpeg_read_header(&cinfo, TRUE); + /* We can ignore the return value from jpeg_read_header since + * (a) suspension is not possible with the stdio data source, and + * (b) we passed TRUE to reject a tables-only JPEG file as an error. + * See libjpeg.doc for more info. + */ + + /* Step 4: set parameters for decompression */ + /* In this example, we don't need to change any of the defaults set by + * jpeg_read_header(), so we do nothing here. + */ + + /* Step 5: Start decompressor */ + if (cinfo.jpeg_color_space == JCS_GRAYSCALE) + { + format = 1; + cinfo.out_color_space = JCS_GRAYSCALE; + } + else /* use rgb */ + { + format = 3; + cinfo.out_color_space = JCS_RGB; + } + + (void) jpeg_start_decompress(&cinfo); + /* We can ignore the return value since suspension is not possible + * with the stdio data source. + */ + + /* We may need to do some setup of our own at this point before reading + * the data. After jpeg_start_decompress() we have the correct scaled + * output image dimensions available, as well as the output colormap + * if we asked for color quantization. + * In this example, we need to make an output work buffer of the right size. + */ + /* JSAMPLEs per row in output buffer */ + row_stride = cinfo.output_width * cinfo.output_components; + /* Make a one-row-high sample array that will go away when done with image */ + rowbuffer = (*cinfo.mem->alloc_sarray) + ((j_common_ptr) &cinfo, JPOOL_IMAGE, row_stride, 1); + width = cinfo.output_width; + height = cinfo.output_height; + buffer = currPtr = (unsigned char*) + malloc(width*height*cinfo.output_components); + + /* Step 6: while (scan lines remain to be read) */ + /* jpeg_read_scanlines(...); */ + + /* Here we use the library's state variable cinfo.output_scanline as the + * loop counter, so that we don't have to keep track ourselves. + */ + + /* flip image upside down */ + if (buffer) + { + currPtr = buffer + row_stride * (cinfo.output_height-1); + + while (cinfo.output_scanline < cinfo.output_height) + { + /* jpeg_read_scanlines expects an array of pointers to scanlines. + * Here the array is only one element long, but you could ask for + * more than one scanline at a time if that's more convenient. + */ + (void) jpeg_read_scanlines(&cinfo, rowbuffer, 1); + /* Assume put_scanline_someplace wants a pointer and sample count. */ + currPtr = copyScanline(currPtr, rowbuffer[0], row_stride); + } + } + /* Step 7: Finish decompression */ + + (void) jpeg_finish_decompress(&cinfo); + /* We can ignore the return value since suspension is not possible + * with the stdio data source. + */ + + /* Step 8: Release JPEG decompression object */ + + /* This is an important step since it will release a good deal of memory. */ + jpeg_destroy_decompress(&cinfo); + + /* After finish_decompress, we can close the input file. + * Here we postpone it until after no more JPEG errors are possible, + * so as to simplify the setjmp error logic above. (Actually, I don't + * think that jpeg_destroy can do an error exit, but why assume anything...) + */ + fclose(infile); + + /* At this point you may want to check to see whether any corrupt-data + * warnings occurred (test whether jerr.pub.num_warnings is nonzero). + */ + + /* And we're done! */ + if (buffer) + { + *width_ret = width; + *height_ret = height; + *numComponents_ret = format; + } + else + { + jpegerror = ERR_MEM; + } + return buffer; } -class ReaderWriterJPEG : public osg::ReaderWriter + +class ReaderWriterJPEG : public osgDB::ReaderWriter { public: virtual const char* className() { return "JPEG Image Reader"; } - virtual bool acceptsExtension(const std::string& extension) { return extension=="jpeg"; } - - virtual osg::Node* readNode(const std::string& fileName) + virtual bool acceptsExtension(const std::string& extension) { - osg::Image* image = readImage(fileName); - if (image) - { - osg::Geode* geode = osg::createGeodeForImage(image); - if (geode==NULL) image->unref(); - return geode; - } - else - { - return NULL; - } + return osgDB::equalCaseInsensitive(extension,"jpeg"); } virtual osg::Image* readImage(const std::string& fileName) @@ -319,7 +317,7 @@ class ReaderWriterJPEG : public osg::ReaderWriter int numComponents_ret; imageData = simage_jpeg_load(fileName.c_str(),&width_ret,&height_ret,&numComponents_ret); - + if (imageData==NULL) return NULL; int s = width_ret; @@ -330,19 +328,19 @@ class ReaderWriterJPEG : public osg::ReaderWriter unsigned int pixelFormat = numComponents_ret == 1 ? GL_LUMINANCE : - numComponents_ret == 2 ? GL_LUMINANCE_ALPHA : - numComponents_ret == 3 ? GL_RGB : - numComponents_ret == 4 ? GL_RGBA : (GLenum)-1; + numComponents_ret == 2 ? GL_LUMINANCE_ALPHA : + numComponents_ret == 3 ? GL_RGB : + numComponents_ret == 4 ? GL_RGBA : (GLenum)-1; unsigned int dataType = GL_UNSIGNED_BYTE; osg::Image* pOsgImage = new osg::Image; pOsgImage->setFileName(fileName.c_str()); - pOsgImage->setImage(s,t,r, - internalFormat, - pixelFormat, - dataType, - imageData); + pOsgImage->setImage(s,t,r, + internalFormat, + pixelFormat, + dataType, + imageData); return pOsgImage; @@ -351,4 +349,4 @@ class ReaderWriterJPEG : public osg::ReaderWriter // now register with Registry to instantiate the above // reader/writer. -osg::RegisterReaderWriterProxy g_readerWriter_JPEG_Proxy; +osgDB::RegisterReaderWriterProxy g_readerWriter_JPEG_Proxy; diff --git a/src/osgPlugins/lib3ds/AUTHORS b/src/osgPlugins/lib3ds/AUTHORS new file mode 100644 index 000000000..e252c1ea7 --- /dev/null +++ b/src/osgPlugins/lib3ds/AUTHORS @@ -0,0 +1 @@ +J.E. Hoffmann diff --git a/src/osgPlugins/lib3ds/Makedepend b/src/osgPlugins/lib3ds/Makedepend new file mode 100644 index 000000000..e69de29bb diff --git a/src/osgPlugins/lib3ds/Makefile b/src/osgPlugins/lib3ds/Makefile new file mode 100644 index 000000000..bf5fbe99a --- /dev/null +++ b/src/osgPlugins/lib3ds/Makefile @@ -0,0 +1,37 @@ +#!smake +include ../../../Make/makedefs + +C++FILES = \ + atmosphere.cpp \ + chunk.cpp \ + lib3ds_float.cpp \ + matrix.cpp \ + quat.cpp \ + tcb.cpp \ + viewport.cpp \ + background.cpp \ + ease.cpp \ + light.cpp \ + mesh.cpp \ + readwrite.cpp \ + tracks.cpp \ + camera.cpp \ + file.cpp \ + material.cpp \ + node.cpp \ + shadow.cpp \ + vector.cpp \ + ReaderWriter3DS.cpp\ + +LIB = ../../../lib/osgPlugins/osgdb_3ds.so + +TARGET_LOADER_FILES = osgPlugins/osgdb_3ds.so + +LIBS = +C++FLAGS += -I. -I../../../include +LDFLAGS += -L../../../lib + +include ../../../Make/makerules + + + diff --git a/src/osgPlugins/lib3ds/README b/src/osgPlugins/lib3ds/README new file mode 100644 index 000000000..1b11fb174 --- /dev/null +++ b/src/osgPlugins/lib3ds/README @@ -0,0 +1,25 @@ + +This 3ds loader is based on lib3ds, details below. ReaderWriter3DS.cpp is the +OSG code which adapts the library into a osg plugin. + +Robert Osfield, Feburary 2001. + +-- + +Lib3ds is a free alternative to Autodesk's 3DS File Toolkit for handling +3DS files It's main goal is to simplify the creation of 3DS import and +export filters. + +This project is not related in any form to Autodesk. The library is +based on unofficial information about the 3DS format found on the web. + +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 Lesser General Public +License for more details. + +The official Lib3ds Homepage can be found under: + http://lib3ds.sourceforge.net + +J.E. Hoffmann + diff --git a/src/osgPlugins/lib3ds/ReaderWriter3DS.cpp b/src/osgPlugins/lib3ds/ReaderWriter3DS.cpp new file mode 100644 index 000000000..0ffe0108f --- /dev/null +++ b/src/osgPlugins/lib3ds/ReaderWriter3DS.cpp @@ -0,0 +1,419 @@ +#include +#include +#include +#include +#include +#include +#include +#include + +#include +#include +#include +#include + +#include +#include +#include +#include + +#include +#include + +#include +#include + +class ReaderWriter3DS : public osgDB::ReaderWriter +{ + public: + + ReaderWriter3DS(); + + virtual const char* className() { return "3DS Auto Studio Reader"; } + virtual bool acceptsExtension(const std::string& extension) { return extension=="3ds"; } + + virtual osg::Node* readNode(const std::string& fileName); + + typedef std::vector FaceList; + typedef std::map GeoStateMap; + + protected: + + osg::Texture* createTexture(Lib3dsTextureMap *texture,const char* label,bool& transparancy); + osg::StateSet* createStateSet(Lib3dsMaterial *materials); + osg::GeoSet* createGeoSet(Lib3dsMesh *meshes,FaceList& faceList); + + std::string _directory; + bool _useSmoothingGroups; + bool _usePerVertexNormals; +}; + +// now register with Registry to instantiate the above +// reader/writer. +osgDB::RegisterReaderWriterProxy g_readerWriter_3DS_Proxy; + +ReaderWriter3DS::ReaderWriter3DS() +{ + _useSmoothingGroups = true; + _usePerVertexNormals = true; +} + + +osg::Node* ReaderWriter3DS::readNode(const std::string& fileName) +{ + + Lib3dsFile *f = lib3ds_open(fileName.c_str()); + if (f==NULL) return NULL; + + _directory = osgDB::getFilePath(fileName); + + osg::Group* group = new osg::Group; + group->setName(fileName); + + typedef std::map StateSetMap; + StateSetMap drawStateMap; + + for (Lib3dsMaterial *mat=f->materials; mat; mat=mat->next) + { + drawStateMap[mat->name] = createStateSet(mat); + } + + for (Lib3dsMesh *mesh=f->meshes; mesh; mesh=mesh->next) + { + + typedef std::vector FaceList; + typedef std::map MaterialFaceMap; + MaterialFaceMap materialFaceMap; + for (unsigned int i=0; ifaces; ++i) + { + materialFaceMap[mesh->faceL[i].material].push_back(i); + } + + if (materialFaceMap.empty()) + { + osg::notify(osg::NOTICE)<<"Warning : no triangles assigned to mesh '"<name<<"'"<setName(mesh->name); + + for(MaterialFaceMap::iterator itr=materialFaceMap.begin(); + itr!=materialFaceMap.end(); + ++itr) + { + FaceList& faceList = itr->second; + + if (_useSmoothingGroups) + { + + typedef std::map SmoothingFaceMap; + SmoothingFaceMap smoothingFaceMap; + for (FaceList::iterator flitr=faceList.begin(); + flitr!=faceList.end(); + ++flitr) + { + smoothingFaceMap[mesh->faceL[*flitr].smoothing].push_back(*flitr); + } + + for(SmoothingFaceMap::iterator sitr=smoothingFaceMap.begin(); + sitr!=smoothingFaceMap.end(); + ++sitr) + { + // each smoothing group to have its own geoset + // to ensure the vertices on adjacent groups + // don't get shared. + FaceList& smoothFaceMap = sitr->second; + + osg::GeoSet* geoset = createGeoSet(mesh,smoothFaceMap); + if (geoset) + { + geoset->setStateSet(drawStateMap[itr->first]); + geode->addDrawable(geoset); + } + } + } + else // ignore smoothing groups. + { + osg::GeoSet* geoset = createGeoSet(mesh,faceList); + if (geoset) + { + geoset->setStateSet(drawStateMap[itr->first]); + geode->addDrawable(geoset); + } + } + } + + group->addChild(geode); + + } + + } + + lib3ds_close(f); + + return group; +} + + +osg::Texture* ReaderWriter3DS::createTexture(Lib3dsTextureMap *texture,const char* label,bool& transparancy) +{ + if (texture && *(texture->name)) + { + std::string fileName = osgDB::findFileInDirectory(texture->name,_directory,true); + if (fileName.empty()) + { + osg::notify(osg::WARN) << "texture '"<name<<"' not found"<name<<"'"<flags<flags)&LIB3DS_DECALE)<flags)&LIB3DS_MIRROR)<flags)&LIB3DS_NEGATE)<flags)&LIB3DS_NO_TILE)<flags)&LIB3DS_SUMMED_AREA)<flags)&LIB3DS_ALPHA_SOURCE)<flags)&LIB3DS_TINT)<flags)&LIB3DS_IGNORE_ALPHA)<flags)&LIB3DS_RGB_TINT)<name<setImage(osg_image); + + // does the texture support transparancy? + transparancy = ((texture->flags)&LIB3DS_ALPHA_SOURCE)!=0; + + // what is the wrap mode of the texture. + osg::Texture::WrapMode wm = ((texture->flags)&LIB3DS_NO_TILE) ? + osg::Texture::CLAMP : wm=osg::Texture::REPEAT; + osg_texture->setWrap(osg::Texture::WRAP_S,wm); + osg_texture->setWrap(osg::Texture::WRAP_T,wm); + osg_texture->setWrap(osg::Texture::WRAP_R,wm); + // bilinear. + osg_texture->setFilter(osg::Texture::MIN_FILTER,osg::Texture::LINEAR_MIPMAP_NEAREST); + + return osg_texture; + } + else + return NULL; +} + + +osg::StateSet* ReaderWriter3DS::createStateSet(Lib3dsMaterial *mat) +{ + if (mat==NULL) return NULL; + + osg::StateSet* stateset = new osg::StateSet; + + osg::Material* material = new osg::Material; + + float transparency = mat->transparency; + float alpha = 1.0f-transparency; + + osg::Vec4 ambient(mat->ambient[0],mat->ambient[1],mat->ambient[2],alpha); + osg::Vec4 diffuse(mat->diffuse[0],mat->diffuse[1],mat->diffuse[2],alpha); + osg::Vec4 specular(mat->specular[0],mat->specular[1],mat->specular[2],alpha); + + float shininess = mat->shininess; + + material->setAmbient(osg::Material::FRONT_AND_BACK,ambient); + material->setDiffuse(osg::Material::FRONT_AND_BACK,diffuse); + material->setSpecular(osg::Material::FRONT_AND_BACK,specular); + material->setShininess(osg::Material::FRONT_AND_BACK,shininess); + + stateset->setAttribute(material); + + bool decal = false; + bool textureTransparancy=false; + osg::Texture* texture1_map = createTexture(&(mat->texture1_map),"texture1_map",textureTransparancy); + if (texture1_map) + { + stateset->setAttributeAndModes(texture1_map,osg::StateAttribute::ON); + + // not sure exactly how to interpret what is best for .3ds + // but the default text env MODULATE doesn't work well, and + // DECAL seems to work better. + osg::TexEnv* texenv = new osg::TexEnv; + if (decal) + { + texenv->setMode(osg::TexEnv::DECAL); + } + else + { + texenv->setMode(osg::TexEnv::MODULATE); + } + + stateset->setAttribute(texenv); + } + + if (transparency>0.0f || textureTransparancy) + { + stateset->setMode(GL_BLEND,osg::StateAttribute::ON); + stateset->setRenderingHint(osg::StateSet::TRANSPARENT_BIN); + } + +/* + osg::ref_ptr texture1_mask = createTexture(&(mat->texture1_mask),"texture1_mask",textureTransparancy); + osg::ref_ptr texture2_map = createTexture(&(mat->texture2_map),"texture2_map",textureTransparancy); + osg::ref_ptr texture2_mask = createTexture(&(mat->texture2_mask),"texture2_mask",textureTransparancy); + osg::ref_ptr opacity_map = createTexture(&(mat->opacity_map),"opacity_map",textureTransparancy); + osg::ref_ptr opacity_mask = createTexture(&(mat->opacity_mask),"opacity_mask",textureTransparancy); + osg::ref_ptr bump_map = createTexture(&(mat->bump_map),"bump_map",textureTransparancy); + osg::ref_ptr bump_mask = createTexture(&(mat->bump_mask),"bump_mask",textureTransparancy); + osg::ref_ptr specular_map = createTexture(&(mat->specular_map),"specular_map",textureTransparancy); + osg::ref_ptr specular_mask = createTexture(&(mat->specular_mask),"specular_mask",textureTransparancy); + osg::ref_ptr shininess_map = createTexture(&(mat->shininess_map),"shininess_map",textureTransparancy); + osg::ref_ptr shininess_mask = createTexture(&(mat->shininess_mask),"shininess_mask",textureTransparancy); + osg::ref_ptr self_illum_map = createTexture(&(mat->self_illum_map),"self_illum_map",textureTransparancy); + osg::ref_ptr self_illum_mask = createTexture(&(mat->self_illum_mask),"self_illum_mask",textureTransparancy); + osg::ref_ptr reflection_map = createTexture(&(mat->reflection_map),"reflection_map",textureTransparancy); + osg::ref_ptr reflection_mask = createTexture(&(mat->reflection_mask),"reflection_mask",textureTransparancy); +*/ + return stateset; +} + + +osg::GeoSet* ReaderWriter3DS::createGeoSet(Lib3dsMesh *m,FaceList& faceList) +{ + + osg::GeoSet* geoset = new osg::GeoSet; + + unsigned int i; + + std::vector orig2NewMapping; + for(i=0;ipoints;++i) orig2NewMapping.push_back(-1); + + unsigned int noVertex=0; + FaceList::iterator fitr; + for (fitr=faceList.begin(); + fitr!=faceList.end(); + ++fitr) + { + + Lib3dsFace& face = m->faceL[*fitr]; + + if (orig2NewMapping[face.points[0]]<0) + orig2NewMapping[face.points[0]] = noVertex++; + + if (orig2NewMapping[face.points[1]]<0) + orig2NewMapping[face.points[1]] = noVertex++; + + if (orig2NewMapping[face.points[2]]<0) + orig2NewMapping[face.points[2]] = noVertex++; + + } + + osg::Vec3* osg_coords = new osg::Vec3[noVertex]; + for (i=0; ipoints; ++i) + { + // lib3ds_vector_transform(pos, m->matrix, m->pointL[i].pos); + if (orig2NewMapping[i]>=0) osg_coords[orig2NewMapping[i]].set(m->pointL[i].pos[0],m->pointL[i].pos[1],m->pointL[i].pos[2]); + } + + osg::Vec2* osg_tcoords = NULL; + if (m->texels>0) + { + if (m->texels==m->points) + { + osg_tcoords = new osg::Vec2[noVertex]; + for (i=0; itexels; ++i) + { + if (orig2NewMapping[i]>=0) osg_tcoords[orig2NewMapping[i]].set(m->texelL[i][0],m->texelL[i][1]); + } + } + else + { + osg::notify(osg::WARN)<<"Warning: in 3ds loader m->texels ("<texels<<") != m->points ("<points<<")"<faceL[*fitr]; + + *(index_ptr++) = orig2NewMapping[face.points[0]]; + *(index_ptr++) = orig2NewMapping[face.points[1]]; + *(index_ptr++) = orig2NewMapping[face.points[2]]; + + if (_usePerVertexNormals) + { + osg_normals[orig2NewMapping[face.points[0]]] += osg::Vec3(face.normal[0],face.normal[1],face.normal[2]);; + osg_normals[orig2NewMapping[face.points[1]]] += osg::Vec3(face.normal[0],face.normal[1],face.normal[2]);; + osg_normals[orig2NewMapping[face.points[2]]] += osg::Vec3(face.normal[0],face.normal[1],face.normal[2]);; + } + else + { + *(normal_ptr++) = osg::Vec3(face.normal[0],face.normal[1],face.normal[2]); + } + + } + + if (_usePerVertexNormals) + { + // normalize the normal list to unit length normals. + for (i=0; isetNormals(osg_normals,osg_indices); + geoset->setNormalBinding(osg::GeoSet::BIND_PERVERTEX); + + } + else + { + geoset->setNormals(osg_normals); + geoset->setNormalBinding(osg::GeoSet::BIND_PERPRIM); + } + + + geoset->setCoords(osg_coords,osg_indices); + if (osg_tcoords) + { + geoset->setTextureBinding(osg::GeoSet::BIND_PERVERTEX); + geoset->setTextureCoords(osg_tcoords,osg_indices); + } + + geoset->setPrimType(osg::GeoSet::TRIANGLES); + geoset->setNumPrims(faceList.size()); + + return geoset; +} diff --git a/src/osgPlugins/lib3ds/atmosphere.cpp b/src/osgPlugins/lib3ds/atmosphere.cpp new file mode 100644 index 000000000..b4586bd6a --- /dev/null +++ b/src/osgPlugins/lib3ds/atmosphere.cpp @@ -0,0 +1,324 @@ +/* + * The 3D Studio File Format Library + * Copyright (C) 1996-2001 by J.E. Hoffmann + * All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or (at + * your option) any later version. + * + * 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 Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + * + * $Id$ + */ +#define LIB3DS_EXPORT +#include +#include +#include + +/*! + * \defgroup atmosphere Atmosphere Settings + * + * \author J.E. Hoffmann + */ + +static Lib3dsBool +fog_read(Lib3dsFog *fog, FILE *f) +{ + Lib3dsChunk c; + Lib3dsWord chunk; + + if (!lib3ds_chunk_read_start(&c, LIB3DS_FOG, f)) + { + return(LIB3DS_FALSE); + } + fog->near_plane=lib3ds_float_read(f); + fog->near_density=lib3ds_float_read(f); + fog->far_plane=lib3ds_float_read(f); + fog->far_density=lib3ds_float_read(f); + lib3ds_chunk_read_tell(&c, f); + + while ((chunk=lib3ds_chunk_read_next(&c, f))!=0) + { + switch (chunk) + { + case LIB3DS_LIN_COLOR_F: + { + int i; + for (i=0; i<3; ++i) + { + fog->col[i]=lib3ds_float_read(f); + } + } + break; + case LIB3DS_COLOR_F: + break; + case LIB3DS_FOG_BGND: + { + fog->fog_background=LIB3DS_TRUE; + } + break; + default: + lib3ds_chunk_unknown(chunk); + } + } + + lib3ds_chunk_read_end(&c, f); + return(LIB3DS_TRUE); +} + + +static Lib3dsBool +layer_fog_read(Lib3dsLayerFog *fog, FILE *f) +{ + Lib3dsChunk c; + Lib3dsWord chunk; + //Lib3dsBool have_lin=LIB3DS_FALSE; + + if (!lib3ds_chunk_read_start(&c, LIB3DS_LAYER_FOG, f)) + { + return(LIB3DS_FALSE); + } + fog->near_y=lib3ds_float_read(f); + fog->far_y=lib3ds_float_read(f); + fog->density=lib3ds_float_read(f); + fog->flags=lib3ds_dword_read(f); + lib3ds_chunk_read_tell(&c, f); + + while ((chunk=lib3ds_chunk_read_next(&c, f))!=0) + { + switch (chunk) + { + case LIB3DS_LIN_COLOR_F: + lib3ds_rgb_read(fog->col,f); + //have_lin=LIB3DS_TRUE; + break; + case LIB3DS_COLOR_F: + lib3ds_rgb_read(fog->col,f); + break; + default: + lib3ds_chunk_unknown(chunk); + } + } + + lib3ds_chunk_read_end(&c, f); + return(LIB3DS_TRUE); +} + + +static Lib3dsBool +distance_cue_read(Lib3dsDistanceCue *cue, FILE *f) +{ + Lib3dsChunk c; + Lib3dsWord chunk; + + if (!lib3ds_chunk_read_start(&c, LIB3DS_DISTANCE_CUE, f)) + { + return(LIB3DS_FALSE); + } + cue->near_plane=lib3ds_float_read(f); + cue->near_dimming=lib3ds_float_read(f); + cue->far_plane=lib3ds_float_read(f); + cue->far_dimming=lib3ds_float_read(f); + lib3ds_chunk_read_tell(&c, f); + + while ((chunk=lib3ds_chunk_read_next(&c, f))!=0) + { + switch (chunk) + { + case LIB3DS_DCUE_BGND: + { + cue->cue_background=LIB3DS_TRUE; + } + break; + default: + lib3ds_chunk_unknown(chunk); + } + } + + lib3ds_chunk_read_end(&c, f); + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup atmosphere + */ +Lib3dsBool +lib3ds_atmosphere_read(Lib3dsAtmosphere *atmosphere, FILE *f) +{ + Lib3dsChunk c; + + if (!lib3ds_chunk_read(&c, f)) + { + return(LIB3DS_FALSE); + } + + switch (c.chunk) + { + case LIB3DS_FOG: + { + lib3ds_chunk_read_reset(&c, f); + if (!fog_read(&atmosphere->fog, f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_LAYER_FOG: + { + lib3ds_chunk_read_reset(&c, f); + if (!layer_fog_read(&atmosphere->layer_fog, f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_DISTANCE_CUE: + { + lib3ds_chunk_read_reset(&c, f); + if (!distance_cue_read(&atmosphere->dist_cue, f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_USE_FOG: + { + atmosphere->fog.use=LIB3DS_TRUE; + } + break; + case LIB3DS_USE_LAYER_FOG: + { + atmosphere->fog.use=LIB3DS_TRUE; + } + break; + case LIB3DS_USE_DISTANCE_CUE: + { + atmosphere->dist_cue.use=LIB3DS_TRUE; + } + break; + } + + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup atmosphere + */ +Lib3dsBool +lib3ds_atmosphere_write(Lib3dsAtmosphere *atmosphere, FILE *f) +{ + { /*---- LIB3DS_FOG ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_FOG; + if (!lib3ds_chunk_write_start(&c,f)) + { + return(LIB3DS_FALSE); + } + lib3ds_float_write(atmosphere->fog.near_plane,f); + lib3ds_float_write(atmosphere->fog.near_density,f); + lib3ds_float_write(atmosphere->fog.far_plane,f); + lib3ds_float_write(atmosphere->fog.far_density,f); + { + Lib3dsChunk c; + c.chunk=LIB3DS_FOG_BGND; + c.size=18; + lib3ds_chunk_write(&c,f); + lib3ds_rgb_write(atmosphere->fog.col,f); + } + if (atmosphere->fog.fog_background) + { + Lib3dsChunk c; + c.chunk=LIB3DS_COLOR_F; + c.size=6; + lib3ds_chunk_write(&c,f); + } + if (!lib3ds_chunk_write_end(&c,f)) + { + return(LIB3DS_FALSE); + } + } + { /*---- LIB3DS_LAYER_FOG ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_LAYER_FOG; + c.size=40; + lib3ds_chunk_write(&c,f); + lib3ds_float_write(atmosphere->layer_fog.near_y,f); + lib3ds_float_write(atmosphere->layer_fog.far_y,f); + lib3ds_float_write(atmosphere->layer_fog.near_y,f); + lib3ds_dword_write(atmosphere->layer_fog.flags,f); + { + Lib3dsChunk c; + c.chunk=LIB3DS_COLOR_F; + c.size=18; + lib3ds_chunk_write(&c,f); + lib3ds_rgb_write(atmosphere->fog.col,f); + } + } + { /*---- LIB3DS_DISTANCE_CUE ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_DISTANCE_CUE; + if (!lib3ds_chunk_write_start(&c,f)) + { + return(LIB3DS_FALSE); + } + lib3ds_float_write(atmosphere->dist_cue.near_plane,f); + lib3ds_float_write(atmosphere->dist_cue.near_dimming,f); + lib3ds_float_write(atmosphere->dist_cue.far_plane,f); + lib3ds_float_write(atmosphere->dist_cue.far_dimming,f); + if (atmosphere->dist_cue.cue_background) + { + Lib3dsChunk c; + c.chunk=LIB3DS_DCUE_BGND; + c.size=6; + lib3ds_chunk_write(&c,f); + } + if (!lib3ds_chunk_write_end(&c,f)) + { + return(LIB3DS_FALSE); + } + } + if (atmosphere->fog.use) /*---- LIB3DS_USE_FOG ----*/ + { + Lib3dsChunk c; + c.chunk=LIB3DS_USE_FOG; + c.size=6; + lib3ds_chunk_write(&c,f); + } + /*---- LIB3DS_USE_LAYER_FOG ----*/ + if (atmosphere->layer_fog.use) + { + Lib3dsChunk c; + c.chunk=LIB3DS_USE_LAYER_FOG; + c.size=6; + lib3ds_chunk_write(&c,f); + } + if (atmosphere->dist_cue.use)/*---- LIB3DS_USE_DISTANCE_CUE ----*/ + { + Lib3dsChunk c; + c.chunk=LIB3DS_USE_V_GRADIENT; + c.size=6; + lib3ds_chunk_write(&c,f); + } + + return(LIB3DS_TRUE); +} + + +/*! + +\typedef Lib3dsAtmosphere + \ingroup atmosphere + \sa _Lib3dsAtmosphere + +*/ diff --git a/src/osgPlugins/lib3ds/atmosphere.h b/src/osgPlugins/lib3ds/atmosphere.h new file mode 100644 index 000000000..ea438340b --- /dev/null +++ b/src/osgPlugins/lib3ds/atmosphere.h @@ -0,0 +1,100 @@ +/* -*- c -*- */ +#ifndef INCLUDED_LIB3DS_ATMOSPHERE_H +#define INCLUDED_LIB3DS_ATMOSPHERE_H +/* + * The 3D Studio File Format Library + * Copyright (C) 1996-2001 by J.E. Hoffmann + * All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or (at + * your option) any later version. + * + * 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 Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + * + * $Id$ + */ + +#ifndef INCLUDED_LIB3DS_TYPES_H +#include +#endif + +#ifdef __cplusplus +extern "C" { +#endif + +/*! + * Fog atmosphere settings + * \ingroup atmosphere + */ +typedef struct _Lib3dsFog { + Lib3dsBool use; + Lib3dsRgb col; + Lib3dsBool fog_background; + Lib3dsFloat near_plane; + Lib3dsFloat near_density; + Lib3dsFloat far_plane; + Lib3dsFloat far_density; +} Lib3dsFog; + +/*! + * Layer fog atmosphere flags + * \ingroup atmosphere + */ +typedef enum _Lib3dsLayerFogFlags { + LIB3DS_BOTTOM_FALL_OFF =0x00000001, + LIB3DS_TOP_FALL_OFF =0x00000002, + LIB3DS_FOG_BACKGROUND =0x00100000 +} Lib3dsLayerFogFlags; + +/*! + * Layer fog atmosphere settings + * \ingroup atmosphere + */ +typedef struct _Lib3dsLayerFog { + Lib3dsBool use; + Lib3dsDword flags; + Lib3dsRgb col; + Lib3dsFloat near_y; + Lib3dsFloat far_y; + Lib3dsFloat density; +} Lib3dsLayerFog; + +/*! + * Distance cue atmosphere settings + * \ingroup atmosphere + */ +typedef struct _Lib3dsDistanceCue { + Lib3dsBool use; + Lib3dsBool cue_background; + Lib3dsFloat near_plane; + Lib3dsFloat near_dimming; + Lib3dsFloat far_plane; + Lib3dsFloat far_dimming; +} Lib3dsDistanceCue; + +/*! + * Atmosphere settings + * \ingroup atmosphere + */ +struct _Lib3dsAtmosphere { + Lib3dsFog fog; + Lib3dsLayerFog layer_fog; + Lib3dsDistanceCue dist_cue; +}; + +extern LIB3DSAPI Lib3dsBool lib3ds_atmosphere_read(Lib3dsAtmosphere *atmosphere, FILE *f); +extern LIB3DSAPI Lib3dsBool lib3ds_atmosphere_write(Lib3dsAtmosphere *atmosphere, FILE *f); + +#ifdef __cplusplus +}; +#endif +#endif diff --git a/src/osgPlugins/lib3ds/background.cpp b/src/osgPlugins/lib3ds/background.cpp new file mode 100644 index 000000000..824261292 --- /dev/null +++ b/src/osgPlugins/lib3ds/background.cpp @@ -0,0 +1,257 @@ +/* + * The 3D Studio File Format Library + * Copyright (C) 1996-2001 by J.E. Hoffmann + * All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or (at + * your option) any later version. + * + * 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 Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + * + * $Id$ + */ +#define LIB3DS_EXPORT +#include +#include +#include +#include + +/*! + * \defgroup background Background Settings + * + * \author J.E. Hoffmann + */ + +static Lib3dsBool +solid_bgnd_read(Lib3dsBackground *background, FILE *f) +{ + Lib3dsChunk c; + Lib3dsWord chunk; + //Lib3dsBool have_lin=LIB3DS_FALSE; + + if (!lib3ds_chunk_read_start(&c, LIB3DS_SOLID_BGND, f)) + { + return(LIB3DS_FALSE); + } + + while ((chunk=lib3ds_chunk_read_next(&c, f))!=0) + { + switch (chunk) + { + case LIB3DS_LIN_COLOR_F: + lib3ds_rgb_read(background->solid.col, f); + //have_lin=LIB3DS_TRUE; + break; + case LIB3DS_COLOR_F: + lib3ds_rgb_read(background->solid.col, f); + break; + default: + lib3ds_chunk_unknown(chunk); + } + } + + lib3ds_chunk_read_end(&c, f); + return(LIB3DS_TRUE); +} + + +static Lib3dsBool +v_gradient_read(Lib3dsBackground *background, FILE *f) +{ + Lib3dsChunk c; + Lib3dsWord chunk; + int index[2]; + Lib3dsRgb col[2][3]; + int have_lin=0; + + if (!lib3ds_chunk_read_start(&c, LIB3DS_V_GRADIENT, f)) + { + return(LIB3DS_FALSE); + } + background->gradient.percent=lib3ds_float_read(f); + lib3ds_chunk_read_tell(&c, f); + + index[0]=index[1]=0; + while ((chunk=lib3ds_chunk_read_next(&c, f))!=0) + { + switch (chunk) + { + case LIB3DS_COLOR_F: + lib3ds_rgb_read(col[0][index[0]],f); + index[0]++; + break; + case LIB3DS_LIN_COLOR_F: + lib3ds_rgb_read(col[1][index[1]],f); + index[1]++; + have_lin=1; + break; + default: + lib3ds_chunk_unknown(chunk); + } + } + { + int i; + for (i=0; i<3; ++i) + { + background->gradient.top[i]=col[have_lin][0][i]; + background->gradient.middle[i]=col[have_lin][1][i]; + background->gradient.bottom[i]=col[have_lin][2][i]; + } + } + lib3ds_chunk_read_end(&c, f); + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup background + */ +Lib3dsBool +lib3ds_background_read(Lib3dsBackground *background, FILE *f) +{ + Lib3dsChunk c; + + if (!lib3ds_chunk_read(&c, f)) + { + return(LIB3DS_FALSE); + } + + switch (c.chunk) + { + case LIB3DS_BIT_MAP: + { + if (!lib3ds_string_read(background->bitmap.name, 64, f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_SOLID_BGND: + { + lib3ds_chunk_read_reset(&c, f); + if (!solid_bgnd_read(background, f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_V_GRADIENT: + { + lib3ds_chunk_read_reset(&c, f); + if (!v_gradient_read(background, f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_USE_BIT_MAP: + { + background->bitmap.use=LIB3DS_TRUE; + } + break; + case LIB3DS_USE_SOLID_BGND: + { + background->solid.use=LIB3DS_TRUE; + } + break; + case LIB3DS_USE_V_GRADIENT: + { + background->gradient.use=LIB3DS_TRUE; + } + break; + } + + return(LIB3DS_TRUE); +} + + +static Lib3dsBool +colorf_write(Lib3dsRgba rgb, FILE *f) +{ + Lib3dsChunk c; + + c.chunk=LIB3DS_COLOR_F; + c.size=18; + lib3ds_chunk_write(&c,f); + lib3ds_rgb_write(rgb,f); + + c.chunk=LIB3DS_LIN_COLOR_F; + c.size=18; + lib3ds_chunk_write(&c,f); + lib3ds_rgb_write(rgb,f); + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup background + */ +Lib3dsBool +lib3ds_background_write(Lib3dsBackground *background, FILE *f) +{ + { /*---- LIB3DS_BIT_MAP ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_BIT_MAP; + c.size=6+1+strlen(background->bitmap.name); + lib3ds_chunk_write(&c,f); + lib3ds_string_write(background->bitmap.name, f); + } + { /*---- LIB3DS_SOLID_BGND ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_SOLID_BGND; + c.size=42; + lib3ds_chunk_write(&c,f); + colorf_write(background->solid.col,f); + } + { /*---- LIB3DS_V_GRADIENT ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_V_GRADIENT; + c.size=118; + lib3ds_chunk_write(&c,f); + lib3ds_float_write(background->gradient.percent,f); + colorf_write(background->gradient.top,f); + colorf_write(background->gradient.middle,f); + colorf_write(background->gradient.bottom,f); + } + if (background->bitmap.use) /*---- LIB3DS_USE_BIT_MAP ----*/ + { + Lib3dsChunk c; + c.chunk=LIB3DS_USE_BIT_MAP; + c.size=6; + lib3ds_chunk_write(&c,f); + } + if (background->solid.use) /*---- LIB3DS_USE_SOLID_BGND ----*/ + { + Lib3dsChunk c; + c.chunk=LIB3DS_USE_SOLID_BGND; + c.size=6; + lib3ds_chunk_write(&c,f); + } + if (background->gradient.use)/*---- LIB3DS_USE_V_GRADIENT ----*/ + { + Lib3dsChunk c; + c.chunk=LIB3DS_USE_V_GRADIENT; + c.size=6; + lib3ds_chunk_write(&c,f); + } + + return(LIB3DS_TRUE); +} + + +/*! + +\typedef Lib3dsBackground + \ingroup background + \sa _Lib3dsBackground + +*/ diff --git a/src/osgPlugins/lib3ds/background.h b/src/osgPlugins/lib3ds/background.h new file mode 100644 index 000000000..489613659 --- /dev/null +++ b/src/osgPlugins/lib3ds/background.h @@ -0,0 +1,85 @@ +/* -*- c -*- */ +#ifndef INCLUDED_LIB3DS_BACKGROUND_H +#define INCLUDED_LIB3DS_BACKGROUND_H +/* + * The 3D Studio File Format Library + * Copyright (C) 1996-2001 by J.E. Hoffmann + * All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or (at + * your option) any later version. + * + * 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 Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + * + * $Id$ + */ + +#ifndef INCLUDED_LIB3DS_TYPES_H +#include +#endif + +#ifdef __cplusplus +extern "C" { +#endif + +/*! + * Bitmap background settings + * \ingroup background + */ +typedef struct _Lib3dsBitmap { + Lib3dsBool use; + char name[64]; +} Lib3dsBitmap; + +/*! + * Solid color background settings + * \ingroup background + */ +typedef struct _Lib3dsSolid { + Lib3dsBool use; + Lib3dsRgb col; +} Lib3dsSolid; + +/*! + * Gradient background settings + * \ingroup background + */ +typedef struct _Lib3dsGradient { + Lib3dsBool use; + Lib3dsFloat percent; + Lib3dsRgb top; + Lib3dsRgb middle; + Lib3dsRgb bottom; +} Lib3dsGradient; + +/*! + * Background settings + * \ingroup background + */ +struct _Lib3dsBackground { + Lib3dsBitmap bitmap; + Lib3dsSolid solid; + Lib3dsGradient gradient; +}; + +extern LIB3DSAPI Lib3dsBool lib3ds_background_read(Lib3dsBackground *background, FILE *f); +extern LIB3DSAPI Lib3dsBool lib3ds_background_write(Lib3dsBackground *background, FILE *f); + +#ifdef __cplusplus +}; +#endif +#endif + + + + + diff --git a/src/osgPlugins/lib3ds/camera.cpp b/src/osgPlugins/lib3ds/camera.cpp new file mode 100644 index 000000000..93830c8cd --- /dev/null +++ b/src/osgPlugins/lib3ds/camera.cpp @@ -0,0 +1,193 @@ +/* + * The 3D Studio File Format Library + * Copyright (C) 1996-2001 by J.E. Hoffmann + * All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or (at + * your option) any later version. + * + * 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 Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + * + * $Id$ + */ +#define LIB3DS_EXPORT +#include +#include +#include +#include +#include +#include +//#include +#ifdef WITH_DMALLOC +#include +#endif + +/*! + * \defgroup camera Cameras + * + * \author J.E. Hoffmann + */ + +/*! + * \ingroup camera + */ +Lib3dsCamera* +lib3ds_camera_new(const char *name) +{ + Lib3dsCamera *camera; + + ASSERT(name); + ASSERT(strlen(name)<64); + + camera=(Lib3dsCamera*)calloc(sizeof(Lib3dsCamera), 1); + if (!camera) + { + return(0); + } + strcpy(camera->name, name); + camera->fov=45.0f; + return(camera); +} + + +/*! + * \ingroup camera + */ +void +lib3ds_camera_free(Lib3dsCamera *camera) +{ + memset(camera, 0, sizeof(Lib3dsCamera)); + free(camera); +} + + +/*! + * \ingroup camera + */ +Lib3dsBool +lib3ds_camera_read(Lib3dsCamera *camera, FILE *f) +{ + Lib3dsChunk c; + Lib3dsWord chunk; + + if (!lib3ds_chunk_read_start(&c, LIB3DS_N_CAMERA, f)) + { + return(LIB3DS_FALSE); + } + { + int i; + for (i=0; i<3; ++i) + { + camera->position[i]=lib3ds_float_read(f); + } + for (i=0; i<3; ++i) + { + camera->target[i]=lib3ds_float_read(f); + } + } + camera->roll=lib3ds_float_read(f); + { + float s; + s=lib3ds_float_read(f); + if (fabs(s)fov=45.0; + } + else + { + camera->fov=2400.0f/s; + } + } + lib3ds_chunk_read_tell(&c, f); + + while ((chunk=lib3ds_chunk_read_next(&c, f))!=0) + { + switch (chunk) + { + case LIB3DS_CAM_SEE_CONE: + { + camera->see_cone=LIB3DS_TRUE; + } + break; + case LIB3DS_CAM_RANGES: + { + camera->near_range=lib3ds_float_read(f); + camera->far_range=lib3ds_float_read(f); + } + break; + default: + lib3ds_chunk_unknown(chunk); + } + } + + lib3ds_chunk_read_end(&c, f); + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup camera + */ +Lib3dsBool +lib3ds_camera_write(Lib3dsCamera *camera, FILE *f) +{ + Lib3dsChunk c; + + c.chunk=LIB3DS_N_CAMERA; + if (!lib3ds_chunk_write_start(&c,f)) + { + return(LIB3DS_FALSE); + } + + lib3ds_vector_write(camera->position, f); + lib3ds_vector_write(camera->target, f); + lib3ds_float_write(camera->roll, f); + if (fabs(camera->fov)fov, f); + } + + if (camera->see_cone) + { + Lib3dsChunk c; + c.chunk=LIB3DS_CAM_SEE_CONE; + c.size=6; + lib3ds_chunk_write(&c, f); + } + { + Lib3dsChunk c; + c.chunk=LIB3DS_CAM_RANGES; + c.size=14; + lib3ds_chunk_write(&c, f); + lib3ds_float_write(camera->near_range, f); + lib3ds_float_write(camera->far_range, f); + } + + if (!lib3ds_chunk_write_end(&c,f)) + { + return(LIB3DS_FALSE); + } + return(LIB3DS_TRUE); +} + + +/*! + +\typedef Lib3dsCamera + \ingroup camera + \sa _Lib3dsCamera + +*/ diff --git a/src/osgPlugins/lib3ds/camera.h b/src/osgPlugins/lib3ds/camera.h new file mode 100644 index 000000000..d0dfcb936 --- /dev/null +++ b/src/osgPlugins/lib3ds/camera.h @@ -0,0 +1,59 @@ +/* -*- c -*- */ +#ifndef INCLUDED_LIB3DS_CAMERA_H +#define INCLUDED_LIB3DS_CAMERA_H +/* + * The 3D Studio File Format Library + * Copyright (C) 1996-2001 by J.E. Hoffmann + * All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or (at + * your option) any later version. + * + * 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 Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + * + * $Id$ + */ + +#ifndef INCLUDED_LIB3DS_TYPES_H +#include +#endif + +#ifdef __cplusplus +extern "C" { +#endif + +/*! + * Camera object + * \ingroup camera + */ +struct _Lib3dsCamera { + Lib3dsCamera *next; + char name[64]; + Lib3dsVector position; + Lib3dsVector target; + Lib3dsFloat roll; + Lib3dsFloat fov; + Lib3dsBool see_cone; + Lib3dsFloat near_range; + Lib3dsFloat far_range; +}; + +extern LIB3DSAPI Lib3dsCamera* lib3ds_camera_new(const char *name); +extern LIB3DSAPI void lib3ds_camera_free(Lib3dsCamera *mesh); +extern LIB3DSAPI Lib3dsBool lib3ds_camera_read(Lib3dsCamera *camera, FILE *f); +extern LIB3DSAPI Lib3dsBool lib3ds_camera_write(Lib3dsCamera *camera, FILE *f); + +#ifdef __cplusplus +}; +#endif +#endif + diff --git a/src/osgPlugins/lib3ds/chunk.cpp b/src/osgPlugins/lib3ds/chunk.cpp new file mode 100644 index 000000000..4c398092a --- /dev/null +++ b/src/osgPlugins/lib3ds/chunk.cpp @@ -0,0 +1,292 @@ +/* + * The 3D Studio File Format Library + * Copyright (C) 1996-2001 by J.E. Hoffmann + * All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or (at + * your option) any later version. + * + * 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 Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + * + * $Id$ + */ +#define LIB3DS_EXPORT +#include +#include +#include +#include + +/*#define LIB3DS_CHUNK_DEBUG*/ +/*#define LIB3DS_CHUNK_WARNING*/ + +/*! + * \defgroup chunk Chunk Handling + * + * \author J.E. Hoffmann + */ + +static Lib3dsBool enable_dump=LIB3DS_FALSE; +static Lib3dsBool enable_unknown=LIB3DS_FALSE; +static char lib3ds_chunk_level[128]=""; + +static void + /*c*/ +lib3ds_chunk_debug_enter(Lib3dsChunk* ) +{ + strcat(lib3ds_chunk_level, " "); +} + + +static void + /*c*/ +lib3ds_chunk_debug_leave(Lib3dsChunk* ) +{ + lib3ds_chunk_level[strlen(lib3ds_chunk_level)-2]=0; +} + + +static void +lib3ds_chunk_debug_dump(Lib3dsChunk *c) +{ + if (enable_dump) + { + printf("%s%s (0x%X) size=%lu\n", + lib3ds_chunk_level, + lib3ds_chunk_name(c->chunk), + c->chunk, + c->size + ); + } +} + + +/*! + * \ingroup chunk + */ +void +lib3ds_chunk_enable_dump(Lib3dsBool enable, Lib3dsBool unknown) +{ + enable_dump=enable; + enable_unknown=unknown; +} + + +/*! + * \ingroup chunk + * + * Reads a 3d-Studio chunk header from a little endian file stream. + * + * \param c The chunk to store the data. + * \param f The file stream. + * + * \return True on success, False otherwise. + */ +Lib3dsBool +lib3ds_chunk_read(Lib3dsChunk *c, FILE *f) +{ + ASSERT(c); + ASSERT(f); + c->cur=ftell(f); + c->chunk=lib3ds_word_read(f); + c->size=lib3ds_dword_read(f); + c->end=c->cur+c->size; + c->cur+=6; + if (ferror(f) || (c->size<6)) + { + return(LIB3DS_FALSE); + } + return(LIB3DS_TRUE); + +} + + +/*! + * \ingroup chunk + */ +Lib3dsBool +lib3ds_chunk_read_start(Lib3dsChunk *c, Lib3dsWord chunk, FILE *f) +{ + ASSERT(c); + ASSERT(f); + if (!lib3ds_chunk_read(c, f)) + { + return(LIB3DS_FALSE); + } + lib3ds_chunk_debug_enter(c); + return((chunk==0) || (c->chunk==chunk)); +} + + +/*! + * \ingroup chunk + */ +void +lib3ds_chunk_read_tell(Lib3dsChunk *c, FILE *f) +{ + c->cur=ftell(f); +} + + +/*! + * \ingroup chunk + */ +Lib3dsWord +lib3ds_chunk_read_next(Lib3dsChunk *c, FILE *f) +{ + Lib3dsChunk d; + + if (c->cur>=c->end) + { + ASSERT(c->cur==c->end); + return(0); + } + + fseek(f, (long)c->cur, SEEK_SET); + d.chunk=lib3ds_word_read(f); + d.size=lib3ds_dword_read(f); + lib3ds_chunk_debug_dump(&d); + c->cur+=d.size; + return(d.chunk); +} + + +/*! + * \ingroup chunk + */ +void + /*c*/ +lib3ds_chunk_read_reset(Lib3dsChunk* , FILE *f) +{ + fseek(f, -6, SEEK_CUR); +} + + +/*! + * \ingroup chunk + */ +void +lib3ds_chunk_read_end(Lib3dsChunk *c, FILE *f) +{ + lib3ds_chunk_debug_leave(c); + fseek(f, c->end, SEEK_SET); +} + + +/*! + * \ingroup chunk + * + * Writes a 3d-Studio chunk header into a little endian file stream. + * + * \param c The chunk to be written. + * \param f The file stream. + * + * \return True on success, False otherwise. + */ +Lib3dsBool +lib3ds_chunk_write(Lib3dsChunk *c, FILE *f) +{ + ASSERT(c); + if (!lib3ds_word_write(c->chunk, f)) + { + LIB3DS_ERROR_LOG; + return(LIB3DS_FALSE); + } + if (!lib3ds_dword_write(c->size, f)) + { + LIB3DS_ERROR_LOG; + return(LIB3DS_FALSE); + } + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup chunk + */ +Lib3dsBool +lib3ds_chunk_write_start(Lib3dsChunk *c, FILE *f) +{ + ASSERT(c); + c->size=0; + c->cur=ftell(f); + if (!lib3ds_word_write(c->chunk, f)) + { + return(LIB3DS_FALSE); + } + if (!lib3ds_dword_write(c->size, f)) + { + return(LIB3DS_FALSE); + } + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup chunk + */ +Lib3dsBool +lib3ds_chunk_write_end(Lib3dsChunk *c, FILE *f) +{ + ASSERT(c); + c->size=ftell(f) - c->cur; + fseek(f, c->cur+2, SEEK_SET); + if (!lib3ds_dword_write(c->size, f)) + { + LIB3DS_ERROR_LOG; + return(LIB3DS_FALSE); + } + + c->cur+=c->size; + fseek(f, c->cur, SEEK_SET); + if (ferror(f)) + { + LIB3DS_ERROR_LOG; + return(LIB3DS_FALSE); + } + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup chunk + */ +const char* +lib3ds_chunk_name(Lib3dsWord chunk) +{ + Lib3dsChunkTable *p; + + for (p=lib3ds_chunk_table; p->name!=0; ++p) + { + if (p->chunk==chunk) + { + return(p->name); + } + } + return("***UNKNOWN***"); +} + + +/*! + * \ingroup chunk + */ +void +lib3ds_chunk_unknown(Lib3dsWord chunk) +{ + if (enable_unknown) + { + printf("%s***WARNING*** Unknown Chunk: %s (0x%X)\n", + lib3ds_chunk_level, + lib3ds_chunk_name(chunk), + chunk + ); + } +} diff --git a/src/osgPlugins/lib3ds/chunk.h b/src/osgPlugins/lib3ds/chunk.h new file mode 100644 index 000000000..dfd930a67 --- /dev/null +++ b/src/osgPlugins/lib3ds/chunk.h @@ -0,0 +1,287 @@ +/* -*- c -*- */ +#ifndef INCLUDED_LIB3DS_CHUNK_H +#define INCLUDED_LIB3DS_CHUNK_H +/* + * The 3D Studio File Format Library + * Copyright (C) 1996-2001 by J.E. Hoffmann + * All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or (at + * your option) any later version. + * + * 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 Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + * + * $Id$ + */ + +#ifndef INCLUDED_LIB3DS_TYPES_H +#include +#endif + +#ifdef __cplusplus +extern "C" { +#endif + +typedef enum _Lib3dsChunks { + LIB3DS_NULL_CHUNK =0x0000, + LIB3DS_M3DMAGIC =0x4D4D, /*3DS file*/ + LIB3DS_SMAGIC =0x2D2D, + LIB3DS_LMAGIC =0x2D3D, + LIB3DS_MLIBMAGIC =0x3DAA, /*MLI file*/ + LIB3DS_MATMAGIC =0x3DFF, + LIB3DS_CMAGIC =0xC23D, /*PRJ file*/ + LIB3DS_M3D_VERSION =0x0002, + LIB3DS_M3D_KFVERSION =0x0005, + + LIB3DS_COLOR_F =0x0010, + LIB3DS_COLOR_24 =0x0011, + LIB3DS_LIN_COLOR_24 =0x0012, + LIB3DS_LIN_COLOR_F =0x0013, + LIB3DS_INT_PERCENTAGE =0x0030, + LIB3DS_FLOAT_PERCENTAGE =0x0031, + + LIB3DS_MDATA =0x3D3D, + LIB3DS_MESH_VERSION =0x3D3E, + LIB3DS_MASTER_SCALE =0x0100, + LIB3DS_LO_SHADOW_BIAS =0x1400, + LIB3DS_HI_SHADOW_BIAS =0x1410, + LIB3DS_SHADOW_MAP_SIZE =0x1420, + LIB3DS_SHADOW_SAMPLES =0x1430, + LIB3DS_SHADOW_RANGE =0x1440, + LIB3DS_SHADOW_FILTER =0x1450, + LIB3DS_RAY_BIAS =0x1460, + LIB3DS_O_CONSTS =0x1500, + LIB3DS_AMBIENT_LIGHT =0x2100, + LIB3DS_BIT_MAP =0x1100, + LIB3DS_SOLID_BGND =0x1200, + LIB3DS_V_GRADIENT =0x1300, + LIB3DS_USE_BIT_MAP =0x1101, + LIB3DS_USE_SOLID_BGND =0x1201, + LIB3DS_USE_V_GRADIENT =0x1301, + LIB3DS_FOG =0x2200, + LIB3DS_FOG_BGND =0x2210, + LIB3DS_LAYER_FOG =0x2302, + LIB3DS_DISTANCE_CUE =0x2300, + LIB3DS_DCUE_BGND =0x2310, + LIB3DS_USE_FOG =0x2201, + LIB3DS_USE_LAYER_FOG =0x2303, + LIB3DS_USE_DISTANCE_CUE =0x2301, + + LIB3DS_MAT_ENTRY =0xAFFF, + LIB3DS_MAT_NAME =0xA000, + LIB3DS_MAT_AMBIENT =0xA010, + LIB3DS_MAT_DIFFUSE =0xA020, + LIB3DS_MAT_SPECULAR =0xA030, + LIB3DS_MAT_SHININESS =0xA040, + LIB3DS_MAT_SHIN2PCT =0xA041, + LIB3DS_MAT_TRANSPARENCY =0xA050, + LIB3DS_MAT_XPFALL =0xA052, + LIB3DS_MAT_USE_XPFALL =0xA240, + LIB3DS_MAT_REFBLUR =0xA053, + LIB3DS_MAT_SHADING =0xA100, + LIB3DS_MAT_USE_REFBLUR =0xA250, + LIB3DS_MAT_SELF_ILLUM =0xA080, + LIB3DS_MAT_TWO_SIDE =0xA081, + LIB3DS_MAT_DECAL =0xA082, + LIB3DS_MAT_ADDITIVE =0xA083, + LIB3DS_MAT_WIRE =0xA085, + LIB3DS_MAT_FACEMAP =0xA088, + LIB3DS_MAT_PHONGSOFT =0xA08C, + LIB3DS_MAT_WIREABS =0xA08E, + LIB3DS_MAT_WIRE_SIZE =0xA087, + LIB3DS_MAT_TEXMAP =0xA200, + LIB3DS_MAT_SXP_TEXT_DATA =0xA320, + LIB3DS_MAT_TEXMASK =0xA33E, + LIB3DS_MAT_SXP_TEXTMASK_DATA =0xA32A, + LIB3DS_MAT_TEX2MAP =0xA33A, + LIB3DS_MAT_SXP_TEXT2_DATA =0xA321, + LIB3DS_MAT_TEX2MASK =0xA340, + LIB3DS_MAT_SXP_TEXT2MASK_DATA =0xA32C, + LIB3DS_MAT_OPACMAP =0xA210, + LIB3DS_MAT_SXP_OPAC_DATA =0xA322, + LIB3DS_MAT_OPACMASK =0xA342, + LIB3DS_MAT_SXP_OPACMASK_DATA =0xA32E, + LIB3DS_MAT_BUMPMAP =0xA230, + LIB3DS_MAT_SXP_BUMP_DATA =0xA324, + LIB3DS_MAT_BUMPMASK =0xA344, + LIB3DS_MAT_SXP_BUMPMASK_DATA =0xA330, + LIB3DS_MAT_SPECMAP =0xA204, + LIB3DS_MAT_SXP_SPEC_DATA =0xA325, + LIB3DS_MAT_SPECMASK =0xA348, + LIB3DS_MAT_SXP_SPECMASK_DATA =0xA332, + LIB3DS_MAT_SHINMAP =0xA33C, + LIB3DS_MAT_SXP_SHIN_DATA =0xA326, + LIB3DS_MAT_SHINMASK =0xA346, + LIB3DS_MAT_SXP_SHINMASK_DATA =0xA334, + LIB3DS_MAT_SELFIMAP =0xA33D, + LIB3DS_MAT_SXP_SELFI_DATA =0xA328, + LIB3DS_MAT_SELFIMASK =0xA34A, + LIB3DS_MAT_SXP_SELFIMASK_DATA =0xA336, + LIB3DS_MAT_REFLMAP =0xA220, + LIB3DS_MAT_REFLMASK =0xA34C, + LIB3DS_MAT_SXP_REFLMASK_DATA =0xA338, + LIB3DS_MAT_ACUBIC =0xA310, + LIB3DS_MAT_MAPNAME =0xA300, + LIB3DS_MAT_MAP_TILING =0xA351, + LIB3DS_MAT_MAP_TEXBLUR =0xA353, + LIB3DS_MAT_MAP_USCALE =0xA354, + LIB3DS_MAT_MAP_VSCALE =0xA356, + LIB3DS_MAT_MAP_UOFFSET =0xA358, + LIB3DS_MAT_MAP_VOFFSET =0xA35A, + LIB3DS_MAT_MAP_ANG =0xA35C, + LIB3DS_MAT_MAP_COL1 =0xA360, + LIB3DS_MAT_MAP_COL2 =0xA362, + LIB3DS_MAT_MAP_RCOL =0xA364, + LIB3DS_MAT_MAP_GCOL =0xA366, + LIB3DS_MAT_MAP_BCOL =0xA368, + + LIB3DS_NAMED_OBJECT =0x4000, + LIB3DS_N_DIRECT_LIGHT =0x4600, + LIB3DS_DL_OFF =0x4620, + LIB3DS_DL_OUTER_RANGE =0x465A, + LIB3DS_DL_INNER_RANGE =0x4659, + LIB3DS_DL_MULTIPLIER =0x465B, + LIB3DS_DL_EXCLUDE =0x4654, + LIB3DS_DL_ATTENUATE =0x4625, + LIB3DS_DL_SPOTLIGHT =0x4610, + LIB3DS_DL_SPOT_ROLL =0x4656, + LIB3DS_DL_SHADOWED =0x4630, + LIB3DS_DL_LOCAL_SHADOW2 =0x4641, + LIB3DS_DL_SEE_CONE =0x4650, + LIB3DS_DL_SPOT_RECTANGULAR =0x4651, + LIB3DS_DL_SPOT_ASPECT =0x4657, + LIB3DS_DL_SPOT_PROJECTOR =0x4653, + LIB3DS_DL_SPOT_OVERSHOOT =0x4652, + LIB3DS_DL_RAY_BIAS =0x4658, + LIB3DS_DL_RAYSHAD =0x4627, + LIB3DS_N_CAMERA =0x4700, + LIB3DS_CAM_SEE_CONE =0x4710, + LIB3DS_CAM_RANGES =0x4720, + LIB3DS_OBJ_HIDDEN =0x4010, + LIB3DS_OBJ_VIS_LOFTER =0x4011, + LIB3DS_OBJ_DOESNT_CAST =0x4012, + LIB3DS_OBJ_DONT_RECVSHADOW =0x4017, + LIB3DS_OBJ_MATTE =0x4013, + LIB3DS_OBJ_FAST =0x4014, + LIB3DS_OBJ_PROCEDURAL =0x4015, + LIB3DS_OBJ_FROZEN =0x4016, + LIB3DS_N_TRI_OBJECT =0x4100, + LIB3DS_POINT_ARRAY =0x4110, + LIB3DS_POINT_FLAG_ARRAY =0x4111, + LIB3DS_FACE_ARRAY =0x4120, + LIB3DS_MSH_MAT_GROUP =0x4130, + LIB3DS_SMOOTH_GROUP =0x4150, + LIB3DS_MSH_BOXMAP =0x4190, + LIB3DS_TEX_VERTS =0x4140, + LIB3DS_MESH_MATRIX =0x4160, + LIB3DS_MESH_COLOR =0x4165, + LIB3DS_MESH_TEXTURE_INFO =0x4170, + + LIB3DS_KFDATA =0xB000, + LIB3DS_KFHDR =0xB00A, + LIB3DS_KFSEG =0xB008, + LIB3DS_KFCURTIME =0xB009, + LIB3DS_AMBIENT_NODE_TAG =0xB001, + LIB3DS_OBJECT_NODE_TAG =0xB002, + LIB3DS_CAMERA_NODE_TAG =0xB003, + LIB3DS_TARGET_NODE_TAG =0xB004, + LIB3DS_LIGHT_NODE_TAG =0xB005, + LIB3DS_L_TARGET_NODE_TAG =0xB006, + LIB3DS_SPOTLIGHT_NODE_TAG =0xB007, + LIB3DS_NODE_ID =0xB030, + LIB3DS_NODE_HDR =0xB010, + LIB3DS_PIVOT =0xB013, + LIB3DS_INSTANCE_NAME =0xB011, + LIB3DS_MORPH_SMOOTH =0xB015, + LIB3DS_BOUNDBOX =0xB014, + LIB3DS_POS_TRACK_TAG =0xB020, + LIB3DS_COL_TRACK_TAG =0xB025, + LIB3DS_ROT_TRACK_TAG =0xB021, + LIB3DS_SCL_TRACK_TAG =0xB022, + LIB3DS_MORPH_TRACK_TAG =0xB026, + LIB3DS_FOV_TRACK_TAG =0xB023, + LIB3DS_ROLL_TRACK_TAG =0xB024, + LIB3DS_HOT_TRACK_TAG =0xB027, + LIB3DS_FALL_TRACK_TAG =0xB028, + LIB3DS_HIDE_TRACK_TAG =0xB029, + + LIB3DS_POLY_2D = 0x5000, + LIB3DS_SHAPE_OK = 0x5010, + LIB3DS_SHAPE_NOT_OK = 0x5011, + LIB3DS_SHAPE_HOOK = 0x5020, + LIB3DS_PATH_3D = 0x6000, + LIB3DS_PATH_MATRIX = 0x6005, + LIB3DS_SHAPE_2D = 0x6010, + LIB3DS_M_SCALE = 0x6020, + LIB3DS_M_TWIST = 0x6030, + LIB3DS_M_TEETER = 0x6040, + LIB3DS_M_FIT = 0x6050, + LIB3DS_M_BEVEL = 0x6060, + LIB3DS_XZ_CURVE = 0x6070, + LIB3DS_YZ_CURVE = 0x6080, + LIB3DS_INTERPCT = 0x6090, + LIB3DS_DEFORM_LIMIT = 0x60A0, + + LIB3DS_USE_CONTOUR = 0x6100, + LIB3DS_USE_TWEEN = 0x6110, + LIB3DS_USE_SCALE = 0x6120, + LIB3DS_USE_TWIST = 0x6130, + LIB3DS_USE_TEETER = 0x6140, + LIB3DS_USE_FIT = 0x6150, + LIB3DS_USE_BEVEL = 0x6160, + + LIB3DS_DEFAULT_VIEW = 0x3000, + LIB3DS_VIEW_TOP = 0x3010, + LIB3DS_VIEW_BOTTOM = 0x3020, + LIB3DS_VIEW_LEFT = 0x3030, + LIB3DS_VIEW_RIGHT = 0x3040, + LIB3DS_VIEW_FRONT = 0x3050, + LIB3DS_VIEW_BACK = 0x3060, + LIB3DS_VIEW_USER = 0x3070, + LIB3DS_VIEW_CAMERA = 0x3080, + LIB3DS_VIEW_WINDOW = 0x3090, + + LIB3DS_VIEWPORT_LAYOUT_OLD = 0x7000, + LIB3DS_VIEWPORT_DATA_OLD = 0x7010, + LIB3DS_VIEWPORT_LAYOUT = 0x7001, + LIB3DS_VIEWPORT_DATA = 0x7011, + LIB3DS_VIEWPORT_DATA_3 = 0x7012, + LIB3DS_VIEWPORT_SIZE = 0x7020, + LIB3DS_NETWORK_VIEW = 0x7030 +} Lib3dsChunks; + +typedef struct _Lib3dsChunk { + Lib3dsWord chunk; + Lib3dsDword size; + Lib3dsDword end; + Lib3dsDword cur; +} Lib3dsChunk; + +extern LIB3DSAPI void lib3ds_chunk_enable_dump(Lib3dsBool enable, Lib3dsBool unknown); +extern LIB3DSAPI Lib3dsBool lib3ds_chunk_read(Lib3dsChunk *c, FILE *f); +extern LIB3DSAPI Lib3dsBool lib3ds_chunk_read_start(Lib3dsChunk *c, Lib3dsWord chunk, FILE *f); +extern LIB3DSAPI void lib3ds_chunk_read_tell(Lib3dsChunk *c, FILE *f); +extern LIB3DSAPI Lib3dsWord lib3ds_chunk_read_next(Lib3dsChunk *c, FILE *f); +extern LIB3DSAPI void lib3ds_chunk_read_reset(Lib3dsChunk *c, FILE *f); +extern LIB3DSAPI void lib3ds_chunk_read_end(Lib3dsChunk *c, FILE *f); +extern LIB3DSAPI Lib3dsBool lib3ds_chunk_write(Lib3dsChunk *c, FILE *f); +extern LIB3DSAPI Lib3dsBool lib3ds_chunk_write_start(Lib3dsChunk *c, FILE *f); +extern LIB3DSAPI Lib3dsBool lib3ds_chunk_write_end(Lib3dsChunk *c, FILE *f); +extern LIB3DSAPI const char* lib3ds_chunk_name(Lib3dsWord chunk); +extern LIB3DSAPI void lib3ds_chunk_unknown(Lib3dsWord chunk); + +#ifdef __cplusplus +}; +#endif +#endif + + diff --git a/src/osgPlugins/lib3ds/chunktable.h b/src/osgPlugins/lib3ds/chunktable.h new file mode 100644 index 000000000..ef5261231 --- /dev/null +++ b/src/osgPlugins/lib3ds/chunktable.h @@ -0,0 +1,263 @@ +/* -*- c -*- */ +#ifndef INCLUDED_LIB3DS_CHUNKTABLE_H +#define INCLUDED_LIB3DS_CHUNKTABLE_H +/* + * The 3D Studio File Format Library + * Copyright (C) 1996-2001 by J.E. Hoffmann + * All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or (at + * your option) any later version. + * + * 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 Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + * + * $Id$ + */ + +#ifndef INCLUDED_LIB3DS_CHUNK_H +#include +#endif + +#ifdef __cplusplus +extern "C" { +#endif + +typedef struct _Lib3dsChunkTable { + Lib3dsDword chunk; + const char* name; +} Lib3dsChunkTable; + +static Lib3dsChunkTable lib3ds_chunk_table[]={ + {LIB3DS_NULL_CHUNK, "LIB3DS_NULL_CHUNK"}, + {LIB3DS_M3DMAGIC, "LIB3DS_M3DMAGIC"}, + {LIB3DS_SMAGIC, "LIB3DS_SMAGIC"}, + {LIB3DS_LMAGIC, "LIB3DS_LMAGIC"}, + {LIB3DS_MLIBMAGIC, "LIB3DS_MLIBMAGIC"}, + {LIB3DS_MATMAGIC, "LIB3DS_MATMAGIC"}, + {LIB3DS_CMAGIC, "LIB3DS_CMAGIC"}, + {LIB3DS_M3D_VERSION, "LIB3DS_M3D_VERSION"}, + {LIB3DS_M3D_KFVERSION, "LIB3DS_M3D_KFVERSION"}, + {LIB3DS_COLOR_F, "LIB3DS_COLOR_F"}, + {LIB3DS_COLOR_24, "LIB3DS_COLOR_24"}, + {LIB3DS_LIN_COLOR_24, "LIB3DS_LIN_COLOR_24"}, + {LIB3DS_LIN_COLOR_F, "LIB3DS_LIN_COLOR_F"}, + {LIB3DS_INT_PERCENTAGE, "LIB3DS_INT_PERCENTAGE"}, + {LIB3DS_FLOAT_PERCENTAGE, "LIB3DS_FLOAT_PERCENTAGE"}, + {LIB3DS_MDATA, "LIB3DS_MDATA"}, + {LIB3DS_MESH_VERSION, "LIB3DS_MESH_VERSION"}, + {LIB3DS_MASTER_SCALE, "LIB3DS_MASTER_SCALE"}, + {LIB3DS_LO_SHADOW_BIAS, "LIB3DS_LO_SHADOW_BIAS"}, + {LIB3DS_HI_SHADOW_BIAS, "LIB3DS_HI_SHADOW_BIAS"}, + {LIB3DS_SHADOW_MAP_SIZE, "LIB3DS_SHADOW_MAP_SIZE"}, + {LIB3DS_SHADOW_SAMPLES, "LIB3DS_SHADOW_SAMPLES"}, + {LIB3DS_SHADOW_RANGE, "LIB3DS_SHADOW_RANGE"}, + {LIB3DS_SHADOW_FILTER, "LIB3DS_SHADOW_FILTER"}, + {LIB3DS_RAY_BIAS, "LIB3DS_RAY_BIAS"}, + {LIB3DS_O_CONSTS, "LIB3DS_O_CONSTS"}, + {LIB3DS_AMBIENT_LIGHT, "LIB3DS_AMBIENT_LIGHT"}, + {LIB3DS_BIT_MAP, "LIB3DS_BIT_MAP"}, + {LIB3DS_SOLID_BGND, "LIB3DS_SOLID_BGND"}, + {LIB3DS_V_GRADIENT, "LIB3DS_V_GRADIENT"}, + {LIB3DS_USE_BIT_MAP, "LIB3DS_USE_BIT_MAP"}, + {LIB3DS_USE_SOLID_BGND, "LIB3DS_USE_SOLID_BGND"}, + {LIB3DS_USE_V_GRADIENT, "LIB3DS_USE_V_GRADIENT"}, + {LIB3DS_FOG, "LIB3DS_FOG"}, + {LIB3DS_FOG_BGND, "LIB3DS_FOG_BGND"}, + {LIB3DS_LAYER_FOG, "LIB3DS_LAYER_FOG"}, + {LIB3DS_DISTANCE_CUE, "LIB3DS_DISTANCE_CUE"}, + {LIB3DS_DCUE_BGND, "LIB3DS_DCUE_BGND"}, + {LIB3DS_USE_FOG, "LIB3DS_USE_FOG"}, + {LIB3DS_USE_LAYER_FOG, "LIB3DS_USE_LAYER_FOG"}, + {LIB3DS_USE_DISTANCE_CUE, "LIB3DS_USE_DISTANCE_CUE"}, + {LIB3DS_MAT_ENTRY, "LIB3DS_MAT_ENTRY"}, + {LIB3DS_MAT_NAME, "LIB3DS_MAT_NAME"}, + {LIB3DS_MAT_AMBIENT, "LIB3DS_MAT_AMBIENT"}, + {LIB3DS_MAT_DIFFUSE, "LIB3DS_MAT_DIFFUSE"}, + {LIB3DS_MAT_SPECULAR, "LIB3DS_MAT_SPECULAR"}, + {LIB3DS_MAT_SHININESS, "LIB3DS_MAT_SHININESS"}, + {LIB3DS_MAT_SHIN2PCT, "LIB3DS_MAT_SHIN2PCT"}, + {LIB3DS_MAT_TRANSPARENCY, "LIB3DS_MAT_TRANSPARENCY"}, + {LIB3DS_MAT_XPFALL, "LIB3DS_MAT_XPFALL"}, + {LIB3DS_MAT_USE_XPFALL, "LIB3DS_MAT_USE_XPFALL"}, + {LIB3DS_MAT_REFBLUR, "LIB3DS_MAT_REFBLUR"}, + {LIB3DS_MAT_SHADING, "LIB3DS_MAT_SHADING"}, + {LIB3DS_MAT_USE_REFBLUR, "LIB3DS_MAT_USE_REFBLUR"}, + {LIB3DS_MAT_SELF_ILLUM, "LIB3DS_MAT_SELF_ILLUM"}, + {LIB3DS_MAT_TWO_SIDE, "LIB3DS_MAT_TWO_SIDE"}, + {LIB3DS_MAT_DECAL, "LIB3DS_MAT_DECAL"}, + {LIB3DS_MAT_ADDITIVE, "LIB3DS_MAT_ADDITIVE"}, + {LIB3DS_MAT_WIRE, "LIB3DS_MAT_WIRE"}, + {LIB3DS_MAT_FACEMAP, "LIB3DS_MAT_FACEMAP"}, + {LIB3DS_MAT_PHONGSOFT, "LIB3DS_MAT_PHONGSOFT"}, + {LIB3DS_MAT_WIREABS, "LIB3DS_MAT_WIREABS"}, + {LIB3DS_MAT_WIRE_SIZE, "LIB3DS_MAT_WIRE_SIZE"}, + {LIB3DS_MAT_TEXMAP, "LIB3DS_MAT_TEXMAP"}, + {LIB3DS_MAT_SXP_TEXT_DATA, "LIB3DS_MAT_SXP_TEXT_DATA"}, + {LIB3DS_MAT_TEXMASK, "LIB3DS_MAT_TEXMASK"}, + {LIB3DS_MAT_SXP_TEXTMASK_DATA, "LIB3DS_MAT_SXP_TEXTMASK_DATA"}, + {LIB3DS_MAT_TEX2MAP, "LIB3DS_MAT_TEX2MAP"}, + {LIB3DS_MAT_SXP_TEXT2_DATA, "LIB3DS_MAT_SXP_TEXT2_DATA"}, + {LIB3DS_MAT_TEX2MASK, "LIB3DS_MAT_TEX2MASK"}, + {LIB3DS_MAT_SXP_TEXT2MASK_DATA, "LIB3DS_MAT_SXP_TEXT2MASK_DATA"}, + {LIB3DS_MAT_OPACMAP, "LIB3DS_MAT_OPACMAP"}, + {LIB3DS_MAT_SXP_OPAC_DATA, "LIB3DS_MAT_SXP_OPAC_DATA"}, + {LIB3DS_MAT_OPACMASK, "LIB3DS_MAT_OPACMASK"}, + {LIB3DS_MAT_SXP_OPACMASK_DATA, "LIB3DS_MAT_SXP_OPACMASK_DATA"}, + {LIB3DS_MAT_BUMPMAP, "LIB3DS_MAT_BUMPMAP"}, + {LIB3DS_MAT_SXP_BUMP_DATA, "LIB3DS_MAT_SXP_BUMP_DATA"}, + {LIB3DS_MAT_BUMPMASK, "LIB3DS_MAT_BUMPMASK"}, + {LIB3DS_MAT_SXP_BUMPMASK_DATA, "LIB3DS_MAT_SXP_BUMPMASK_DATA"}, + {LIB3DS_MAT_SPECMAP, "LIB3DS_MAT_SPECMAP"}, + {LIB3DS_MAT_SXP_SPEC_DATA, "LIB3DS_MAT_SXP_SPEC_DATA"}, + {LIB3DS_MAT_SPECMASK, "LIB3DS_MAT_SPECMASK"}, + {LIB3DS_MAT_SXP_SPECMASK_DATA, "LIB3DS_MAT_SXP_SPECMASK_DATA"}, + {LIB3DS_MAT_SHINMAP, "LIB3DS_MAT_SHINMAP"}, + {LIB3DS_MAT_SXP_SHIN_DATA, "LIB3DS_MAT_SXP_SHIN_DATA"}, + {LIB3DS_MAT_SHINMASK, "LIB3DS_MAT_SHINMASK"}, + {LIB3DS_MAT_SXP_SHINMASK_DATA, "LIB3DS_MAT_SXP_SHINMASK_DATA"}, + {LIB3DS_MAT_SELFIMAP, "LIB3DS_MAT_SELFIMAP"}, + {LIB3DS_MAT_SXP_SELFI_DATA, "LIB3DS_MAT_SXP_SELFI_DATA"}, + {LIB3DS_MAT_SELFIMASK, "LIB3DS_MAT_SELFIMASK"}, + {LIB3DS_MAT_SXP_SELFIMASK_DATA, "LIB3DS_MAT_SXP_SELFIMASK_DATA"}, + {LIB3DS_MAT_REFLMAP, "LIB3DS_MAT_REFLMAP"}, + {LIB3DS_MAT_REFLMASK, "LIB3DS_MAT_REFLMASK"}, + {LIB3DS_MAT_SXP_REFLMASK_DATA, "LIB3DS_MAT_SXP_REFLMASK_DATA"}, + {LIB3DS_MAT_ACUBIC, "LIB3DS_MAT_ACUBIC"}, + {LIB3DS_MAT_MAPNAME, "LIB3DS_MAT_MAPNAME"}, + {LIB3DS_MAT_MAP_TILING, "LIB3DS_MAT_MAP_TILING"}, + {LIB3DS_MAT_MAP_TEXBLUR, "LIB3DS_MAT_MAP_TEXBLUR"}, + {LIB3DS_MAT_MAP_USCALE, "LIB3DS_MAT_MAP_USCALE"}, + {LIB3DS_MAT_MAP_VSCALE, "LIB3DS_MAT_MAP_VSCALE"}, + {LIB3DS_MAT_MAP_UOFFSET, "LIB3DS_MAT_MAP_UOFFSET"}, + {LIB3DS_MAT_MAP_VOFFSET, "LIB3DS_MAT_MAP_VOFFSET"}, + {LIB3DS_MAT_MAP_ANG, "LIB3DS_MAT_MAP_ANG"}, + {LIB3DS_MAT_MAP_COL1, "LIB3DS_MAT_MAP_COL1"}, + {LIB3DS_MAT_MAP_COL2, "LIB3DS_MAT_MAP_COL2"}, + {LIB3DS_MAT_MAP_RCOL, "LIB3DS_MAT_MAP_RCOL"}, + {LIB3DS_MAT_MAP_GCOL, "LIB3DS_MAT_MAP_GCOL"}, + {LIB3DS_MAT_MAP_BCOL, "LIB3DS_MAT_MAP_BCOL"}, + {LIB3DS_NAMED_OBJECT, "LIB3DS_NAMED_OBJECT"}, + {LIB3DS_N_DIRECT_LIGHT, "LIB3DS_N_DIRECT_LIGHT"}, + {LIB3DS_DL_OFF, "LIB3DS_DL_OFF"}, + {LIB3DS_DL_OUTER_RANGE, "LIB3DS_DL_OUTER_RANGE"}, + {LIB3DS_DL_INNER_RANGE, "LIB3DS_DL_INNER_RANGE"}, + {LIB3DS_DL_MULTIPLIER, "LIB3DS_DL_MULTIPLIER"}, + {LIB3DS_DL_EXCLUDE, "LIB3DS_DL_EXCLUDE"}, + {LIB3DS_DL_ATTENUATE, "LIB3DS_DL_ATTENUATE"}, + {LIB3DS_DL_SPOTLIGHT, "LIB3DS_DL_SPOTLIGHT"}, + {LIB3DS_DL_SPOT_ROLL, "LIB3DS_DL_SPOT_ROLL"}, + {LIB3DS_DL_SHADOWED, "LIB3DS_DL_SHADOWED"}, + {LIB3DS_DL_LOCAL_SHADOW2, "LIB3DS_DL_LOCAL_SHADOW2"}, + {LIB3DS_DL_SEE_CONE, "LIB3DS_DL_SEE_CONE"}, + {LIB3DS_DL_SPOT_RECTANGULAR, "LIB3DS_DL_SPOT_RECTANGULAR"}, + {LIB3DS_DL_SPOT_ASPECT, "LIB3DS_DL_SPOT_ASPECT"}, + {LIB3DS_DL_SPOT_PROJECTOR, "LIB3DS_DL_SPOT_PROJECTOR"}, + {LIB3DS_DL_SPOT_OVERSHOOT, "LIB3DS_DL_SPOT_OVERSHOOT"}, + {LIB3DS_DL_RAY_BIAS, "LIB3DS_DL_RAY_BIAS"}, + {LIB3DS_DL_RAYSHAD, "LIB3DS_DL_RAYSHAD"}, + {LIB3DS_N_CAMERA, "LIB3DS_N_CAMERA"}, + {LIB3DS_CAM_SEE_CONE, "LIB3DS_CAM_SEE_CONE"}, + {LIB3DS_CAM_RANGES, "LIB3DS_CAM_RANGES"}, + {LIB3DS_OBJ_HIDDEN, "LIB3DS_OBJ_HIDDEN"}, + {LIB3DS_OBJ_VIS_LOFTER, "LIB3DS_OBJ_VIS_LOFTER"}, + {LIB3DS_OBJ_DOESNT_CAST, "LIB3DS_OBJ_DOESNT_CAST"}, + {LIB3DS_OBJ_DONT_RECVSHADOW, "LIB3DS_OBJ_DONT_RECVSHADOW"}, + {LIB3DS_OBJ_MATTE, "LIB3DS_OBJ_MATTE"}, + {LIB3DS_OBJ_FAST, "LIB3DS_OBJ_FAST"}, + {LIB3DS_OBJ_PROCEDURAL, "LIB3DS_OBJ_PROCEDURAL"}, + {LIB3DS_OBJ_FROZEN, "LIB3DS_OBJ_FROZEN"}, + {LIB3DS_N_TRI_OBJECT, "LIB3DS_N_TRI_OBJECT"}, + {LIB3DS_POINT_ARRAY, "LIB3DS_POINT_ARRAY"}, + {LIB3DS_POINT_FLAG_ARRAY, "LIB3DS_POINT_FLAG_ARRAY"}, + {LIB3DS_FACE_ARRAY, "LIB3DS_FACE_ARRAY"}, + {LIB3DS_MSH_MAT_GROUP, "LIB3DS_MSH_MAT_GROUP"}, + {LIB3DS_SMOOTH_GROUP, "LIB3DS_SMOOTH_GROUP"}, + {LIB3DS_MSH_BOXMAP, "LIB3DS_MSH_BOXMAP"}, + {LIB3DS_TEX_VERTS, "LIB3DS_TEX_VERTS"}, + {LIB3DS_MESH_MATRIX, "LIB3DS_MESH_MATRIX"}, + {LIB3DS_MESH_COLOR, "LIB3DS_MESH_COLOR"}, + {LIB3DS_MESH_TEXTURE_INFO, "LIB3DS_MESH_TEXTURE_INFO"}, + {LIB3DS_KFDATA, "LIB3DS_KFDATA"}, + {LIB3DS_KFHDR, "LIB3DS_KFHDR"}, + {LIB3DS_KFSEG, "LIB3DS_KFSEG"}, + {LIB3DS_KFCURTIME, "LIB3DS_KFCURTIME"}, + {LIB3DS_AMBIENT_NODE_TAG, "LIB3DS_AMBIENT_NODE_TAG"}, + {LIB3DS_OBJECT_NODE_TAG, "LIB3DS_OBJECT_NODE_TAG"}, + {LIB3DS_CAMERA_NODE_TAG, "LIB3DS_CAMERA_NODE_TAG"}, + {LIB3DS_TARGET_NODE_TAG, "LIB3DS_TARGET_NODE_TAG"}, + {LIB3DS_LIGHT_NODE_TAG, "LIB3DS_LIGHT_NODE_TAG"}, + {LIB3DS_L_TARGET_NODE_TAG, "LIB3DS_L_TARGET_NODE_TAG"}, + {LIB3DS_SPOTLIGHT_NODE_TAG, "LIB3DS_SPOTLIGHT_NODE_TAG"}, + {LIB3DS_NODE_ID, "LIB3DS_NODE_ID"}, + {LIB3DS_NODE_HDR, "LIB3DS_NODE_HDR"}, + {LIB3DS_PIVOT, "LIB3DS_PIVOT"}, + {LIB3DS_INSTANCE_NAME, "LIB3DS_INSTANCE_NAME"}, + {LIB3DS_MORPH_SMOOTH, "LIB3DS_MORPH_SMOOTH"}, + {LIB3DS_BOUNDBOX, "LIB3DS_BOUNDBOX"}, + {LIB3DS_POS_TRACK_TAG, "LIB3DS_POS_TRACK_TAG"}, + {LIB3DS_COL_TRACK_TAG, "LIB3DS_COL_TRACK_TAG"}, + {LIB3DS_ROT_TRACK_TAG, "LIB3DS_ROT_TRACK_TAG"}, + {LIB3DS_SCL_TRACK_TAG, "LIB3DS_SCL_TRACK_TAG"}, + {LIB3DS_MORPH_TRACK_TAG, "LIB3DS_MORPH_TRACK_TAG"}, + {LIB3DS_FOV_TRACK_TAG, "LIB3DS_FOV_TRACK_TAG"}, + {LIB3DS_ROLL_TRACK_TAG, "LIB3DS_ROLL_TRACK_TAG"}, + {LIB3DS_HOT_TRACK_TAG, "LIB3DS_HOT_TRACK_TAG"}, + {LIB3DS_FALL_TRACK_TAG, "LIB3DS_FALL_TRACK_TAG"}, + {LIB3DS_HIDE_TRACK_TAG, "LIB3DS_HIDE_TRACK_TAG"}, + {LIB3DS_POLY_2D, "LIB3DS_POLY_2D"}, + {LIB3DS_SHAPE_OK, "LIB3DS_SHAPE_OK"}, + {LIB3DS_SHAPE_NOT_OK, "LIB3DS_SHAPE_NOT_OK"}, + {LIB3DS_SHAPE_HOOK, "LIB3DS_SHAPE_HOOK"}, + {LIB3DS_PATH_3D, "LIB3DS_PATH_3D"}, + {LIB3DS_PATH_MATRIX, "LIB3DS_PATH_MATRIX"}, + {LIB3DS_SHAPE_2D, "LIB3DS_SHAPE_2D"}, + {LIB3DS_M_SCALE, "LIB3DS_M_SCALE"}, + {LIB3DS_M_TWIST, "LIB3DS_M_TWIST"}, + {LIB3DS_M_TEETER, "LIB3DS_M_TEETER"}, + {LIB3DS_M_FIT, "LIB3DS_M_FIT"}, + {LIB3DS_M_BEVEL, "LIB3DS_M_BEVEL"}, + {LIB3DS_XZ_CURVE, "LIB3DS_XZ_CURVE"}, + {LIB3DS_YZ_CURVE, "LIB3DS_YZ_CURVE"}, + {LIB3DS_INTERPCT, "LIB3DS_INTERPCT"}, + {LIB3DS_DEFORM_LIMIT, "LIB3DS_DEFORM_LIMIT"}, + {LIB3DS_USE_CONTOUR, "LIB3DS_USE_CONTOUR"}, + {LIB3DS_USE_TWEEN, "LIB3DS_USE_TWEEN"}, + {LIB3DS_USE_SCALE, "LIB3DS_USE_SCALE"}, + {LIB3DS_USE_TWIST, "LIB3DS_USE_TWIST"}, + {LIB3DS_USE_TEETER, "LIB3DS_USE_TEETER"}, + {LIB3DS_USE_FIT, "LIB3DS_USE_FIT"}, + {LIB3DS_USE_BEVEL, "LIB3DS_USE_BEVEL"}, + {LIB3DS_DEFAULT_VIEW, "LIB3DS_DEFAULT_VIEW"}, + {LIB3DS_VIEW_TOP, "LIB3DS_VIEW_TOP"}, + {LIB3DS_VIEW_BOTTOM, "LIB3DS_VIEW_BOTTOM"}, + {LIB3DS_VIEW_LEFT, "LIB3DS_VIEW_LEFT"}, + {LIB3DS_VIEW_RIGHT, "LIB3DS_VIEW_RIGHT"}, + {LIB3DS_VIEW_FRONT, "LIB3DS_VIEW_FRONT"}, + {LIB3DS_VIEW_BACK, "LIB3DS_VIEW_BACK"}, + {LIB3DS_VIEW_USER, "LIB3DS_VIEW_USER"}, + {LIB3DS_VIEW_CAMERA, "LIB3DS_VIEW_CAMERA"}, + {LIB3DS_VIEW_WINDOW, "LIB3DS_VIEW_WINDOW"}, + {LIB3DS_VIEWPORT_LAYOUT_OLD, "LIB3DS_VIEWPORT_LAYOUT_OLD"}, + {LIB3DS_VIEWPORT_DATA_OLD, "LIB3DS_VIEWPORT_DATA_OLD"}, + {LIB3DS_VIEWPORT_LAYOUT, "LIB3DS_VIEWPORT_LAYOUT"}, + {LIB3DS_VIEWPORT_DATA, "LIB3DS_VIEWPORT_DATA"}, + {LIB3DS_VIEWPORT_DATA_3, "LIB3DS_VIEWPORT_DATA_3"}, + {LIB3DS_VIEWPORT_SIZE, "LIB3DS_VIEWPORT_SIZE"}, + {LIB3DS_NETWORK_VIEW, "LIB3DS_NETWORK_VIEW"}, + {0,0} +}; + +#ifdef __cplusplus +}; +#endif +#endif + diff --git a/src/osgPlugins/lib3ds/ease.cpp b/src/osgPlugins/lib3ds/ease.cpp new file mode 100644 index 000000000..a0e658473 --- /dev/null +++ b/src/osgPlugins/lib3ds/ease.cpp @@ -0,0 +1,68 @@ +/* + * The 3D Studio File Format Library + * Copyright (C) 1996-2001 by J.E. Hoffmann + * All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or (at + * your option) any later version. + * + * 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 Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + * + * $Id$ + */ +#define LIB3DS_EXPORT +#include + +/*! + * \defgroup ease Ease + * + * \author J.E. Hoffmann + */ + +/*! + * \ingroup ease + */ +Lib3dsFloat +lib3ds_ease(Lib3dsFloat fp, Lib3dsFloat fc, Lib3dsFloat fn, +Lib3dsFloat ease_from, Lib3dsFloat ease_to) +{ + Lib3dsDouble s,step; + Lib3dsDouble tofrom; + Lib3dsDouble a; + + s=step=(Lib3dsFloat)(fc-fp)/(fn-fp); + tofrom=ease_to+ease_from; + if (tofrom!=0.0) + { + if (tofrom>1.0) + { + ease_to=(Lib3dsFloat)(ease_to/tofrom); + ease_from=(Lib3dsFloat)(ease_from/tofrom); + } + a=1.0/(2.0-(ease_to+ease_from)); + + if (step + * All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or (at + * your option) any later version. + * + * 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 Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + * + * $Id$ + */ + +#ifndef INCLUDED_LIB3DS_TYPES_H +#include +#endif + +#ifdef __cplusplus +extern "C" { +#endif + +extern LIB3DSAPI Lib3dsFloat lib3ds_ease(Lib3dsFloat fp, Lib3dsFloat fc, + Lib3dsFloat fn, Lib3dsFloat ease_from, Lib3dsFloat ease_to); + +#ifdef __cplusplus +}; +#endif +#endif + diff --git a/src/osgPlugins/lib3ds/file.cpp b/src/osgPlugins/lib3ds/file.cpp new file mode 100644 index 000000000..f2238cb5c --- /dev/null +++ b/src/osgPlugins/lib3ds/file.cpp @@ -0,0 +1,1596 @@ +/* + * The 3D Studio File Format Library + * Copyright (C) 1996-2001 by J.E. Hoffmann + * All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or (at + * your option) any later version. + * + * 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 Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + * + * $Id$ + */ +#define LIB3DS_EXPORT +#include +#include +#include +#include +#include +#include +#include +#include +#include +#include +//#include +#ifdef WITH_DMALLOC +#include +#endif + +/*! + * \defgroup file Files + * + * \author J.E. Hoffmann + */ + +/*! + * \ingroup file + */ +Lib3dsFile* +lib3ds_open(const char *filename) +{ + FILE *f; + Lib3dsFile *file; + + f=fopen(filename, "rb"); + if (!f) + { + return(0); + } + file=lib3ds_file_new(); + if (!file) + { + fclose(f); + return(0); + } + + if (!lib3ds_file_read(file, f)) + { + free(file); + fclose(f); + return(0); + } + fclose(f); + return(file); +} + + +/*! + * \ingroup file + */ +void +lib3ds_close(Lib3dsFile *file) +{ + lib3ds_file_free(file); +} + + +/*! + * \ingroup file + */ +Lib3dsFile* +lib3ds_file_new() +{ + Lib3dsFile *file; + + file=(Lib3dsFile*)calloc(sizeof(Lib3dsFile),1); + if (!file) + { + return(0); + } + file->mesh_version=3; + file->master_scale=1.0f; + file->keyf_revision=5; + return(file); +} + + +/*! + * \ingroup file + */ +void +lib3ds_file_free(Lib3dsFile* file) +{ + ASSERT(file); + lib3ds_viewport_set_views(&file->viewport,0); + { + Lib3dsMaterial *p,*q; + + for (p=file->materials; p; p=q) + { + q=p->next; + lib3ds_material_free(p); + } + file->materials=0; + } + { + Lib3dsCamera *p,*q; + + for (p=file->cameras; p; p=q) + { + q=p->next; + lib3ds_camera_free(p); + } + file->cameras=0; + } + { + Lib3dsLight *p,*q; + + for (p=file->lights; p; p=q) + { + q=p->next; + lib3ds_light_free(p); + } + file->lights=0; + } + { + Lib3dsMesh *p,*q; + + for (p=file->meshes; p; p=q) + { + q=p->next; + lib3ds_mesh_free(p); + } + file->meshes=0; + } + { + Lib3dsNode *p,*q; + + for (p=file->nodes; p; p=q) + { + q=p->next; + lib3ds_node_free(p); + } + } + free(file); +} + + +/*! + * \ingroup file + */ +void +lib3ds_file_eval(Lib3dsFile *file, Lib3dsFloat t) +{ + Lib3dsNode *p; + + for (p=file->nodes; p!=0; p=p->next) + { + lib3ds_node_eval(p, t); + } +} + + +static Lib3dsBool +named_object_read(Lib3dsFile *file, FILE *f) +{ + Lib3dsChunk c; + char name[64]; + Lib3dsWord chunk; + + if (!lib3ds_chunk_read_start(&c, LIB3DS_NAMED_OBJECT, f)) + { + return(LIB3DS_FALSE); + } + if (!lib3ds_string_read(name, 64, f)) + { + return(LIB3DS_FALSE); + } + lib3ds_chunk_read_tell(&c, f); + + while ((chunk=lib3ds_chunk_read_next(&c, f))!=0) + { + switch (chunk) + { + case LIB3DS_N_TRI_OBJECT: + { + Lib3dsMesh *mesh; + + mesh=lib3ds_mesh_new(name); + if (!mesh) + { + return(LIB3DS_FALSE); + } + lib3ds_chunk_read_reset(&c, f); + if (!lib3ds_mesh_read(mesh, f)) + { + return(LIB3DS_FALSE); + } + lib3ds_file_insert_mesh(file, mesh); + } + break; + case LIB3DS_N_CAMERA: + { + Lib3dsCamera *camera; + + camera=lib3ds_camera_new(name); + if (!camera) + { + return(LIB3DS_FALSE); + } + lib3ds_chunk_read_reset(&c, f); + if (!lib3ds_camera_read(camera, f)) + { + return(LIB3DS_FALSE); + } + lib3ds_file_insert_camera(file, camera); + } + break; + case LIB3DS_N_DIRECT_LIGHT: + { + Lib3dsLight *light; + + light=lib3ds_light_new(name); + if (!light) + { + return(LIB3DS_FALSE); + } + lib3ds_chunk_read_reset(&c, f); + if (!lib3ds_light_read(light, f)) + { + return(LIB3DS_FALSE); + } + lib3ds_file_insert_light(file, light); + } + break; + default: + lib3ds_chunk_unknown(chunk); + } + } + + lib3ds_chunk_read_end(&c, f); + return(LIB3DS_TRUE); +} + + +static Lib3dsBool +ambient_read(Lib3dsFile *file, FILE *f) +{ + Lib3dsChunk c; + Lib3dsWord chunk; + Lib3dsBool have_lin=LIB3DS_FALSE; + + if (!lib3ds_chunk_read_start(&c, LIB3DS_AMBIENT_LIGHT, f)) + { + return(LIB3DS_FALSE); + } + + while ((chunk=lib3ds_chunk_read_next(&c, f))!=0) + { + switch (chunk) + { + case LIB3DS_LIN_COLOR_F: + { + int i; + for (i=0; i<3; ++i) + { + file->ambient[i]=lib3ds_float_read(f); + } + } + have_lin=LIB3DS_TRUE; + break; + case LIB3DS_COLOR_F: + { + /* gamma corrected color chunk + replaced in 3ds R3 by LIN_COLOR_24 */ + if (!have_lin) + { + int i; + for (i=0; i<3; ++i) + { + file->ambient[i]=lib3ds_float_read(f); + } + } + } + break; + default: + lib3ds_chunk_unknown(chunk); + } + } + + lib3ds_chunk_read_end(&c, f); + return(LIB3DS_TRUE); +} + + +static Lib3dsBool +mdata_read(Lib3dsFile *file, FILE *f) +{ + Lib3dsChunk c; + Lib3dsWord chunk; + + if (!lib3ds_chunk_read_start(&c, LIB3DS_MDATA, f)) + { + return(LIB3DS_FALSE); + } + + while ((chunk=lib3ds_chunk_read_next(&c, f))!=0) + { + switch (chunk) + { + case LIB3DS_MESH_VERSION: + { + file->mesh_version=lib3ds_intd_read(f); + } + break; + case LIB3DS_MASTER_SCALE: + { + file->master_scale=lib3ds_float_read(f); + } + break; + case LIB3DS_SHADOW_MAP_SIZE: + case LIB3DS_LO_SHADOW_BIAS: + case LIB3DS_HI_SHADOW_BIAS: + case LIB3DS_SHADOW_SAMPLES: + case LIB3DS_SHADOW_RANGE: + case LIB3DS_SHADOW_FILTER: + case LIB3DS_RAY_BIAS: + { + lib3ds_chunk_read_reset(&c, f); + if (!lib3ds_shadow_read(&file->shadow, f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_VIEWPORT_LAYOUT: + case LIB3DS_DEFAULT_VIEW: + { + lib3ds_chunk_read_reset(&c, f); + if (!lib3ds_viewport_read(&file->viewport, f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_O_CONSTS: + { + int i; + for (i=0; i<3; ++i) + { + file->construction_plane[i]=lib3ds_float_read(f); + } + } + break; + case LIB3DS_AMBIENT_LIGHT: + { + lib3ds_chunk_read_reset(&c, f); + if (!ambient_read(file, f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_BIT_MAP: + case LIB3DS_SOLID_BGND: + case LIB3DS_V_GRADIENT: + case LIB3DS_USE_BIT_MAP: + case LIB3DS_USE_SOLID_BGND: + case LIB3DS_USE_V_GRADIENT: + { + lib3ds_chunk_read_reset(&c, f); + if (!lib3ds_background_read(&file->background, f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_FOG: + case LIB3DS_LAYER_FOG: + case LIB3DS_DISTANCE_CUE: + case LIB3DS_USE_FOG: + case LIB3DS_USE_LAYER_FOG: + case LIB3DS_USE_DISTANCE_CUE: + { + lib3ds_chunk_read_reset(&c, f); + if (!lib3ds_atmosphere_read(&file->atmosphere, f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_MAT_ENTRY: + { + Lib3dsMaterial *material; + + material=lib3ds_material_new(); + if (!material) + { + return(LIB3DS_FALSE); + } + lib3ds_chunk_read_reset(&c, f); + if (!lib3ds_material_read(material, f)) + { + return(LIB3DS_FALSE); + } + lib3ds_file_insert_material(file, material); + } + break; + case LIB3DS_NAMED_OBJECT: + { + lib3ds_chunk_read_reset(&c, f); + if (!named_object_read(file, f)) + { + return(LIB3DS_FALSE); + } + } + break; + default: + lib3ds_chunk_unknown(chunk); + } + } + + lib3ds_chunk_read_end(&c, f); + return(LIB3DS_TRUE); +} + + +static Lib3dsBool +kfdata_read(Lib3dsFile *file, FILE *f) +{ + Lib3dsChunk c; + Lib3dsWord chunk; + + if (!lib3ds_chunk_read_start(&c, LIB3DS_KFDATA, f)) + { + return(LIB3DS_FALSE); + } + + while ((chunk=lib3ds_chunk_read_next(&c, f))!=0) + { + switch (chunk) + { + case LIB3DS_KFHDR: + { + char s[64]; + file->keyf_revision=lib3ds_word_read(f); + if (!lib3ds_string_read(s, 64, f)) + { + return(LIB3DS_FALSE); + } + file->frames=lib3ds_intd_read(f); + } + break; + case LIB3DS_KFSEG: + { + file->segment_from=lib3ds_intd_read(f); + file->segment_to=lib3ds_intd_read(f); + } + break; + case LIB3DS_KFCURTIME: + { + file->current_frame=lib3ds_intd_read(f); + } + break; + case LIB3DS_VIEWPORT_LAYOUT: + case LIB3DS_DEFAULT_VIEW: + { + lib3ds_chunk_read_reset(&c, f); + if (!lib3ds_viewport_read(&file->viewport_keyf, f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_AMBIENT_NODE_TAG: + { + Lib3dsNode *node; + + node=lib3ds_node_new_ambient(); + if (!node) + { + return(LIB3DS_FALSE); + } + lib3ds_chunk_read_reset(&c, f); + if (!lib3ds_node_read(node, file, f)) + { + return(LIB3DS_FALSE); + } + lib3ds_file_insert_node(file, node); + } + break; + case LIB3DS_OBJECT_NODE_TAG: + { + Lib3dsNode *node; + + node=lib3ds_node_new_object(); + if (!node) + { + return(LIB3DS_FALSE); + } + lib3ds_chunk_read_reset(&c, f); + if (!lib3ds_node_read(node, file, f)) + { + return(LIB3DS_FALSE); + } + lib3ds_file_insert_node(file, node); + } + break; + case LIB3DS_CAMERA_NODE_TAG: + { + Lib3dsNode *node; + + node=lib3ds_node_new_camera(); + if (!node) + { + return(LIB3DS_FALSE); + } + lib3ds_chunk_read_reset(&c, f); + if (!lib3ds_node_read(node, file, f)) + { + return(LIB3DS_FALSE); + } + lib3ds_file_insert_node(file, node); + } + break; + case LIB3DS_TARGET_NODE_TAG: + { + Lib3dsNode *node; + + node=lib3ds_node_new_target(); + if (!node) + { + return(LIB3DS_FALSE); + } + lib3ds_chunk_read_reset(&c, f); + if (!lib3ds_node_read(node, file, f)) + { + return(LIB3DS_FALSE); + } + lib3ds_file_insert_node(file, node); + } + break; + case LIB3DS_LIGHT_NODE_TAG: + case LIB3DS_SPOTLIGHT_NODE_TAG: + { + Lib3dsNode *node; + + node=lib3ds_node_new_light(); + if (!node) + { + return(LIB3DS_FALSE); + } + lib3ds_chunk_read_reset(&c, f); + if (!lib3ds_node_read(node, file, f)) + { + return(LIB3DS_FALSE); + } + lib3ds_file_insert_node(file, node); + } + break; + case LIB3DS_L_TARGET_NODE_TAG: + { + Lib3dsNode *node; + + node=lib3ds_node_new_spot(); + if (!node) + { + return(LIB3DS_FALSE); + } + lib3ds_chunk_read_reset(&c, f); + if (!lib3ds_node_read(node, file, f)) + { + return(LIB3DS_FALSE); + } + lib3ds_file_insert_node(file, node); + } + break; + default: + lib3ds_chunk_unknown(chunk); + } + } + + lib3ds_chunk_read_end(&c, f); + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup file + */ +Lib3dsBool +lib3ds_file_read(Lib3dsFile *file, FILE *f) +{ + Lib3dsChunk c; + Lib3dsWord chunk; + + if (!lib3ds_chunk_read_start(&c, 0, f)) + { + return(LIB3DS_FALSE); + } + switch (c.chunk) + { + case LIB3DS_MDATA: + { + lib3ds_chunk_read_reset(&c, f); + if (!mdata_read(file, f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_M3DMAGIC: + case LIB3DS_MLIBMAGIC: + case LIB3DS_CMAGIC: + { + while ((chunk=lib3ds_chunk_read_next(&c, f))!=0) + { + switch (chunk) + { + case LIB3DS_M3D_VERSION: + { + file->mesh_version=lib3ds_dword_read(f); + } + break; + case LIB3DS_MDATA: + { + lib3ds_chunk_read_reset(&c, f); + if (!mdata_read(file, f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_KFDATA: + { + lib3ds_chunk_read_reset(&c, f); + if (!kfdata_read(file, f)) + { + return(LIB3DS_FALSE); + } + } + break; + default: + lib3ds_chunk_unknown(chunk); + } + } + } + break; + default: + lib3ds_chunk_unknown(c.chunk); + return(LIB3DS_FALSE); + } + + lib3ds_chunk_read_end(&c, f); + return(LIB3DS_TRUE); +} + + +static Lib3dsBool +colorf_write(Lib3dsRgba rgb, FILE *f) +{ + Lib3dsChunk c; + + c.chunk=LIB3DS_COLOR_F; + c.size=18; + lib3ds_chunk_write(&c,f); + lib3ds_rgb_write(rgb,f); + + c.chunk=LIB3DS_LIN_COLOR_F; + c.size=18; + lib3ds_chunk_write(&c,f); + lib3ds_rgb_write(rgb,f); + return(LIB3DS_TRUE); +} + + +static Lib3dsBool +mdata_write(Lib3dsFile *file, FILE *f) +{ + Lib3dsChunk c; + + c.chunk=LIB3DS_MDATA; + if (!lib3ds_chunk_write_start(&c,f)) + { + return(LIB3DS_FALSE); + } + + { /*---- LIB3DS_MESH_VERSION ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_MESH_VERSION; + c.size=10; + lib3ds_chunk_write(&c,f); + lib3ds_intd_write(file->mesh_version,f); + } + { /*---- LIB3DS_MASTER_SCALE ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_MASTER_SCALE; + c.size=10; + lib3ds_chunk_write(&c,f); + lib3ds_float_write(file->master_scale,f); + } + { /*---- LIB3DS_O_CONSTS ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_O_CONSTS; + c.size=18; + lib3ds_chunk_write(&c,f); + lib3ds_vector_write(file->construction_plane,f); + } + + { /*---- LIB3DS_AMBIENT_LIGHT ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_AMBIENT_LIGHT; + c.size=42; + lib3ds_chunk_write(&c,f); + colorf_write(file->ambient,f); + } + lib3ds_background_write(&file->background, f); + lib3ds_atmosphere_write(&file->atmosphere, f); + lib3ds_shadow_write(&file->shadow, f); + lib3ds_viewport_write(&file->viewport, f); + { + Lib3dsMaterial *p; + for (p=file->materials; p!=0; p=p->next) + { + if (!lib3ds_material_write(p,f)) + { + return(LIB3DS_FALSE); + } + } + } + { + Lib3dsCamera *p; + Lib3dsChunk c; + + for (p=file->cameras; p!=0; p=p->next) + { + c.chunk=LIB3DS_NAMED_OBJECT; + if (!lib3ds_chunk_write_start(&c,f)) + { + return(LIB3DS_FALSE); + } + lib3ds_string_write(p->name,f); + lib3ds_camera_write(p,f); + if (!lib3ds_chunk_write_end(&c,f)) + { + return(LIB3DS_FALSE); + } + } + } + { + Lib3dsLight *p; + Lib3dsChunk c; + + for (p=file->lights; p!=0; p=p->next) + { + c.chunk=LIB3DS_NAMED_OBJECT; + if (!lib3ds_chunk_write_start(&c,f)) + { + return(LIB3DS_FALSE); + } + lib3ds_string_write(p->name,f); + lib3ds_light_write(p,f); + if (!lib3ds_chunk_write_end(&c,f)) + { + return(LIB3DS_FALSE); + } + } + } + { + Lib3dsMesh *p; + Lib3dsChunk c; + + for (p=file->meshes; p!=0; p=p->next) + { + c.chunk=LIB3DS_NAMED_OBJECT; + if (!lib3ds_chunk_write_start(&c,f)) + { + return(LIB3DS_FALSE); + } + lib3ds_string_write(p->name,f); + lib3ds_mesh_write(p,f); + if (!lib3ds_chunk_write_end(&c,f)) + { + return(LIB3DS_FALSE); + } + } + } + + if (!lib3ds_chunk_write_end(&c,f)) + { + return(LIB3DS_FALSE); + } + return(LIB3DS_TRUE); +} + + +static Lib3dsBool +nodes_write(Lib3dsNode *node, Lib3dsFile *file, FILE *f) +{ + { + Lib3dsNode *p; + for (p=node->childs; p!=0; p=p->next) + { + if (!lib3ds_node_write(p, file, f)) + { + return(LIB3DS_FALSE); + } + nodes_write(p, file, f); + } + } + return(LIB3DS_TRUE); +} + + +static Lib3dsBool +kfdata_write(Lib3dsFile *file, FILE *f) +{ + Lib3dsChunk c; + + c.chunk=LIB3DS_KFDATA; + if (!lib3ds_chunk_write_start(&c,f)) + { + return(LIB3DS_FALSE); + } + + { /*---- LIB3DS_KFHDR ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_KFHDR; + c.size=25; + lib3ds_chunk_write(&c,f); + lib3ds_intw_write(file->keyf_revision,f); + lib3ds_string_write("????????.3ds", f); + lib3ds_intd_write(file->frames, f); + } + { /*---- LIB3DS_KFSEG ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_KFSEG; + c.size=14; + lib3ds_chunk_write(&c,f); + lib3ds_intd_write(file->segment_from,f); + lib3ds_intd_write(file->segment_to,f); + } + { /*---- LIB3DS_KFCURTIME ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_KFCURTIME; + c.size=10; + lib3ds_chunk_write(&c,f); + lib3ds_intd_write(file->current_frame,f); + } + + { + Lib3dsNode *p; + for (p=file->nodes; p!=0; p=p->next) + { + if (!lib3ds_node_write(p, file, f)) + { + return(LIB3DS_FALSE); + } + if (!nodes_write(p, file, f)) + { + return(LIB3DS_FALSE); + } + } + } + + if (!lib3ds_chunk_write_end(&c,f)) + { + return(LIB3DS_FALSE); + } + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup file + */ +Lib3dsBool +lib3ds_file_write(Lib3dsFile *file, FILE *f) +{ + Lib3dsChunk c; + + c.chunk=LIB3DS_M3DMAGIC; + if (!lib3ds_chunk_write_start(&c,f)) + { + LIB3DS_ERROR_LOG; + return(LIB3DS_FALSE); + } + + { /*---- LIB3DS_M3D_VERSION ----*/ + Lib3dsChunk c; + + c.chunk=LIB3DS_M3D_VERSION; + c.size=10; + lib3ds_chunk_write(&c,f); + lib3ds_dword_write(file->mesh_version, f); + } + + if (!mdata_write(file, f)) + { + return(LIB3DS_FALSE); + } + if (!kfdata_write(file, f)) + { + return(LIB3DS_FALSE); + } + + if (!lib3ds_chunk_write_end(&c,f)) + { + return(LIB3DS_FALSE); + } + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup file + */ +void +lib3ds_file_insert_material(Lib3dsFile *file, Lib3dsMaterial *material) +{ + Lib3dsMaterial *p,*q; + + ASSERT(file); + ASSERT(material); + ASSERT(!material->next); + + q=0; + for (p=file->materials; p!=0; p=p->next) + { + if (strcmp(material->name, p->name)<0) + { + break; + } + q=p; + } + if (!q) + { + material->next=file->materials; + file->materials=material; + } + else + { + material->next=q->next; + q->next=material; + } +} + + +/*! + * \ingroup file + */ +void +lib3ds_file_remove_material(Lib3dsFile *file, Lib3dsMaterial *material) +{ + Lib3dsMaterial *p,*q; + + ASSERT(file); + ASSERT(material); + ASSERT(file->materials); + for (p=0,q=file->materials; q; p=q,q=q->next) + { + if (q==material) + { + break; + } + } + if (!q) + { + ASSERT(LIB3DS_FALSE); + return; + } + if (!p) + { + file->materials=material->next; + } + else + { + p->next=q->next; + } + material->next=0; +} + + +/*! + * \ingroup file + */ +Lib3dsMaterial* +lib3ds_file_material_by_name(Lib3dsFile *file, const char *name) +{ + Lib3dsMaterial *p; + + ASSERT(file); + for (p=file->materials; p!=0; p=p->next) + { + if (strcmp(p->name,name)==0) + { + return(p); + } + } + return(0); +} + + +/*! + * \ingroup file + */ +void +lib3ds_file_dump_materials(Lib3dsFile *file) +{ + Lib3dsMaterial *p; + + ASSERT(file); + for (p=file->materials; p!=0; p=p->next) + { + lib3ds_material_dump(p); + } +} + + +/*! + * \ingroup file + */ +void +lib3ds_file_insert_mesh(Lib3dsFile *file, Lib3dsMesh *mesh) +{ + Lib3dsMesh *p,*q; + + ASSERT(file); + ASSERT(mesh); + ASSERT(!mesh->next); + + q=0; + for (p=file->meshes; p!=0; p=p->next) + { + if (strcmp(mesh->name, p->name)<0) + { + break; + } + q=p; + } + if (!q) + { + mesh->next=file->meshes; + file->meshes=mesh; + } + else + { + mesh->next=q->next; + q->next=mesh; + } +} + + +/*! + * \ingroup file + */ +void +lib3ds_file_remove_mesh(Lib3dsFile *file, Lib3dsMesh *mesh) +{ + Lib3dsMesh *p,*q; + + ASSERT(file); + ASSERT(mesh); + ASSERT(file->meshes); + for (p=0,q=file->meshes; q; p=q,q=q->next) + { + if (q==mesh) + { + break; + } + } + if (!q) + { + ASSERT(LIB3DS_FALSE); + return; + } + if (!p) + { + file->meshes=mesh->next; + } + else + { + p->next=q->next; + } + mesh->next=0; +} + + +/*! + * \ingroup file + */ +Lib3dsMesh* +lib3ds_file_mesh_by_name(Lib3dsFile *file, const char *name) +{ + Lib3dsMesh *p; + + ASSERT(file); + for (p=file->meshes; p!=0; p=p->next) + { + if (strcmp(p->name,name)==0) + { + return(p); + } + } + return(0); +} + + +/*! + * \ingroup file + */ +void +lib3ds_file_dump_meshes(Lib3dsFile *file) +{ + Lib3dsMesh *p; + + ASSERT(file); + for (p=file->meshes; p!=0; p=p->next) + { + lib3ds_mesh_dump(p); + } +} + + +static void +dump_instances(Lib3dsNode *node, const char* parent) +{ + Lib3dsNode *p; + char name[255]; + + ASSERT(node); + ASSERT(parent); + strcpy(name, parent); + strcat(name, "."); + strcat(name, node->name); + if (node->type==LIB3DS_OBJECT_NODE) + { + printf(" %s : %s\n", name, node->data.object.instance); + } + for (p=node->childs; p!=0; p=p->next) + { + dump_instances(p, parent); + } +} + + +/*! + * \ingroup file + */ +void +lib3ds_file_dump_instances(Lib3dsFile *file) +{ + Lib3dsNode *p; + + ASSERT(file); + for (p=file->nodes; p!=0; p=p->next) + { + dump_instances(p,""); + } +} + + +/*! + * \ingroup file + */ +void +lib3ds_file_insert_camera(Lib3dsFile *file, Lib3dsCamera *camera) +{ + Lib3dsCamera *p,*q; + + ASSERT(file); + ASSERT(camera); + ASSERT(!camera->next); + + q=0; + for (p=file->cameras; p!=0; p=p->next) + { + if (strcmp(camera->name, p->name)<0) + { + break; + } + q=p; + } + if (!q) + { + camera->next=file->cameras; + file->cameras=camera; + } + else + { + camera->next=q->next; + q->next=camera; + } +} + + +/*! + * \ingroup file + */ +void +lib3ds_file_remove_camera(Lib3dsFile *file, Lib3dsCamera *camera) +{ + Lib3dsCamera *p,*q; + + ASSERT(file); + ASSERT(camera); + ASSERT(file->cameras); + for (p=0,q=file->cameras; q; p=q,q=q->next) + { + if (q==camera) + { + break; + } + } + if (!q) + { + ASSERT(LIB3DS_FALSE); + return; + } + if (!p) + { + file->cameras=camera->next; + } + else + { + p->next=q->next; + } + camera->next=0; +} + + +/*! + * \ingroup file + */ +Lib3dsCamera* +lib3ds_file_camera_by_name(Lib3dsFile *file, const char *name) +{ + Lib3dsCamera *p; + + ASSERT(file); + for (p=file->cameras; p!=0; p=p->next) + { + if (strcmp(p->name,name)==0) + { + return(p); + } + } + return(0); +} + + +/*! + * \ingroup file + */ +void +lib3ds_file_dump_cameras(Lib3dsFile *file) +{ + Lib3dsCamera *p; + + ASSERT(file); + for (p=file->cameras; p!=0; p=p->next) + { + printf(" %s\n", p->name); + } +} + + +/*! + * \ingroup file + */ +void +lib3ds_file_insert_light(Lib3dsFile *file, Lib3dsLight *light) +{ + Lib3dsLight *p,*q; + + ASSERT(file); + ASSERT(light); + ASSERT(!light->next); + + q=0; + for (p=file->lights; p!=0; p=p->next) + { + if (strcmp(light->name, p->name)<0) + { + break; + } + q=p; + } + if (!q) + { + light->next=file->lights; + file->lights=light; + } + else + { + light->next=q->next; + q->next=light; + } +} + + +/*! + * \ingroup file + */ +void +lib3ds_file_remove_light(Lib3dsFile *file, Lib3dsLight *light) +{ + Lib3dsLight *p,*q; + + ASSERT(file); + ASSERT(light); + ASSERT(file->lights); + for (p=0,q=file->lights; q; p=q,q=q->next) + { + if (q==light) + { + break; + } + } + if (!q) + { + ASSERT(LIB3DS_FALSE); + return; + } + if (!p) + { + file->lights=light->next; + } + else + { + p->next=q->next; + } + light->next=0; +} + + +/*! + * \ingroup file + */ +Lib3dsLight* +lib3ds_file_light_by_name(Lib3dsFile *file, const char *name) +{ + Lib3dsLight *p; + + ASSERT(file); + for (p=file->lights; p!=0; p=p->next) + { + if (strcmp(p->name,name)==0) + { + return(p); + } + } + return(0); +} + + +/*! + * \ingroup file + */ +void +lib3ds_file_dump_lights(Lib3dsFile *file) +{ + Lib3dsLight *p; + + ASSERT(file); + for (p=file->lights; p!=0; p=p->next) + { + printf(" %s\n", p->name); + } +} + + +/*! + * \ingroup file + */ +Lib3dsNode* +lib3ds_file_node_by_name(Lib3dsFile *file, const char* name, Lib3dsNodeTypes type) +{ + Lib3dsNode *p,*q; + + ASSERT(file); + for (p=file->nodes; p!=0; p=p->next) + { + if ((p->type==type) && (strcmp(p->name, name)==0)) + { + return(p); + } + q=lib3ds_node_by_name(p, name, type); + if (q) + { + return(q); + } + } + return(0); +} + + +/*! + * \ingroup file + */ +Lib3dsNode* +lib3ds_file_node_by_id(Lib3dsFile *file, Lib3dsWord id) +{ + Lib3dsNode *p,*q; + + ASSERT(file); + for (p=file->nodes; p!=0; p=p->next) + { + if (p->id==id) + { + return(p); + } + q=lib3ds_node_by_id(p, id); + if (q) + { + return(q); + } + } + return(0); +} + + +/*! + * \ingroup file + */ +void +lib3ds_file_insert_node(Lib3dsFile *file, Lib3dsNode *node) +{ + Lib3dsNode *parent,*p,*n; + + ASSERT(node); + ASSERT(!node->next); + ASSERT(!node->parent); + + parent=0; + if (node->parent_id!=LIB3DS_NO_PARENT) + { + parent=lib3ds_file_node_by_id(file, node->parent_id); + } + node->parent=parent; + + if (!parent) + { + for (p=0,n=file->nodes; n!=0; p=n,n=n->next) + { + if (strcmp(n->name, node->name)>0) + { + break; + } + } + if (!p) + { + node->next=file->nodes; + file->nodes=node; + } + else + { + node->next=p->next; + p->next=node; + } + } + else + { + for (p=0,n=parent->childs; n!=0; p=n,n=n->next) + { + if (strcmp(n->name, node->name)>0) + { + break; + } + } + if (!p) + { + node->next=parent->childs; + parent->childs=node; + } + else + { + node->next=p->next; + p->next=node; + } + } + + if (node->id!=LIB3DS_NO_PARENT) + { + for (n=file->nodes; n!=0; n=p) + { + p=n->next; + if (n->parent_id==node->id) + { + lib3ds_file_remove_node(file, n); + lib3ds_file_insert_node(file, n); + } + } + } +} + + +/*! + * \ingroup file + */ +Lib3dsBool +lib3ds_file_remove_node(Lib3dsFile *file, Lib3dsNode *node) +{ + Lib3dsNode *p,*n; + + if (node->parent) + { + for (p=0,n=node->parent->childs; n; p=n,n=n->next) + { + if (n==node) + { + break; + } + } + if (!n) + { + return(LIB3DS_FALSE); + } + + if (!p) + { + node->parent->childs=n->next; + } + else + { + p->next=n->next; + } + } + else + { + for (p=0,n=file->nodes; n; p=n,n=n->next) + { + if (n==node) + { + break; + } + } + if (!n) + { + return(LIB3DS_FALSE); + } + + if (!p) + { + file->nodes=n->next; + } + else + { + p->next=n->next; + } + } + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup file + */ +void +lib3ds_file_dump_nodes(Lib3dsFile *file) +{ + Lib3dsNode *p; + + ASSERT(file); + for (p=file->nodes; p!=0; p=p->next) + { + lib3ds_node_dump(p,1); + } +} + + +/*! + +\typedef Lib3dsFile + \ingroup file + \sa _Lib3dsFile + +*/ diff --git a/src/osgPlugins/lib3ds/file.h b/src/osgPlugins/lib3ds/file.h new file mode 100644 index 000000000..a64f8b2a5 --- /dev/null +++ b/src/osgPlugins/lib3ds/file.h @@ -0,0 +1,111 @@ +/* -*- c -*- */ +#ifndef INCLUDED_LIB3DS_FILE_H +#define INCLUDED_LIB3DS_FILE_H +/* + * The 3D Studio File Format Library + * Copyright (C) 1996-2001 by J.E. Hoffmann + * All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or (at + * your option) any later version. + * + * 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 Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + * + * $Id$ + */ + +#ifndef INCLUDED_LIB3DS_BACKGROUND_H +#include +#endif +#ifndef INCLUDED_LIB3DS_ATMOSPHERE_H +#include +#endif +#ifndef INCLUDED_LIB3DS_SHADOW_H +#include +#endif +#ifndef INCLUDED_LIB3DS_VIEWPORT_H +#include +#endif + +#ifdef __cplusplus +extern "C" { +#endif + +/*! + * 3ds file structure + * \ingroup file + */ +struct _Lib3dsFile { + Lib3dsDword mesh_version; + Lib3dsWord keyf_revision; + Lib3dsFloat master_scale; + Lib3dsVector construction_plane; + Lib3dsRgb ambient; + Lib3dsShadow shadow; + Lib3dsBackground background; + Lib3dsAtmosphere atmosphere; + Lib3dsViewport viewport; + Lib3dsViewport viewport_keyf; + Lib3dsIntd frames; + Lib3dsIntd segment_from; + Lib3dsIntd segment_to; + Lib3dsIntd current_frame; + Lib3dsMaterial *materials; + Lib3dsMesh *meshes; + Lib3dsCamera *cameras; + Lib3dsLight *lights; + Lib3dsNode *nodes; +}; + +extern LIB3DSAPI Lib3dsFile* lib3ds_open(const char *filename); +extern LIB3DSAPI void lib3ds_close(Lib3dsFile *file); + +extern LIB3DSAPI Lib3dsFile* lib3ds_file_new(); +extern LIB3DSAPI void lib3ds_file_free(Lib3dsFile *file); +extern LIB3DSAPI void lib3ds_file_eval(Lib3dsFile *file, Lib3dsFloat t); + +extern LIB3DSAPI Lib3dsBool lib3ds_file_read(Lib3dsFile *file, FILE *f); +extern LIB3DSAPI Lib3dsBool lib3ds_file_write(Lib3dsFile *file, FILE *f); + +extern LIB3DSAPI void lib3ds_file_insert_material(Lib3dsFile *file, Lib3dsMaterial *material); +extern LIB3DSAPI void lib3ds_file_remove_material(Lib3dsFile *file, Lib3dsMaterial *material); +extern LIB3DSAPI Lib3dsMaterial* lib3ds_file_material_by_name(Lib3dsFile *file, const char *name); +extern LIB3DSAPI void lib3ds_file_dump_materials(Lib3dsFile *file); + +extern LIB3DSAPI void lib3ds_file_insert_mesh(Lib3dsFile *file, Lib3dsMesh *mesh); +extern LIB3DSAPI void lib3ds_file_remove_mesh(Lib3dsFile *file, Lib3dsMesh *mesh); +extern LIB3DSAPI Lib3dsMesh* lib3ds_file_mesh_by_name(Lib3dsFile *file, const char *name); +extern LIB3DSAPI void lib3ds_file_dump_meshes(Lib3dsFile *file); +extern LIB3DSAPI void lib3ds_file_dump_instances(Lib3dsFile *file); + +extern LIB3DSAPI void lib3ds_file_insert_camera(Lib3dsFile *file, Lib3dsCamera *camera); +extern LIB3DSAPI void lib3ds_file_remove_camera(Lib3dsFile *file, Lib3dsCamera *camera); +extern LIB3DSAPI Lib3dsCamera* lib3ds_file_camera_by_name(Lib3dsFile *file, const char *name); +extern LIB3DSAPI void lib3ds_file_dump_cameras(Lib3dsFile *file); + +extern LIB3DSAPI void lib3ds_file_insert_light(Lib3dsFile *file, Lib3dsLight *light); +extern LIB3DSAPI void lib3ds_file_remove_light(Lib3dsFile *file, Lib3dsLight *light); +extern LIB3DSAPI Lib3dsLight* lib3ds_file_light_by_name(Lib3dsFile *file, const char *name); +extern LIB3DSAPI void lib3ds_file_dump_lights(Lib3dsFile *file); + +extern LIB3DSAPI Lib3dsNode* lib3ds_file_node_by_name(Lib3dsFile *file, const char* name, + Lib3dsNodeTypes type); +extern LIB3DSAPI Lib3dsNode* lib3ds_file_node_by_id(Lib3dsFile *file, Lib3dsWord id); +extern LIB3DSAPI void lib3ds_file_insert_node(Lib3dsFile *file, Lib3dsNode *node); +extern LIB3DSAPI Lib3dsBool lib3ds_file_remove_node(Lib3dsFile *file, Lib3dsNode *node); +extern LIB3DSAPI void lib3ds_file_dump_nodes(Lib3dsFile *file); + +#ifdef __cplusplus +}; +#endif +#endif + diff --git a/src/osgPlugins/lib3ds/lib3ds_float.cpp b/src/osgPlugins/lib3ds/lib3ds_float.cpp new file mode 100644 index 000000000..2124d5342 --- /dev/null +++ b/src/osgPlugins/lib3ds/lib3ds_float.cpp @@ -0,0 +1,44 @@ +/* + * The 3D Studio File Format Library + * Copyright (C) 1996-2001 by J.E. Hoffmann + * All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or (at + * your option) any later version. + * + * 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 Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + * + * $Id$ + */ +#define LIB3DS_EXPORT +#include + +/*! + * \defgroup float Floating Point Mathematics + * + * \author J.E. Hoffmann + */ + +/*! + * \ingroup float + */ +Lib3dsFloat +lib3ds_float_cubic(Lib3dsFloat a, Lib3dsFloat p, Lib3dsFloat q, Lib3dsFloat b, Lib3dsFloat t) +{ + Lib3dsDouble x,y,z,w; + + x=2*t*t*t - 3*t*t + 1; + y=-2*t*t*t + 3*t*t; + z=t*t*t - 2*t*t + t; + w=t*t*t - t*t; + return((Lib3dsFloat)(x*a + y*b + z*p + w*q)); +} diff --git a/src/osgPlugins/lib3ds/lib3ds_float.h b/src/osgPlugins/lib3ds/lib3ds_float.h new file mode 100644 index 000000000..b8dc1a213 --- /dev/null +++ b/src/osgPlugins/lib3ds/lib3ds_float.h @@ -0,0 +1,41 @@ +/* -*- c -*- */ +#ifndef INCLUDED_LIB3DS_FLOAT_H +#define INCLUDED_LIB3DS_FLOAT_H +/* + * The 3D Studio File Format Library + * Copyright (C) 1996-2001 by J.E. Hoffmann + * All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or (at + * your option) any later version. + * + * 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 Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + * + * $Id$ + */ + +#ifndef INCLUDED_LIB3DS_TYPES_H +#include +#endif + +#ifdef __cplusplus +extern "C" { +#endif + +extern LIB3DSAPI Lib3dsFloat lib3ds_float_cubic(Lib3dsFloat a, Lib3dsFloat p, + Lib3dsFloat q, Lib3dsFloat b, Lib3dsFloat t); + +#ifdef __cplusplus +}; +#endif +#endif + diff --git a/src/osgPlugins/lib3ds/light.cpp b/src/osgPlugins/lib3ds/light.cpp new file mode 100644 index 000000000..ddccc5642 --- /dev/null +++ b/src/osgPlugins/lib3ds/light.cpp @@ -0,0 +1,378 @@ +/* + * The 3D Studio File Format Library + * Copyright (C) 1996-2001 by J.E. Hoffmann + * All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or (at + * your option) any later version. + * + * 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 Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + * + * $Id$ + */ +#define LIB3DS_EXPORT +#include +#include +#include +#include +#include +#include +//#include +#ifdef WITH_DMALLOC +#include +#endif + +/*! + * \defgroup light Lights + * + * \author J.E. Hoffmann + */ + +/*! + * \ingroup light + */ +Lib3dsLight* +lib3ds_light_new(const char *name) +{ + Lib3dsLight *light; + + ASSERT(name); + ASSERT(strlen(name)<64); + + light=(Lib3dsLight*)calloc(sizeof(Lib3dsLight), 1); + if (!light) + { + return(0); + } + strcpy(light->name, name); + return(light); +} + + +/*! + * \ingroup light + */ +void +lib3ds_light_free(Lib3dsLight *light) +{ + memset(light, 0, sizeof(Lib3dsLight)); + free(light); +} + + +/*! + * \ingroup light + */ +Lib3dsBool +lib3ds_light_read(Lib3dsLight *light, FILE *f) +{ + Lib3dsChunk c; + Lib3dsWord chunk; + + if (!lib3ds_chunk_read_start(&c, LIB3DS_N_DIRECT_LIGHT, f)) + { + return(LIB3DS_FALSE); + } + { + int i; + for (i=0; i<3; ++i) + { + light->position[i]=lib3ds_float_read(f); + } + } + lib3ds_chunk_read_tell(&c, f); + + while ((chunk=lib3ds_chunk_read_next(&c, f))!=0) + { + switch (chunk) + { + case LIB3DS_COLOR_F: + { + int i; + for (i=0; i<3; ++i) + { + light->color[i]=lib3ds_float_read(f); + } + } + break; + case LIB3DS_DL_OFF: + { + light->off=LIB3DS_TRUE; + } + break; + case LIB3DS_DL_OUTER_RANGE: + { + light->outer_range=lib3ds_float_read(f); + } + break; + case LIB3DS_DL_INNER_RANGE: + { + light->inner_range=lib3ds_float_read(f); + } + break; + case LIB3DS_DL_MULTIPLIER: + { + light->multiplier=lib3ds_float_read(f); + } + break; + case LIB3DS_DL_EXCLUDE: + { + /* FIXME: */ + lib3ds_chunk_unknown(chunk); + } + case LIB3DS_DL_ATTENUATE: + { + light->attenuation=lib3ds_float_read(f); + } + break; + case LIB3DS_DL_SPOTLIGHT: + { + int i; + light->spot_light=LIB3DS_TRUE; + for (i=0; i<3; ++i) + { + light->spot[i]=lib3ds_float_read(f); + } + light->hot_spot=lib3ds_float_read(f); + light->fall_off=lib3ds_float_read(f); + } + break; + case LIB3DS_DL_SPOT_ROLL: + { + light->roll=lib3ds_float_read(f); + } + break; + case LIB3DS_DL_SHADOWED: + { + light->shadowed=LIB3DS_TRUE; + } + break; + case LIB3DS_DL_LOCAL_SHADOW2: + { + light->shadow_bias=lib3ds_float_read(f); + light->shadow_filter=lib3ds_float_read(f); + light->shadow_size=lib3ds_intw_read(f); + } + break; + case LIB3DS_DL_SEE_CONE: + { + light->see_cone=LIB3DS_TRUE; + } + break; + case LIB3DS_DL_SPOT_RECTANGULAR: + { + light->rectangular_spot=LIB3DS_TRUE; + } + break; + case LIB3DS_DL_SPOT_ASPECT: + { + light->spot_aspect=lib3ds_float_read(f); + } + break; + case LIB3DS_DL_SPOT_PROJECTOR: + { + light->use_projector=LIB3DS_TRUE; + if (!lib3ds_string_read(light->projector, 64, f)) + { + return(LIB3DS_FALSE); + } + } + case LIB3DS_DL_SPOT_OVERSHOOT: + { + light->spot_overshoot=LIB3DS_TRUE; + } + break; + case LIB3DS_DL_RAY_BIAS: + { + light->ray_bias=lib3ds_float_read(f); + } + break; + case LIB3DS_DL_RAYSHAD: + { + light->ray_shadows=LIB3DS_TRUE; + } + break; + default: + lib3ds_chunk_unknown(chunk); + } + } + + lib3ds_chunk_read_end(&c, f); + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup light + */ +Lib3dsBool +lib3ds_light_write(Lib3dsLight *light, FILE *f) +{ + Lib3dsChunk c; + + c.chunk=LIB3DS_N_DIRECT_LIGHT; + if (!lib3ds_chunk_write_start(&c,f)) + { + return(LIB3DS_FALSE); + } + lib3ds_vector_write(light->position, f); + { /*---- LIB3DS_COLOR_F ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_COLOR_F; + c.size=18; + lib3ds_chunk_write(&c, f); + lib3ds_rgb_write(light->color,f); + } + if (light->off) /*---- LIB3DS_DL_OFF ----*/ + { + Lib3dsChunk c; + c.chunk=LIB3DS_DL_OFF; + c.size=6; + lib3ds_chunk_write(&c, f); + } + { /*---- LIB3DS_DL_OUTER_RANGE ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_DL_OUTER_RANGE; + c.size=10; + lib3ds_chunk_write(&c, f); + lib3ds_float_write(light->outer_range,f); + } + { /*---- LIB3DS_DL_INNER_RANGE ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_DL_INNER_RANGE; + c.size=10; + lib3ds_chunk_write(&c, f); + lib3ds_float_write(light->inner_range,f); + } + { /*---- LIB3DS_DL_MULTIPLIER ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_DL_MULTIPLIER; + c.size=10; + lib3ds_chunk_write(&c, f); + lib3ds_float_write(light->multiplier, f); + } + if (light->attenuation) /*---- LIB3DS_DL_ATTENUATE ----*/ + { + Lib3dsChunk c; + c.chunk=LIB3DS_DL_ATTENUATE; + c.size=6; + lib3ds_chunk_write(&c, f); + } + + if (light->spot_light) + { + Lib3dsChunk c; + + c.chunk=LIB3DS_DL_SPOTLIGHT; + if (!lib3ds_chunk_write_start(&c,f)) + { + return(LIB3DS_FALSE); + } + lib3ds_vector_write(light->spot, f); + lib3ds_float_write(light->hot_spot, f); + lib3ds_float_write(light->fall_off, f); + + { /*---- LIB3DS_DL_SPOT_ROLL ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_DL_SPOT_ROLL; + c.size=10; + lib3ds_chunk_write(&c, f); + lib3ds_float_write(light->roll,f); + } + if (light->shadowed) /*---- LIB3DS_DL_SHADOWED ----*/ + { + Lib3dsChunk c; + c.chunk=LIB3DS_DL_SHADOWED; + c.size=6; + lib3ds_chunk_write(&c, f); + } + { /*---- LIB3DS_DL_LOCAL_SHADOW2 ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_DL_LOCAL_SHADOW2; + c.size=16; + lib3ds_chunk_write(&c, f); + lib3ds_float_write(light->shadow_bias,f); + lib3ds_float_write(light->shadow_filter,f); + lib3ds_intw_write(light->shadow_size,f); + } + if (light->see_cone) /*---- LIB3DS_DL_SEE_CONE ----*/ + { + Lib3dsChunk c; + c.chunk=LIB3DS_DL_SEE_CONE; + c.size=6; + lib3ds_chunk_write(&c, f); + } + /*---- LIB3DS_DL_SPOT_RECTANGULAR ----*/ + if (light->rectangular_spot) + { + Lib3dsChunk c; + c.chunk=LIB3DS_DL_SPOT_RECTANGULAR; + c.size=6; + lib3ds_chunk_write(&c, f); + } + { /*---- LIB3DS_DL_SPOT_ASPECT ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_DL_SPOT_ASPECT; + c.size=10; + lib3ds_chunk_write(&c, f); + lib3ds_float_write(light->spot_aspect,f); + } + if (light->use_projector)/*---- LIB3DS_DL_SPOT_PROJECTOR ----*/ + { + Lib3dsChunk c; + c.chunk=LIB3DS_DL_SPOT_PROJECTOR; + c.size=10; + lib3ds_chunk_write(&c, f); + lib3ds_string_write(light->projector,f); + } + /*---- LIB3DS_DL_SPOT_OVERSHOOT ----*/ + if (light->spot_overshoot) + { + Lib3dsChunk c; + c.chunk=LIB3DS_DL_SPOT_OVERSHOOT; + c.size=6; + lib3ds_chunk_write(&c, f); + } + { /*---- LIB3DS_DL_RAY_BIAS ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_DL_RAY_BIAS; + c.size=10; + lib3ds_chunk_write(&c, f); + lib3ds_float_write(light->ray_bias,f); + } + if (light->ray_shadows) /*---- LIB3DS_DL_RAYSHAD ----*/ + { + Lib3dsChunk c; + c.chunk=LIB3DS_DL_RAYSHAD; + c.size=6; + lib3ds_chunk_write(&c, f); + } + if (!lib3ds_chunk_write_end(&c,f)) + { + return(LIB3DS_FALSE); + } + } + if (!lib3ds_chunk_write_end(&c,f)) + { + return(LIB3DS_FALSE); + } + return(LIB3DS_TRUE); +} + + +/*! + +\typedef Lib3dsLight + \ingroup light + \sa _Lib3dsLight + +*/ diff --git a/src/osgPlugins/lib3ds/light.h b/src/osgPlugins/lib3ds/light.h new file mode 100644 index 000000000..8d981dc07 --- /dev/null +++ b/src/osgPlugins/lib3ds/light.h @@ -0,0 +1,77 @@ +/* -*- c -*- */ +#ifndef INCLUDED_LIB3DS_LIGHT_H +#define INCLUDED_LIB3DS_LIGHT_H +/* + * The 3D Studio File Format Library + * Copyright (C) 1996-2001 by J.E. Hoffmann + * All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or (at + * your option) any later version. + * + * 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 Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + * + * $Id$ + */ + +#ifndef INCLUDED_LIB3DS_TYPES_H +#include +#endif + +#ifdef __cplusplus +extern "C" { +#endif + +/*! + * Light + * \ingroup light + */ +struct _Lib3dsLight { + Lib3dsLight *next; + char name[64]; + Lib3dsBool spot_light; + Lib3dsBool see_cone; + Lib3dsRgb color; + Lib3dsVector position; + Lib3dsVector spot; + Lib3dsFloat roll; + Lib3dsBool off; + Lib3dsFloat outer_range; + Lib3dsFloat inner_range; + Lib3dsFloat multiplier; + /*const char** excludes;*/ + Lib3dsFloat attenuation; + Lib3dsBool rectangular_spot; + Lib3dsBool shadowed; + Lib3dsFloat shadow_bias; + Lib3dsFloat shadow_filter; + Lib3dsIntw shadow_size; + Lib3dsFloat spot_aspect; + Lib3dsBool use_projector; + char projector[64]; + Lib3dsIntd spot_overshoot; + Lib3dsBool ray_shadows; + Lib3dsFloat ray_bias; + Lib3dsFloat hot_spot; + Lib3dsFloat fall_off; +}; + +extern LIB3DSAPI Lib3dsLight* lib3ds_light_new(const char *name); +extern LIB3DSAPI void lib3ds_light_free(Lib3dsLight *mesh); +extern LIB3DSAPI Lib3dsBool lib3ds_light_read(Lib3dsLight *light, FILE *f); +extern LIB3DSAPI Lib3dsBool lib3ds_light_write(Lib3dsLight *light, FILE *f); + +#ifdef __cplusplus +}; +#endif +#endif + diff --git a/src/osgPlugins/lib3ds/material.cpp b/src/osgPlugins/lib3ds/material.cpp new file mode 100644 index 000000000..ed8c1920f --- /dev/null +++ b/src/osgPlugins/lib3ds/material.cpp @@ -0,0 +1,1052 @@ +/* + * The 3D Studio File Format Library + * Copyright (C) 1996-2001 by J.E. Hoffmann + * All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or (at + * your option) any later version. + * + * 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 Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + * + * $Id$ + */ +#define LIB3DS_EXPORT +#include +#include +#include +#include +#include +#include +//#include +#ifdef WITH_DMALLOC +#include +#endif + +/*! + * \defgroup material Materials + * + * \author J.E. Hoffmann + */ + +/*! + * \ingroup material + */ +Lib3dsMaterial* +lib3ds_material_new() +{ + Lib3dsMaterial *material; + + material=(Lib3dsMaterial*)calloc(sizeof(Lib3dsMaterial), 1); + if (!material) + { + return(0); + } + return(material); +} + + +/*! + * \ingroup material + */ +void +lib3ds_material_free(Lib3dsMaterial *material) +{ + memset(material, 0, sizeof(Lib3dsMaterial)); + free(material); +} + + +static Lib3dsBool +color_read(Lib3dsRgba rgb, FILE *f) +{ + Lib3dsChunk c; + Lib3dsWord chunk; + Lib3dsBool have_lin=LIB3DS_FALSE; + + if (!lib3ds_chunk_read_start(&c, 0, f)) + { + return(LIB3DS_FALSE); + } + + while ((chunk=lib3ds_chunk_read_next(&c, f))!=0) + { + switch (chunk) + { + case LIB3DS_LIN_COLOR_24: + { + int i; + for (i=0; i<3; ++i) + { + rgb[i]=1.0f*lib3ds_byte_read(f)/255.0f; + } + rgb[3]=1.0f; + } + have_lin=LIB3DS_TRUE; + break; + case LIB3DS_COLOR_24: + /* gamma corrected color chunk + replaced in 3ds R3 by LIN_COLOR_24 */ + if (!have_lin) + { + int i; + for (i=0; i<3; ++i) + { + rgb[i]=1.0f*lib3ds_byte_read(f)/255.0f; + } + rgb[3]=1.0f; + } + break; + default: + lib3ds_chunk_unknown(chunk); + } + } + + lib3ds_chunk_read_end(&c, f); + return(LIB3DS_TRUE); +} + + +static Lib3dsBool +int_percentage_read(Lib3dsFloat *p, FILE *f) +{ + Lib3dsChunk c; + Lib3dsWord chunk; + + if (!lib3ds_chunk_read_start(&c, 0, f)) + { + return(LIB3DS_FALSE); + } + + while ((chunk=lib3ds_chunk_read_next(&c, f))!=0) + { + switch (chunk) + { + case LIB3DS_INT_PERCENTAGE: + { + Lib3dsIntw i=lib3ds_intw_read(f); + *p=(Lib3dsFloat)(1.0*i/100.0); + } + break; + default: + lib3ds_chunk_unknown(chunk); + } + } + + lib3ds_chunk_read_end(&c, f); + return(LIB3DS_TRUE); +} + + +static Lib3dsBool +texture_map_read(Lib3dsTextureMap *map, FILE *f) +{ + Lib3dsChunk c; + Lib3dsWord chunk; + + if (!lib3ds_chunk_read_start(&c, 0, f)) + { + return(LIB3DS_FALSE); + } + + while ((chunk=lib3ds_chunk_read_next(&c, f))!=0) + { + switch (chunk) + { + case LIB3DS_INT_PERCENTAGE: + { + map->percent=1.0f*lib3ds_intw_read(f)/100.0f; + } + break; + case LIB3DS_MAT_MAPNAME: + { + if (!lib3ds_string_read(map->name, 64, f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_MAT_MAP_TILING: + { + map->flags=lib3ds_word_read(f); + } + break; + case LIB3DS_MAT_MAP_TEXBLUR: + { + map->blur=lib3ds_float_read(f); + } + break; + case LIB3DS_MAT_MAP_USCALE: + { + map->scale[0]=lib3ds_float_read(f); + } + break; + case LIB3DS_MAT_MAP_VSCALE: + { + map->scale[1]=lib3ds_float_read(f); + } + break; + case LIB3DS_MAT_MAP_UOFFSET: + { + map->offset[0]=lib3ds_float_read(f); + } + break; + case LIB3DS_MAT_MAP_VOFFSET: + { + map->offset[1]=lib3ds_float_read(f); + } + break; + case LIB3DS_MAT_MAP_ANG: + { + map->rotation=lib3ds_float_read(f); + } + break; + case LIB3DS_MAT_MAP_COL1: + { + map->tint_1[0]=1.0f*lib3ds_byte_read(f)/255.0f; + map->tint_1[1]=1.0f*lib3ds_byte_read(f)/255.0f; + map->tint_1[2]=1.0f*lib3ds_byte_read(f)/255.0f; + } + break; + case LIB3DS_MAT_MAP_COL2: + { + map->tint_2[0]=1.0f*lib3ds_byte_read(f)/255.0f; + map->tint_2[1]=1.0f*lib3ds_byte_read(f)/255.0f; + map->tint_2[2]=1.0f*lib3ds_byte_read(f)/255.0f; + } + break; + case LIB3DS_MAT_MAP_RCOL: + { + map->tint_r[0]=1.0f*lib3ds_byte_read(f)/255.0f; + map->tint_r[1]=1.0f*lib3ds_byte_read(f)/255.0f; + map->tint_r[2]=1.0f*lib3ds_byte_read(f)/255.0f; + } + break; + case LIB3DS_MAT_MAP_GCOL: + { + map->tint_g[0]=1.0f*lib3ds_byte_read(f)/255.0f; + map->tint_g[1]=1.0f*lib3ds_byte_read(f)/255.0f; + map->tint_g[2]=1.0f*lib3ds_byte_read(f)/255.0f; + } + break; + case LIB3DS_MAT_MAP_BCOL: + { + map->tint_b[0]=1.0f*lib3ds_byte_read(f)/255.0f; + map->tint_b[1]=1.0f*lib3ds_byte_read(f)/255.0f; + map->tint_b[2]=1.0f*lib3ds_byte_read(f)/255.0f; + } + break; + default: + lib3ds_chunk_unknown(chunk); + } + } + + lib3ds_chunk_read_end(&c, f); + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup material + */ +void +lib3ds_material_dump(Lib3dsMaterial *material) +{ + ASSERT(material); + printf(" %s\n", material->name); + printf(" Ambient: %1.2f %1.2f %1.2f\n", + material->ambient[0],material->ambient[1], material->ambient[2]); + printf(" Diffuse: %1.2f %1.2f %1.2f\n", + material->diffuse[0],material->diffuse[1], material->diffuse[2]); + printf(" Specular: %1.2f %1.2f %1.2f\n", + material->specular[0],material->specular[1], material->specular[2]); + printf(" Shininess: %1.2f\n", material->shininess); + printf(" Shin. Strength: %1.2f\n", material->shin_strength); + printf(" Shading: %d\n", material->shading); + if (*material->texture1_map.name) + { + printf(" Texture 1 Map: '%s'\n", material->texture1_map.name); + } + if (*material->texture1_mask.name) + { + printf(" Texture 1 Mask: '%s'\n", material->texture1_mask.name); + } + if (*material->texture2_map.name) + { + printf(" Texture 2 Map: '%s'\n", material->texture2_map.name); + } + if (*material->texture2_mask.name) + { + printf(" Texture 2 Mask: '%s'\n", material->texture2_mask.name); + } +} + + +/*! + * \ingroup material + */ +Lib3dsBool +lib3ds_material_read(Lib3dsMaterial *material, FILE *f) +{ + Lib3dsChunk c; + Lib3dsWord chunk; + + ASSERT(material); + if (!lib3ds_chunk_read_start(&c, LIB3DS_MAT_ENTRY, f)) + { + return(LIB3DS_FALSE); + } + + while ((chunk=lib3ds_chunk_read_next(&c, f))!=0) + { + switch (chunk) + { + case LIB3DS_MAT_NAME: + { + if (!lib3ds_string_read(material->name, 64, f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_MAT_AMBIENT: + { + lib3ds_chunk_read_reset(&c, f); + if (!color_read(material->ambient, f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_MAT_DIFFUSE: + { + lib3ds_chunk_read_reset(&c, f); + if (!color_read(material->diffuse, f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_MAT_SPECULAR: + { + lib3ds_chunk_read_reset(&c, f); + if (!color_read(material->specular, f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_MAT_SHININESS: + { + lib3ds_chunk_read_reset(&c, f); + if (!int_percentage_read(&material->shininess, f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_MAT_SHIN2PCT: + { + lib3ds_chunk_read_reset(&c, f); + if (!int_percentage_read(&material->shin_strength, f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_MAT_TRANSPARENCY: + { + lib3ds_chunk_read_reset(&c, f); + if (!int_percentage_read(&material->transparency, f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_MAT_XPFALL: + { + lib3ds_chunk_read_reset(&c, f); + if (!int_percentage_read(&material->falloff, f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_MAT_USE_XPFALL: + { + material->use_falloff=LIB3DS_TRUE; + } + break; + case LIB3DS_MAT_REFBLUR: + { + lib3ds_chunk_read_reset(&c, f); + if (!int_percentage_read(&material->blur, f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_MAT_USE_REFBLUR: + { + material->use_blur=LIB3DS_TRUE; + } + break; + case LIB3DS_MAT_SHADING: + { + material->shading=lib3ds_intw_read(f); + } + break; + case LIB3DS_MAT_SELF_ILLUM: + { + material->self_illum=LIB3DS_TRUE; + } + break; + case LIB3DS_MAT_TWO_SIDE: + { + material->two_sided=LIB3DS_TRUE; + } + break; + case LIB3DS_MAT_DECAL: + { + material->map_decal=LIB3DS_TRUE; + } + break; + case LIB3DS_MAT_ADDITIVE: + { + material->additive=LIB3DS_TRUE; + } + break; + case LIB3DS_MAT_FACEMAP: + { + material->face_map=LIB3DS_TRUE; + } + break; + case LIB3DS_MAT_PHONGSOFT: + { + material->soften=LIB3DS_TRUE; + } + break; + case LIB3DS_MAT_WIRE: + { + material->use_wire=LIB3DS_TRUE; + } + break; + case LIB3DS_MAT_WIREABS: + { + material->use_wire_abs=LIB3DS_TRUE; + } + break; + case LIB3DS_MAT_WIRE_SIZE: + { + material->wire_size=lib3ds_float_read(f); + } + break; + case LIB3DS_MAT_TEXMAP: + { + lib3ds_chunk_read_reset(&c, f); + if (!texture_map_read(&material->texture1_map, f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_MAT_TEXMASK: + { + lib3ds_chunk_read_reset(&c, f); + if (!texture_map_read(&material->texture1_mask, f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_MAT_TEX2MAP: + { + lib3ds_chunk_read_reset(&c, f); + if (!texture_map_read(&material->texture2_map, f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_MAT_TEX2MASK: + { + lib3ds_chunk_read_reset(&c, f); + if (!texture_map_read(&material->texture2_mask, f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_MAT_OPACMAP: + { + lib3ds_chunk_read_reset(&c, f); + if (!texture_map_read(&material->opacity_map, f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_MAT_OPACMASK: + { + lib3ds_chunk_read_reset(&c, f); + if (!texture_map_read(&material->opacity_mask, f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_MAT_BUMPMAP: + { + lib3ds_chunk_read_reset(&c, f); + if (!texture_map_read(&material->bump_map, f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_MAT_BUMPMASK: + { + lib3ds_chunk_read_reset(&c, f); + if (!texture_map_read(&material->bump_mask, f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_MAT_SPECMAP: + { + lib3ds_chunk_read_reset(&c, f); + if (!texture_map_read(&material->specular_map, f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_MAT_SPECMASK: + { + lib3ds_chunk_read_reset(&c, f); + if (!texture_map_read(&material->specular_mask, f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_MAT_SHINMAP: + { + lib3ds_chunk_read_reset(&c, f); + if (!texture_map_read(&material->shininess_map, f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_MAT_SHINMASK: + { + lib3ds_chunk_read_reset(&c, f); + if (!texture_map_read(&material->shininess_mask, f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_MAT_SELFIMAP: + { + lib3ds_chunk_read_reset(&c, f); + if (!texture_map_read(&material->self_illum_map, f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_MAT_SELFIMASK: + { + lib3ds_chunk_read_reset(&c, f); + if (!texture_map_read(&material->self_illum_mask, f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_MAT_REFLMAP: + { + lib3ds_chunk_read_reset(&c, f); + if (!texture_map_read(&material->reflection_map, f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_MAT_REFLMASK: + { + lib3ds_chunk_read_reset(&c, f); + if (!texture_map_read(&material->reflection_mask, f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_MAT_ACUBIC: + { + lib3ds_intb_read(f); + material->autorefl_map.level=lib3ds_intb_read(f); + material->autorefl_map.flags=lib3ds_intw_read(f); + material->autorefl_map.size=lib3ds_intd_read(f); + material->autorefl_map.frame_step=lib3ds_intd_read(f); + } + break; + default: + lib3ds_chunk_unknown(chunk); + } + } + + lib3ds_chunk_read_end(&c, f); + return(LIB3DS_TRUE); +} + + +static Lib3dsBool +color_write(Lib3dsRgba rgb, FILE *f) +{ + Lib3dsChunk c; + + c.chunk=LIB3DS_COLOR_24; + c.size=9; + lib3ds_chunk_write(&c,f); + lib3ds_byte_write((Lib3dsByte)floor(255.0*rgb[0]+0.5),f); + lib3ds_byte_write((Lib3dsByte)floor(255.0*rgb[1]+0.5),f); + lib3ds_byte_write((Lib3dsByte)floor(255.0*rgb[2]+0.5),f); + + c.chunk=LIB3DS_LIN_COLOR_24; + c.size=9; + lib3ds_chunk_write(&c,f); + lib3ds_byte_write((Lib3dsByte)floor(255.0*rgb[0]+0.5),f); + lib3ds_byte_write((Lib3dsByte)floor(255.0*rgb[1]+0.5),f); + lib3ds_byte_write((Lib3dsByte)floor(255.0*rgb[2]+0.5),f); + + return(LIB3DS_TRUE); +} + + +static Lib3dsBool +int_percentage_write(Lib3dsFloat p, FILE *f) +{ + Lib3dsChunk c; + + c.chunk=LIB3DS_INT_PERCENTAGE; + c.size=8; + lib3ds_chunk_write(&c,f); + lib3ds_intw_write((Lib3dsByte)floor(100.0*p+0.5),f); + + return(LIB3DS_TRUE); +} + + +static Lib3dsBool +texture_map_write(Lib3dsWord chunk, Lib3dsTextureMap *map, FILE *f) +{ + Lib3dsChunk c; + + if (strlen(map->name)==0) + { + return(LIB3DS_TRUE); + } + c.chunk=chunk; + if (!lib3ds_chunk_write_start(&c,f)) + { + return(LIB3DS_FALSE); + } + + int_percentage_write(map->percent,f); + + { /*---- LIB3DS_MAT_MAPNAME ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_MAT_MAPNAME; + c.size=6+strlen(map->name)+1; + lib3ds_chunk_write(&c,f); + lib3ds_string_write(map->name,f); + } + + { /*---- LIB3DS_MAT_MAP_TILING ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_MAT_MAP_TILING; + c.size=8; + lib3ds_chunk_write(&c,f); + lib3ds_word_write((Lib3dsWord)map->flags,f); + } + + { /*---- LIB3DS_MAT_MAP_TEXBLUR ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_MAT_MAP_TEXBLUR; + c.size=10; + lib3ds_chunk_write(&c,f); + lib3ds_float_write(map->blur,f); + } + + { /*---- LIB3DS_MAT_MAP_USCALE ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_MAT_MAP_USCALE; + c.size=10; + lib3ds_chunk_write(&c,f); + lib3ds_float_write(map->scale[0],f); + } + + { /*---- LIB3DS_MAT_MAP_VSCALE ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_MAT_MAP_VSCALE; + c.size=10; + lib3ds_chunk_write(&c,f); + lib3ds_float_write(map->scale[1],f); + } + + { /*---- LIB3DS_MAT_MAP_UOFFSET ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_MAT_MAP_UOFFSET; + c.size=10; + lib3ds_chunk_write(&c,f); + lib3ds_float_write(map->offset[0],f); + } + + { /*---- LIB3DS_MAT_MAP_VOFFSET ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_MAT_MAP_VOFFSET; + c.size=10; + lib3ds_chunk_write(&c,f); + lib3ds_float_write(map->offset[1],f); + } + + { /*---- LIB3DS_MAT_MAP_ANG ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_MAT_MAP_ANG; + c.size=10; + lib3ds_chunk_write(&c,f); + lib3ds_float_write(map->rotation,f); + } + + { /*---- LIB3DS_MAT_MAP_COL1 ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_MAT_MAP_COL1; + c.size=9; + lib3ds_chunk_write(&c,f); + lib3ds_byte_write((Lib3dsByte)floor(255.0*map->tint_1[0]+0.5), f); + lib3ds_byte_write((Lib3dsByte)floor(255.0*map->tint_1[1]+0.5), f); + lib3ds_byte_write((Lib3dsByte)floor(255.0*map->tint_1[2]+0.5), f); + } + + { /*---- LIB3DS_MAT_MAP_COL2 ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_MAT_MAP_COL2; + c.size=9; + lib3ds_chunk_write(&c,f); + lib3ds_byte_write((Lib3dsByte)floor(255.0*map->tint_2[0]+0.5), f); + lib3ds_byte_write((Lib3dsByte)floor(255.0*map->tint_2[1]+0.5), f); + lib3ds_byte_write((Lib3dsByte)floor(255.0*map->tint_2[2]+0.5), f); + } + + { /*---- LIB3DS_MAT_MAP_RCOL ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_MAT_MAP_RCOL; + c.size=9; + lib3ds_chunk_write(&c,f); + lib3ds_byte_write((Lib3dsByte)floor(255.0*map->tint_r[0]+0.5), f); + lib3ds_byte_write((Lib3dsByte)floor(255.0*map->tint_r[1]+0.5), f); + lib3ds_byte_write((Lib3dsByte)floor(255.0*map->tint_r[2]+0.5), f); + } + + { /*---- LIB3DS_MAT_MAP_GCOL ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_MAT_MAP_GCOL; + c.size=9; + lib3ds_chunk_write(&c,f); + lib3ds_byte_write((Lib3dsByte)floor(255.0*map->tint_g[0]+0.5), f); + lib3ds_byte_write((Lib3dsByte)floor(255.0*map->tint_g[1]+0.5), f); + lib3ds_byte_write((Lib3dsByte)floor(255.0*map->tint_g[2]+0.5), f); + } + + { /*---- LIB3DS_MAT_MAP_BCOL ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_MAT_MAP_BCOL; + c.size=9; + lib3ds_chunk_write(&c,f); + lib3ds_byte_write((Lib3dsByte)floor(255.0*map->tint_b[0]+0.5), f); + lib3ds_byte_write((Lib3dsByte)floor(255.0*map->tint_b[1]+0.5), f); + lib3ds_byte_write((Lib3dsByte)floor(255.0*map->tint_b[2]+0.5), f); + } + + if (!lib3ds_chunk_write_end(&c,f)) + { + return(LIB3DS_FALSE); + } + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup material + */ +Lib3dsBool +lib3ds_material_write(Lib3dsMaterial *material, FILE *f) +{ + Lib3dsChunk c; + + c.chunk=LIB3DS_MAT_ENTRY; + if (!lib3ds_chunk_write_start(&c,f)) + { + return(LIB3DS_FALSE); + } + + { /*---- LIB3DS_MAT_NAME ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_MAT_NAME; + c.size=6+strlen(material->name)+1; + lib3ds_chunk_write(&c,f); + lib3ds_string_write(material->name,f); + } + + { /*---- LIB3DS_MAT_AMBIENT ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_MAT_AMBIENT; + c.size=24; + lib3ds_chunk_write(&c,f); + color_write(material->ambient,f); + } + + { /*---- LIB3DS_MAT_DIFFUSE ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_MAT_DIFFUSE; + c.size=24; + lib3ds_chunk_write(&c,f); + color_write(material->diffuse,f); + } + + { /*---- LIB3DS_MAT_SPECULAR ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_MAT_SPECULAR; + c.size=24; + lib3ds_chunk_write(&c,f); + color_write(material->specular,f); + } + + { /*---- LIB3DS_MAT_SHININESS ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_MAT_SHININESS; + c.size=14; + lib3ds_chunk_write(&c,f); + int_percentage_write(material->shininess,f); + } + + { /*---- LIB3DS_MAT_SHIN2PCT ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_MAT_SHIN2PCT; + c.size=14; + lib3ds_chunk_write(&c,f); + int_percentage_write(material->shin_strength,f); + } + + { /*---- LIB3DS_MAT_TRANSPARENCY ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_MAT_TRANSPARENCY; + c.size=14; + lib3ds_chunk_write(&c,f); + int_percentage_write(material->transparency,f); + } + + { /*---- LIB3DS_MAT_XPFALL ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_MAT_XPFALL; + c.size=14; + lib3ds_chunk_write(&c,f); + int_percentage_write(material->falloff,f); + } + + if (material->use_falloff) /*---- LIB3DS_MAT_USE_XPFALL ----*/ + { + Lib3dsChunk c; + c.chunk=LIB3DS_MAT_USE_XPFALL; + c.size=6; + lib3ds_chunk_write(&c,f); + } + + { /*---- LIB3DS_MAT_SHADING ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_MAT_SHADING; + c.size=8; + lib3ds_chunk_write(&c,f); + lib3ds_intw_write(material->shading,f); + } + + { /*---- LIB3DS_MAT_REFBLUR ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_MAT_REFBLUR; + c.size=14; + lib3ds_chunk_write(&c,f); + int_percentage_write(material->blur,f); + } + + if (material->use_blur) /*---- LIB3DS_MAT_USE_REFBLUR ----*/ + { + Lib3dsChunk c; + c.chunk=LIB3DS_MAT_USE_REFBLUR; + c.size=6; + lib3ds_chunk_write(&c,f); + } + + if (material->self_illum) /*---- LIB3DS_MAT_SELF_ILLUM ----*/ + { + Lib3dsChunk c; + c.chunk=LIB3DS_MAT_SELF_ILLUM; + c.size=6; + lib3ds_chunk_write(&c,f); + } + + if (material->two_sided) /*---- LIB3DS_MAT_TWO_SIDE ----*/ + { + Lib3dsChunk c; + c.chunk=LIB3DS_MAT_TWO_SIDE; + c.size=6; + lib3ds_chunk_write(&c,f); + } + + if (material->map_decal) /*---- LIB3DS_MAT_DECAL ----*/ + { + Lib3dsChunk c; + c.chunk=LIB3DS_MAT_DECAL; + c.size=6; + lib3ds_chunk_write(&c,f); + } + + if (material->additive) /*---- LIB3DS_MAT_ADDITIVE ----*/ + { + Lib3dsChunk c; + c.chunk=LIB3DS_MAT_ADDITIVE; + c.size=6; + lib3ds_chunk_write(&c,f); + } + + if (material->use_wire) /*---- LIB3DS_MAT_WIRE ----*/ + { + Lib3dsChunk c; + c.chunk=LIB3DS_MAT_WIRE; + c.size=6; + lib3ds_chunk_write(&c,f); + } + + if (material->use_wire_abs) /*---- LIB3DS_MAT_WIREABS ----*/ + { + Lib3dsChunk c; + c.chunk=LIB3DS_MAT_WIREABS; + c.size=6; + lib3ds_chunk_write(&c,f); + } + + { /*---- LIB3DS_MAT_WIRE_SIZE ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_MAT_WIRE_SIZE; + c.size=10; + lib3ds_chunk_write(&c,f); + lib3ds_float_write(material->wire_size,f); + } + + if (material->face_map) /*---- LIB3DS_MAT_FACEMAP ----*/ + { + Lib3dsChunk c; + c.chunk=LIB3DS_MAT_FACEMAP; + c.size=6; + lib3ds_chunk_write(&c,f); + } + + if (material->soften) /*---- LIB3DS_MAT_PHONGSOFT ----*/ + { + Lib3dsChunk c; + c.chunk=LIB3DS_MAT_PHONGSOFT; + c.size=6; + lib3ds_chunk_write(&c,f); + } + + if (!texture_map_write(LIB3DS_MAT_TEXMAP, &material->texture1_map, f)) + { + return(LIB3DS_FALSE); + } + if (!texture_map_write(LIB3DS_MAT_TEXMASK, &material->texture1_mask, f)) + { + return(LIB3DS_FALSE); + } + if (!texture_map_write(LIB3DS_MAT_TEX2MAP, &material->texture2_map, f)) + { + return(LIB3DS_FALSE); + } + if (!texture_map_write(LIB3DS_MAT_TEX2MASK, &material->texture2_mask, f)) + { + return(LIB3DS_FALSE); + } + if (!texture_map_write(LIB3DS_MAT_OPACMAP, &material->opacity_map, f)) + { + return(LIB3DS_FALSE); + } + if (!texture_map_write(LIB3DS_MAT_OPACMASK, &material->opacity_mask, f)) + { + return(LIB3DS_FALSE); + } + if (!texture_map_write(LIB3DS_MAT_BUMPMAP, &material->bump_map, f)) + { + return(LIB3DS_FALSE); + } + if (!texture_map_write(LIB3DS_MAT_BUMPMASK, &material->bump_mask, f)) + { + return(LIB3DS_FALSE); + } + if (!texture_map_write(LIB3DS_MAT_SPECMAP, &material->specular_map, f)) + { + return(LIB3DS_FALSE); + } + if (!texture_map_write(LIB3DS_MAT_SPECMASK, &material->specular_mask, f)) + { + return(LIB3DS_FALSE); + } + if (!texture_map_write(LIB3DS_MAT_SHINMAP, &material->shininess_map, f)) + { + return(LIB3DS_FALSE); + } + if (!texture_map_write(LIB3DS_MAT_SHINMASK, &material->shininess_mask, f)) + { + return(LIB3DS_FALSE); + } + if (!texture_map_write(LIB3DS_MAT_SELFIMAP, &material->self_illum_map, f)) + { + return(LIB3DS_FALSE); + } + if (!texture_map_write(LIB3DS_MAT_SELFIMASK, &material->self_illum_mask, f)) + { + return(LIB3DS_FALSE); + } + if (!texture_map_write(LIB3DS_MAT_REFLMAP, &material->reflection_map, f)) + { + return(LIB3DS_FALSE); + } + if (!texture_map_write(LIB3DS_MAT_REFLMASK, &material->reflection_mask, f)) + { + return(LIB3DS_FALSE); + } + + if (!lib3ds_chunk_write_end(&c,f)) + { + return(LIB3DS_FALSE); + } + return(LIB3DS_TRUE); +} + + +/*! + +\typedef Lib3dsMaterial + \ingroup material + \sa _Lib3dsMaterial + +*/ diff --git a/src/osgPlugins/lib3ds/material.h b/src/osgPlugins/lib3ds/material.h new file mode 100644 index 000000000..3562f54f9 --- /dev/null +++ b/src/osgPlugins/lib3ds/material.h @@ -0,0 +1,168 @@ +/* -*- c -*- */ +#ifndef INCLUDED_LIB3DS_MATERIAL_H +#define INCLUDED_LIB3DS_MATERIAL_H +/* + * The 3D Studio File Format Library + * Copyright (C) 1996-2001 by J.E. Hoffmann + * All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or (at + * your option) any later version. + * + * 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 Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + * + * $Id$ + */ + +#ifndef INCLUDED_LIB3DS_TYPES_H +#include +#endif + +#ifdef __cplusplus +extern "C" { +#endif + +/*! + * \ingroup material + */ +typedef enum _Lib3dsTextureMapFlags { + LIB3DS_DECALE =0x0001, + LIB3DS_MIRROR =0x0002, + LIB3DS_NEGATE =0x0004, + LIB3DS_NO_TILE =0x0008, + LIB3DS_SUMMED_AREA =0x0010, + LIB3DS_ALPHA_SOURCE =0x0020, + LIB3DS_TINT =0x0040, + LIB3DS_IGNORE_ALPHA =0x0080, + LIB3DS_RGB_TINT =0x0100 +} Lib3dsTextureMapFlags; + +/*! + * Mateial texture map + * \ingroup material + */ +typedef struct _Lib3dsTextureMap { + char name[64]; + Lib3dsDword flags; + Lib3dsFloat percent; + Lib3dsFloat blur; + Lib3dsFloat scale[2]; + Lib3dsFloat offset[2]; + Lib3dsFloat rotation; + Lib3dsRgb tint_1; + Lib3dsRgb tint_2; + Lib3dsRgb tint_r; + Lib3dsRgb tint_g; + Lib3dsRgb tint_b; +} Lib3dsTextureMap; + +/*! + * \ingroup material + */ +typedef enum _Lib3dsAutoReflMapFlags { + LIB3DS_USE_REFL_MAP =0x0001, + LIB3DS_READ_FIRST_FRAME_ONLY =0x0004, + LIB3DS_FLAT_MIRROR =0x0008 +} Lib3dsAutoReflectionMapFlags; + +/*! + * \ingroup material + */ +typedef enum _Lib3dsAutoReflMapAntiAliasLevel { + LIB3DS_ANTI_ALIAS_NONE =0, + LIB3DS_ANTI_ALIAS_LOW =1, + LIB3DS_ANTI_ALIAS_MEDIUM =2, + LIB3DS_ANTI_ALIAS_HIGH =3 +} Lib3dsAutoReflMapAntiAliasLevel; + +/*! + * Auto reflection map settings + * \ingroup material + */ +typedef struct _Lib3dsAutoReflMap { + Lib3dsDword flags; + Lib3dsIntd level; + Lib3dsIntd size; + Lib3dsIntd frame_step; +} Lib3dsAutoReflMap; + +/*! + * \ingroup material + */ +typedef enum _Lib3dsMaterialShading { + LIB3DS_WIRE_FRAME =0, + LIB3DS_FLAT =1, + LIB3DS_GOURAUD =2, + LIB3DS_PHONG =3, + LIB3DS_METAL =4 +} Lib3dsMaterialShading; + +/*! + * Material + * \ingroup material + */ +struct _Lib3dsMaterial { + Lib3dsUserData user; + Lib3dsMaterial *next; + char name[64]; + Lib3dsRgba ambient; + Lib3dsRgba diffuse; + Lib3dsRgba specular; + Lib3dsFloat shininess; + Lib3dsFloat shin_strength; + Lib3dsBool use_blur; + Lib3dsFloat blur; + Lib3dsFloat transparency; + Lib3dsFloat falloff; + Lib3dsBool additive; + Lib3dsBool use_falloff; + Lib3dsBool self_illum; + Lib3dsIntw shading; + Lib3dsBool soften; + Lib3dsBool face_map; + Lib3dsBool two_sided; + Lib3dsBool map_decal; + Lib3dsBool use_wire; + Lib3dsBool use_wire_abs; + Lib3dsFloat wire_size; + Lib3dsTextureMap texture1_map; + Lib3dsTextureMap texture1_mask; + Lib3dsTextureMap texture2_map; + Lib3dsTextureMap texture2_mask; + Lib3dsTextureMap opacity_map; + Lib3dsTextureMap opacity_mask; + Lib3dsTextureMap bump_map; + Lib3dsTextureMap bump_mask; + Lib3dsTextureMap specular_map; + Lib3dsTextureMap specular_mask; + Lib3dsTextureMap shininess_map; + Lib3dsTextureMap shininess_mask; + Lib3dsTextureMap self_illum_map; + Lib3dsTextureMap self_illum_mask; + Lib3dsTextureMap reflection_map; + Lib3dsTextureMap reflection_mask; + Lib3dsAutoReflMap autorefl_map; +}; + +extern LIB3DSAPI Lib3dsMaterial* lib3ds_material_new(); +extern LIB3DSAPI void lib3ds_material_free(Lib3dsMaterial *material); +extern LIB3DSAPI void lib3ds_material_dump(Lib3dsMaterial *material); +extern LIB3DSAPI Lib3dsBool lib3ds_material_read(Lib3dsMaterial *material, FILE *f); +extern LIB3DSAPI Lib3dsBool lib3ds_material_write(Lib3dsMaterial *material, FILE *f); + +#ifdef __cplusplus +}; +#endif +#endif + + + diff --git a/src/osgPlugins/lib3ds/matrix.cpp b/src/osgPlugins/lib3ds/matrix.cpp new file mode 100644 index 000000000..9b8690b82 --- /dev/null +++ b/src/osgPlugins/lib3ds/matrix.cpp @@ -0,0 +1,677 @@ +/* + * The 3D Studio File Format Library + * Copyright (C) 1996-2001 by J.E. Hoffmann + * All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or (at + * your option) any later version. + * + * 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 Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + * + * $Id$ + */ +#define LIB3DS_EXPORT +#include +#include +#include +#include +#include + +/*! + * \defgroup matrix Matrix Mathematics + * + * \author J.E. Hoffmann + */ +/*! + * \typedef Lib3dsMatrix + * \ingroup matrix + */ + +/*! + * \ingroup matrix + */ +void +lib3ds_matrix_zero(Lib3dsMatrix m) +{ + int i,j; + + for (i=0; i<4; i++) + { + for (j=0; j<4; j++) m[i][j]=0.0f; + } +} + + +/*! + * \ingroup matrix + */ +void +lib3ds_matrix_identity(Lib3dsMatrix m) +{ + int i,j; + + for (i=0; i<4; i++) + { + for (j=0; j<4; j++) m[i][j]=0.0; + } + for (i=0; i<4; i++) m[i][i]=1.0; +} + + +/*! + * \ingroup matrix + */ +void +lib3ds_matrix_copy(Lib3dsMatrix dest, Lib3dsMatrix src) +{ + memcpy(dest, src, sizeof(Lib3dsMatrix)); +} + + +/*! + * \ingroup matrix + */ +void +lib3ds_matrix_neg(Lib3dsMatrix m) +{ + int i,j; + + for (j=0; j<4; j++) + { + for (i=0; i<4; i++) + { + m[j][i]=-m[j][i]; + } + } +} + + +/*! + * \ingroup matrix + */ +void +lib3ds_matrix_abs(Lib3dsMatrix m) +{ + int i,j; + + for (j=0; j<4; j++) + { + for (i=0; i<4; i++) + { + m[j][i]=(Lib3dsFloat)fabs(m[j][i]); + } + } +} + + +/*! + * \ingroup matrix + */ +void +lib3ds_matrix_transpose(Lib3dsMatrix m) +{ + int i,j; + Lib3dsFloat swp; + + for (j=0; j<4; j++) + { + for (i=j+1; i<4; i++) + { + swp=m[j][i]; + m[j][i]=m[i][j]; + m[i][j]=swp; + } + } +} + + +/*! + * \ingroup matrix + */ +void +lib3ds_matrix_add(Lib3dsMatrix m, Lib3dsMatrix a, Lib3dsMatrix b) +{ + int i,j; + + for (j=0; j<4; j++) + { + for (i=0; i<4; i++) + { + m[j][i]=a[j][i]+b[j][i]; + } + } +} + + +/*! + * \ingroup matrix + */ +void +lib3ds_matrix_sub(Lib3dsMatrix m, Lib3dsMatrix a, Lib3dsMatrix b) +{ + int i,j; + + for (j=0; j<4; j++) + { + for (i=0; i<4; i++) + { + m[j][i]=a[j][i]-b[j][i]; + } + } +} + + +/*! + * \ingroup matrix + */ +void +lib3ds_matrix_mul(Lib3dsMatrix m, Lib3dsMatrix a, Lib3dsMatrix b) +{ + int i,j,k; + Lib3dsFloat ab; + + for (j=0; j<4; j++) + { + for (i=0; i<4; i++) + { + ab=0.0f; + for (k=0; k<4; k++) ab+=a[k][i]*b[j][k]; + m[j][i]=ab; + } + } +} + + +/*! + * \ingroup matrix + */ +void +lib3ds_matrix_scalar(Lib3dsMatrix m, Lib3dsFloat k) +{ + int i,j; + + for (j=0; j<4; j++) + { + for (i=0; i<4; i++) + { + m[j][i]*=k; + } + } +} + + +static Lib3dsFloat +det2x2( +Lib3dsFloat a, Lib3dsFloat b, +Lib3dsFloat c, Lib3dsFloat d) +{ + return((a)*(d)-(b)*(c)); +} + + +static Lib3dsFloat +det3x3( +Lib3dsFloat a1, Lib3dsFloat a2, Lib3dsFloat a3, +Lib3dsFloat b1, Lib3dsFloat b2, Lib3dsFloat b3, +Lib3dsFloat c1, Lib3dsFloat c2, Lib3dsFloat c3) +{ + return( + a1*det2x2(b2,b3,c2,c3)- + b1*det2x2(a2,a3,c2,c3)+ + c1*det2x2(a2,a3,b2,b3) + ); +} + + +/*! + * \ingroup matrix + */ +Lib3dsFloat +lib3ds_matrix_det(Lib3dsMatrix m) +{ + Lib3dsFloat a1,a2,a3,a4,b1,b2,b3,b4,c1,c2,c3,c4,d1,d2,d3,d4; + + a1 = m[0][0]; + b1 = m[1][0]; + c1 = m[2][0]; + d1 = m[3][0]; + a2 = m[0][1]; + b2 = m[1][1]; + c2 = m[2][1]; + d2 = m[3][1]; + a3 = m[0][2]; + b3 = m[1][2]; + c3 = m[2][2]; + d3 = m[3][2]; + a4 = m[0][3]; + b4 = m[1][3]; + c4 = m[2][3]; + d4 = m[3][3]; + return( + a1 * det3x3(b2, b3, b4, c2, c3, c4, d2, d3, d4)- + b1 * det3x3(a2, a3, a4, c2, c3, c4, d2, d3, d4)+ + c1 * det3x3(a2, a3, a4, b2, b3, b4, d2, d3, d4)- + d1 * det3x3(a2, a3, a4, b2, b3, b4, c2, c3, c4) + ); +} + + +/*! + * \ingroup matrix + */ +void +lib3ds_matrix_adjoint(Lib3dsMatrix m) +{ + Lib3dsFloat a1,a2,a3,a4,b1,b2,b3,b4,c1,c2,c3,c4,d1,d2,d3,d4; + + a1 = m[0][0]; + b1 = m[1][0]; + c1 = m[2][0]; + d1 = m[3][0]; + a2 = m[0][1]; + b2 = m[1][1]; + c2 = m[2][1]; + d2 = m[3][1]; + a3 = m[0][2]; + b3 = m[1][2]; + c3 = m[2][2]; + d3 = m[3][2]; + a4 = m[0][3]; + b4 = m[1][3]; + c4 = m[2][3]; + d4 = m[3][3]; + m[0][0]= det3x3 (b2, b3, b4, c2, c3, c4, d2, d3, d4); + m[0][1]= -det3x3 (a2, a3, a4, c2, c3, c4, d2, d3, d4); + m[0][2]= det3x3 (a2, a3, a4, b2, b3, b4, d2, d3, d4); + m[0][3]= -det3x3 (a2, a3, a4, b2, b3, b4, c2, c3, c4); + m[1][0]= -det3x3 (b1, b3, b4, c1, c3, c4, d1, d3, d4); + m[1][1]= det3x3 (a1, a3, a4, c1, c3, c4, d1, d3, d4); + m[1][2]= -det3x3 (a1, a3, a4, b1, b3, b4, d1, d3, d4); + m[1][3]= det3x3 (a1, a3, a4, b1, b3, b4, c1, c3, c4); + m[2][0]= det3x3 (b1, b2, b4, c1, c2, c4, d1, d2, d4); + m[2][1]= -det3x3 (a1, a2, a4, c1, c2, c4, d1, d2, d4); + m[2][2]= det3x3 (a1, a2, a4, b1, b2, b4, d1, d2, d4); + m[2][3]= -det3x3 (a1, a2, a4, b1, b2, b4, c1, c2, c4); + m[3][0]= -det3x3 (b1, b2, b3, c1, c2, c3, d1, d2, d3); + m[3][1]= det3x3 (a1, a2, a3, c1, c2, c3, d1, d2, d3); + m[3][2]= -det3x3 (a1, a2, a3, b1, b2, b3, d1, d2, d3); + m[3][3]= det3x3 (a1, a2, a3, b1, b2, b3, c1, c2, c3); +} + + +/*! + * \ingroup matrix + * + * GGemsII, K.Wu, Fast Matrix Inversion + */ +Lib3dsBool +lib3ds_matrix_inv(Lib3dsMatrix m) +{ + int i,j,k; + int pvt_i[4], pvt_j[4]; /* Locations of pivot elements */ + Lib3dsFloat pvt_val; /* Value of current pivot element */ + Lib3dsFloat hold; /* Temporary storage */ + Lib3dsFloat determinat; + + determinat = 1.0f; + for (k=0; k<4; k++) + { + /* Locate k'th pivot element */ + pvt_val=m[k][k]; /* Initialize for search */ + pvt_i[k]=k; + pvt_j[k]=k; + for (i=k; i<4; i++) + { + for (j=k; j<4; j++) + { + if (fabs(m[i][j]) > fabs(pvt_val)) + { + pvt_i[k]=i; + pvt_j[k]=j; + pvt_val=m[i][j]; + } + } + } + + /* Product of pivots, gives determinant when finished */ + determinat*=pvt_val; + if (fabs(determinat)=0; k--) /* Don't need to work with 1 by 1 corner*/ + { + i=pvt_j[k]; /* Rows to swap correspond to pivot COLUMN */ + if (i!=k) /* If rows are different */ + { + for(j=0; j<4; j++) + { + hold = m[k][j]; + m[k][j]=-m[i][j]; + m[i][j]=hold; + } + } + + j=pvt_i[k]; /* Columns to swap correspond to pivot ROW */ + if (j!=k) /* If columns are different */ + for (i=0; i<4; i++) + { + hold=m[i][k]; + m[i][k]=-m[i][j]; + m[i][j]=hold; + } + } + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup matrix + */ +void +lib3ds_matrix_translate_xyz(Lib3dsMatrix m, Lib3dsFloat x, Lib3dsFloat y, Lib3dsFloat z) +{ + int i; + + for (i=0; i<3; i++) + { + m[3][i]+= m[0][i]*x + m[1][i]*y + m[2][i]*z; + } +} + + +/*! + * \ingroup matrix + */ +void +lib3ds_matrix_translate(Lib3dsMatrix m, Lib3dsVector t) +{ + int i; + + for (i=0; i<3; i++) + { + m[3][i]+= m[0][i]*t[0] + m[1][i]*t[1] + m[2][i]*t[2]; + } +} + + +/*! + * \ingroup matrix + */ +void +lib3ds_matrix_scale_xyz(Lib3dsMatrix m, Lib3dsFloat x, Lib3dsFloat y, Lib3dsFloat z) +{ + int i; + + for (i=0; i<4; i++) + { + m[0][i]*=x; + m[1][i]*=y; + m[2][i]*=z; + } +} + + +/*! + * \ingroup matrix + */ +void +lib3ds_matrix_scale(Lib3dsMatrix m, Lib3dsVector s) +{ + int i; + + for (i=0; i<4; i++) + { + m[0][i]*=s[0]; + m[1][i]*=s[1]; + m[2][i]*=s[2]; + } +} + + +/*! + * \ingroup matrix + */ +void +lib3ds_matrix_rotate_x(Lib3dsMatrix m, Lib3dsFloat phi) +{ + Lib3dsFloat SinPhi,CosPhi; + Lib3dsFloat a1[4],a2[4]; + + SinPhi=(Lib3dsFloat)sin(phi); + CosPhi=(Lib3dsFloat)cos(phi); + memcpy(a1,m[1],4*sizeof(Lib3dsFloat)); + memcpy(a2,m[2],4*sizeof(Lib3dsFloat)); + m[1][0]=CosPhi*a1[0]+SinPhi*a2[0]; + m[1][1]=CosPhi*a1[1]+SinPhi*a2[1]; + m[1][2]=CosPhi*a1[2]+SinPhi*a2[2]; + m[1][3]=CosPhi*a1[3]+SinPhi*a2[3]; + m[2][0]=-SinPhi*a1[0]+CosPhi*a2[0]; + m[2][1]=-SinPhi*a1[1]+CosPhi*a2[1]; + m[2][2]=-SinPhi*a1[2]+CosPhi*a2[2]; + m[2][3]=-SinPhi*a1[3]+CosPhi*a2[3]; +} + + +/*! + * \ingroup matrix + */ +void +lib3ds_matrix_rotate_y(Lib3dsMatrix m, Lib3dsFloat phi) +{ + Lib3dsFloat SinPhi,CosPhi; + Lib3dsFloat a0[4],a2[4]; + + SinPhi=(Lib3dsFloat)sin(phi); + CosPhi=(Lib3dsFloat)cos(phi); + memcpy(a0,m[0],4*sizeof(Lib3dsFloat)); + memcpy(a2,m[2],4*sizeof(Lib3dsFloat)); + m[0][0]=CosPhi*a0[0]-SinPhi*a2[0]; + m[0][1]=CosPhi*a0[1]-SinPhi*a2[1]; + m[0][2]=CosPhi*a0[2]-SinPhi*a2[2]; + m[0][3]=CosPhi*a0[3]-SinPhi*a2[3]; + m[2][0]=SinPhi*a0[0]+CosPhi*a2[0]; + m[2][1]=SinPhi*a0[1]+CosPhi*a2[1]; + m[2][2]=SinPhi*a0[2]+CosPhi*a2[2]; + m[2][3]=SinPhi*a0[3]+CosPhi*a2[3]; +} + + +/*! + * \ingroup matrix + */ +void +lib3ds_matrix_rotate_z(Lib3dsMatrix m, Lib3dsFloat phi) +{ + Lib3dsFloat SinPhi,CosPhi; + Lib3dsFloat a0[4],a1[4]; + + SinPhi=(Lib3dsFloat)sin(phi); + CosPhi=(Lib3dsFloat)cos(phi); + memcpy(a0,m[0],4*sizeof(Lib3dsFloat)); + memcpy(a1,m[1],4*sizeof(Lib3dsFloat)); + m[0][0]=CosPhi*a0[0]+SinPhi*a1[0]; + m[0][1]=CosPhi*a0[1]+SinPhi*a1[1]; + m[0][2]=CosPhi*a0[2]+SinPhi*a1[2]; + m[0][3]=CosPhi*a0[3]+SinPhi*a1[3]; + m[1][0]=-SinPhi*a0[0]+CosPhi*a1[0]; + m[1][1]=-SinPhi*a0[1]+CosPhi*a1[1]; + m[1][2]=-SinPhi*a0[2]+CosPhi*a1[2]; + m[1][3]=-SinPhi*a0[3]+CosPhi*a1[3]; +} + + +/*! + * \ingroup matrix + */ +void +lib3ds_matrix_rotate(Lib3dsMatrix m, Lib3dsQuat q) +{ + Lib3dsFloat s,xs,ys,zs,wx,wy,wz,xx,xy,xz,yy,yz,zz,l; + Lib3dsMatrix a,b; + + lib3ds_matrix_copy(a, m); + + l=q[0]*q[0] + q[1]*q[1] + q[2]*q[2] + q[3]*q[3]; + if (fabs(l) + * All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or (at + * your option) any later version. + * + * 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 Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + * + * $Id$ + */ + +#ifndef INCLUDED_LIB3DS_TYPES_H +#include +#endif + +#ifdef __cplusplus +extern "C" { +#endif + +extern LIB3DSAPI void lib3ds_matrix_zero(Lib3dsMatrix m); +extern LIB3DSAPI void lib3ds_matrix_identity(Lib3dsMatrix m); +extern LIB3DSAPI void lib3ds_matrix_copy(Lib3dsMatrix dest, Lib3dsMatrix src); +extern LIB3DSAPI void lib3ds_matrix_neg(Lib3dsMatrix m); +extern LIB3DSAPI void lib3ds_matrix_abs(Lib3dsMatrix m); +extern LIB3DSAPI void lib3ds_matrix_transpose(Lib3dsMatrix m); +extern LIB3DSAPI void lib3ds_matrix_add(Lib3dsMatrix m, Lib3dsMatrix a, Lib3dsMatrix b); +extern LIB3DSAPI void lib3ds_matrix_sub(Lib3dsMatrix m, Lib3dsMatrix a, Lib3dsMatrix b); +extern LIB3DSAPI void lib3ds_matrix_mul(Lib3dsMatrix m, Lib3dsMatrix a, Lib3dsMatrix b); +extern LIB3DSAPI void lib3ds_matrix_scalar(Lib3dsMatrix m, Lib3dsFloat k); +extern LIB3DSAPI Lib3dsFloat lib3ds_matrix_det(Lib3dsMatrix m); +extern LIB3DSAPI void lib3ds_matrix_adjoint(Lib3dsMatrix m); +extern LIB3DSAPI Lib3dsBool lib3ds_matrix_inv(Lib3dsMatrix m); +void lib3ds_matrix_translate_xyz(Lib3dsMatrix m, Lib3dsFloat x, + Lib3dsFloat y, Lib3dsFloat z); +extern LIB3DSAPI void lib3ds_matrix_translate(Lib3dsMatrix m, Lib3dsVector t); +extern LIB3DSAPI void lib3ds_matrix_scale_xyz(Lib3dsMatrix m, Lib3dsFloat x, + Lib3dsFloat y, Lib3dsFloat z); +extern LIB3DSAPI void lib3ds_matrix_scale(Lib3dsMatrix m, Lib3dsVector s); +extern LIB3DSAPI void lib3ds_matrix_rotate_x(Lib3dsMatrix m, Lib3dsFloat phi); +extern LIB3DSAPI void lib3ds_matrix_rotate_y(Lib3dsMatrix m, Lib3dsFloat phi); +extern LIB3DSAPI void lib3ds_matrix_rotate_z(Lib3dsMatrix m, Lib3dsFloat phi); +extern LIB3DSAPI void lib3ds_matrix_rotate(Lib3dsMatrix m, Lib3dsQuat q); +extern LIB3DSAPI void lib3ds_matrix_rotate_axis(Lib3dsMatrix m, + Lib3dsVector axis, Lib3dsFloat angle); +extern LIB3DSAPI void lib3ds_matrix_camera(Lib3dsMatrix matrix, Lib3dsVector pos, + Lib3dsVector tgt, Lib3dsFloat roll); +extern LIB3DSAPI void lib3ds_matrix_dump(Lib3dsMatrix matrix); + +#ifdef __cplusplus +}; +#endif +#endif + diff --git a/src/osgPlugins/lib3ds/mesh.cpp b/src/osgPlugins/lib3ds/mesh.cpp new file mode 100644 index 000000000..d39562090 --- /dev/null +++ b/src/osgPlugins/lib3ds/mesh.cpp @@ -0,0 +1,937 @@ +/* + * The 3D Studio File Format Library + * Copyright (C) 1996-2001 by J.E. Hoffmann + * All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or (at + * your option) any later version. + * + * 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 Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + * + * $Id$ + */ +#define LIB3DS_EXPORT +#include +#include +#include +#include +#include +#include +#include +//#include +#ifdef WITH_DMALLOC +#include +#endif + +/*! + * \defgroup mesh Meshes + * + * \author J.E. Hoffmann + */ + +static Lib3dsBool +face_array_read(Lib3dsMesh *mesh, FILE *f) +{ + Lib3dsChunk c; + Lib3dsWord chunk; + int i; + int faces; + + if (!lib3ds_chunk_read_start(&c, LIB3DS_FACE_ARRAY, f)) + { + return(LIB3DS_FALSE); + } + lib3ds_mesh_free_face_list(mesh); + + faces=lib3ds_word_read(f); + if (faces) + { + if (!lib3ds_mesh_new_face_list(mesh, faces)) + { + LIB3DS_ERROR_LOG; + return(LIB3DS_FALSE); + } + for (i=0; ifaceL[i].material, ""); + mesh->faceL[i].points[0]=lib3ds_word_read(f); + mesh->faceL[i].points[1]=lib3ds_word_read(f); + mesh->faceL[i].points[2]=lib3ds_word_read(f); + mesh->faceL[i].flags=lib3ds_word_read(f); + } + lib3ds_chunk_read_tell(&c, f); + + while ((chunk=lib3ds_chunk_read_next(&c, f))!=0) + { + switch (chunk) + { + case LIB3DS_SMOOTH_GROUP: + { + unsigned i; + + for (i=0; ifaces; ++i) + { + mesh->faceL[i].smoothing=lib3ds_dword_read(f); + } + } + break; + case LIB3DS_MSH_MAT_GROUP: + { + char name[64]; + unsigned faces; + unsigned i; + unsigned index; + + if (!lib3ds_string_read(name, 64, f)) + { + return(LIB3DS_FALSE); + } + faces=lib3ds_word_read(f); + for (i=0; ifaces); + strcpy(mesh->faceL[index].material, name); + } + } + break; + case LIB3DS_MSH_BOXMAP: + { + char name[64]; + + if (!lib3ds_string_read(name, 64, f)) + { + return(LIB3DS_FALSE); + } + strcpy(mesh->box_map.front, name); + if (!lib3ds_string_read(name, 64, f)) + { + return(LIB3DS_FALSE); + } + strcpy(mesh->box_map.back, name); + if (!lib3ds_string_read(name, 64, f)) + { + return(LIB3DS_FALSE); + } + strcpy(mesh->box_map.left, name); + if (!lib3ds_string_read(name, 64, f)) + { + return(LIB3DS_FALSE); + } + strcpy(mesh->box_map.right, name); + if (!lib3ds_string_read(name, 64, f)) + { + return(LIB3DS_FALSE); + } + strcpy(mesh->box_map.top, name); + if (!lib3ds_string_read(name, 64, f)) + { + return(LIB3DS_FALSE); + } + strcpy(mesh->box_map.bottom, name); + } + break; + default: + lib3ds_chunk_unknown(chunk); + } + } + + } + lib3ds_chunk_read_end(&c, f); + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup mesh + */ +Lib3dsMesh* +lib3ds_mesh_new(const char *name) +{ + Lib3dsMesh *mesh; + + ASSERT(name); + ASSERT(strlen(name)<64); + + mesh=(Lib3dsMesh*)calloc(sizeof(Lib3dsMesh), 1); + if (!mesh) + { + return(0); + } + strcpy(mesh->name, name); + lib3ds_matrix_identity(mesh->matrix); + return(mesh); +} + + +/*! + * \ingroup mesh + */ +void +lib3ds_mesh_free(Lib3dsMesh *mesh) +{ + lib3ds_mesh_free_point_list(mesh); + lib3ds_mesh_free_flag_list(mesh); + lib3ds_mesh_free_texel_list(mesh); + lib3ds_mesh_free_face_list(mesh); + memset(mesh, 0, sizeof(Lib3dsMesh)); + free(mesh); +} + + +/*! + * \ingroup mesh + */ +Lib3dsBool +lib3ds_mesh_new_point_list(Lib3dsMesh *mesh, Lib3dsDword points) +{ + ASSERT(mesh); + if (mesh->pointL) + { + ASSERT(mesh->points); + lib3ds_mesh_free_point_list(mesh); + } + ASSERT(!mesh->pointL && !mesh->points); + mesh->points=0; + mesh->pointL=(Lib3dsPoint*)calloc(sizeof(Lib3dsPoint)*points,1); + if (!mesh->pointL) + { + LIB3DS_ERROR_LOG; + return(LIB3DS_FALSE); + } + mesh->points=points; + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup mesh + */ +void +lib3ds_mesh_free_point_list(Lib3dsMesh *mesh) +{ + ASSERT(mesh); + if (mesh->pointL) + { + ASSERT(mesh->points); + free(mesh->pointL); + mesh->pointL=0; + mesh->points=0; + } + else + { + ASSERT(!mesh->points); + } +} + + +/*! + * \ingroup mesh + */ +Lib3dsBool +lib3ds_mesh_new_flag_list(Lib3dsMesh *mesh, Lib3dsDword flags) +{ + ASSERT(mesh); + if (mesh->flagL) + { + ASSERT(mesh->flags); + lib3ds_mesh_free_flag_list(mesh); + } + ASSERT(!mesh->flagL && !mesh->flags); + mesh->flags=0; + mesh->flagL=(Lib3dsWord*)calloc(sizeof(Lib3dsWord)*flags,1); + if (!mesh->flagL) + { + LIB3DS_ERROR_LOG; + return(LIB3DS_FALSE); + } + mesh->flags=flags; + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup mesh + */ +void +lib3ds_mesh_free_flag_list(Lib3dsMesh *mesh) +{ + ASSERT(mesh); + if (mesh->flagL) + { + ASSERT(mesh->flags); + free(mesh->flagL); + mesh->flagL=0; + mesh->flags=0; + } + else + { + ASSERT(!mesh->flags); + } +} + + +/*! + * \ingroup mesh + */ +Lib3dsBool +lib3ds_mesh_new_texel_list(Lib3dsMesh *mesh, Lib3dsDword texels) +{ + ASSERT(mesh); + if (mesh->texelL) + { + ASSERT(mesh->texels); + lib3ds_mesh_free_texel_list(mesh); + } + ASSERT(!mesh->texelL && !mesh->texels); + mesh->texels=0; + mesh->texelL=(Lib3dsTexel*)calloc(sizeof(Lib3dsTexel)*texels,1); + if (!mesh->texelL) + { + LIB3DS_ERROR_LOG; + return(LIB3DS_FALSE); + } + mesh->texels=texels; + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup mesh + */ +void +lib3ds_mesh_free_texel_list(Lib3dsMesh *mesh) +{ + ASSERT(mesh); + if (mesh->texelL) + { + ASSERT(mesh->texels); + free(mesh->texelL); + mesh->texelL=0; + mesh->texels=0; + } + else + { + ASSERT(!mesh->texels); + } +} + + +/*! + * \ingroup mesh + */ +Lib3dsBool +lib3ds_mesh_new_face_list(Lib3dsMesh *mesh, Lib3dsDword faces) +{ + ASSERT(mesh); + if (mesh->faceL) + { + ASSERT(mesh->faces); + lib3ds_mesh_free_face_list(mesh); + } + ASSERT(!mesh->faceL && !mesh->faces); + mesh->faces=0; + mesh->faceL=(Lib3dsFace*)calloc(sizeof(Lib3dsFace)*faces,1); + if (!mesh->faceL) + { + LIB3DS_ERROR_LOG; + return(LIB3DS_FALSE); + } + mesh->faces=faces; + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup mesh + */ +void +lib3ds_mesh_free_face_list(Lib3dsMesh *mesh) +{ + ASSERT(mesh); + if (mesh->faceL) + { + ASSERT(mesh->faces); + free(mesh->faceL); + mesh->faceL=0; + mesh->faces=0; + } + else + { + ASSERT(!mesh->faces); + } +} + + +/*! + * \ingroup mesh + */ +void +lib3ds_mesh_bounding_box(Lib3dsMesh *mesh, Lib3dsVector min, Lib3dsVector max) +{ + unsigned i,j; + Lib3dsFloat v; + + if (!mesh->points) + { + lib3ds_vector_zero(min); + lib3ds_vector_zero(max); + return; + } + + lib3ds_vector_copy(min, mesh->pointL[0].pos); + lib3ds_vector_copy(max, mesh->pointL[0].pos); + for (i=1; ipoints; ++i) + { + for (j=0; j<3; ++j) + { + v=mesh->pointL[i].pos[j]; + if (vmax[j]) + { + max[j]=v; + } + } + }; +} + + +/*! + * \ingroup mesh + */ +void +lib3ds_mesh_dump(Lib3dsMesh *mesh) +{ + unsigned i; + Lib3dsVector p; + + ASSERT(mesh); + printf(" %s vertices=%ld faces=%ld\n", + mesh->name, + mesh->points, + mesh->faces + ); + printf(" matrix:\n"); + lib3ds_matrix_dump(mesh->matrix); + printf(" point list:\n"); + for (i=0; ipoints; ++i) + { + lib3ds_vector_transform(p, mesh->matrix, mesh->pointL[i].pos); + printf (" %8f %8f %8f\n", p[0], p[1], p[2]); + } +} + + +/*! + * \ingroup mesh + */ +Lib3dsBool +lib3ds_mesh_read(Lib3dsMesh *mesh, FILE *f) +{ + Lib3dsChunk c; + Lib3dsWord chunk; + + if (!lib3ds_chunk_read_start(&c, LIB3DS_N_TRI_OBJECT, f)) + { + return(LIB3DS_FALSE); + } + + while ((chunk=lib3ds_chunk_read_next(&c, f))!=0) + { + switch (chunk) + { + case LIB3DS_MESH_MATRIX: + { + int i,j; + + lib3ds_matrix_identity(mesh->matrix); + for (i=0; i<4; i++) + { + for (j=0; j<3; j++) + { + mesh->matrix[i][j]=lib3ds_float_read(f); + } + } + } + break; + case LIB3DS_MESH_COLOR: + { + mesh->color=lib3ds_byte_read(f); + } + break; + case LIB3DS_POINT_ARRAY: + { + unsigned i,j; + unsigned points; + + lib3ds_mesh_free_point_list(mesh); + points=lib3ds_word_read(f); + if (points) + { + if (!lib3ds_mesh_new_point_list(mesh, points)) + { + LIB3DS_ERROR_LOG; + return(LIB3DS_FALSE); + } + for (i=0; ipoints; ++i) + { + for (j=0; j<3; ++j) + { + mesh->pointL[i].pos[j]=lib3ds_float_read(f); + } + } + ASSERT((!mesh->flags) || (mesh->points==mesh->flags)); + ASSERT((!mesh->texels) || (mesh->points==mesh->texels)); + } + } + break; + case LIB3DS_POINT_FLAG_ARRAY: + { + unsigned i; + unsigned flags; + + lib3ds_mesh_free_flag_list(mesh); + flags=lib3ds_word_read(f); + if (flags) + { + if (!lib3ds_mesh_new_flag_list(mesh, flags)) + { + LIB3DS_ERROR_LOG; + return(LIB3DS_FALSE); + } + for (i=0; iflags; ++i) + { + mesh->flagL[i]=lib3ds_word_read(f); + } + ASSERT((!mesh->points) || (mesh->flags==mesh->points)); + ASSERT((!mesh->texels) || (mesh->flags==mesh->texels)); + } + } + break; + case LIB3DS_FACE_ARRAY: + { + lib3ds_chunk_read_reset(&c, f); + if (!face_array_read(mesh, f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_MESH_TEXTURE_INFO: + { + int i,j; + + for (i=0; i<2; ++i) + { + mesh->map_data.tile[i]=lib3ds_float_read(f); + } + for (i=0; i<3; ++i) + { + mesh->map_data.pos[i]=lib3ds_float_read(f); + } + mesh->map_data.scale=lib3ds_float_read(f); + + lib3ds_matrix_identity(mesh->map_data.matrix); + for (i=0; i<4; i++) + { + for (j=0; j<3; j++) + { + mesh->map_data.matrix[i][j]=lib3ds_float_read(f); + } + } + for (i=0; i<2; ++i) + { + mesh->map_data.planar_size[i]=lib3ds_float_read(f); + } + mesh->map_data.cylinder_height=lib3ds_float_read(f); + } + break; + case LIB3DS_TEX_VERTS: + { + unsigned i; + unsigned texels; + + lib3ds_mesh_free_texel_list(mesh); + texels=lib3ds_word_read(f); + if (texels) + { + if (!lib3ds_mesh_new_texel_list(mesh, texels)) + { + LIB3DS_ERROR_LOG; + return(LIB3DS_FALSE); + } + for (i=0; itexels; ++i) + { + mesh->texelL[i][0]=lib3ds_float_read(f); + mesh->texelL[i][1]=lib3ds_float_read(f); + } + ASSERT((!mesh->points) || (mesh->texels==mesh->points)); + ASSERT((!mesh->flags) || (mesh->texels==mesh->flags)); + } + } + break; + default: + lib3ds_chunk_unknown(chunk); + } + } + { + unsigned j; + + for (j=0; jfaces; ++j) + { + ASSERT(mesh->faceL[j].points[0]points); + ASSERT(mesh->faceL[j].points[1]points); + ASSERT(mesh->faceL[j].points[2]points); + lib3ds_vector_normal( + mesh->faceL[j].normal, + mesh->pointL[mesh->faceL[j].points[0]].pos, + mesh->pointL[mesh->faceL[j].points[1]].pos, + mesh->pointL[mesh->faceL[j].points[2]].pos + ); + } + } + + lib3ds_chunk_read_end(&c, f); + return(LIB3DS_TRUE); +} + + +static Lib3dsBool +point_array_write(Lib3dsMesh *mesh, FILE *f) +{ + Lib3dsChunk c; + unsigned i; + + if (!mesh->points || !mesh->pointL) + { + return(LIB3DS_TRUE); + } + ASSERT(mesh->points<0x10000); + c.chunk=LIB3DS_POINT_ARRAY; + c.size=8+12*mesh->points; + lib3ds_chunk_write(&c, f); + + lib3ds_word_write((Lib3dsWord)mesh->points, f); + for (i=0; ipoints; ++i) + { + lib3ds_vector_write(mesh->pointL[i].pos, f); + } + return(LIB3DS_TRUE); +} + + +static Lib3dsBool +flag_array_write(Lib3dsMesh *mesh, FILE *f) +{ + Lib3dsChunk c; + unsigned i; + + if (!mesh->flags || !mesh->flagL) + { + return(LIB3DS_TRUE); + } + ASSERT(mesh->flags<0x10000); + c.chunk=LIB3DS_POINT_FLAG_ARRAY; + c.size=8+2*mesh->flags; + lib3ds_chunk_write(&c, f); + + lib3ds_word_write((Lib3dsWord)mesh->flags, f); + for (i=0; iflags; ++i) + { + lib3ds_word_write(mesh->flagL[i], f); + } + return(LIB3DS_TRUE); +} + + +static Lib3dsBool +face_array_write(Lib3dsMesh *mesh, FILE *f) +{ + Lib3dsChunk c; + + if (!mesh->faces || !mesh->faceL) + { + return(LIB3DS_TRUE); + } + ASSERT(mesh->faces<0x10000); + c.chunk=LIB3DS_FACE_ARRAY; + if (!lib3ds_chunk_write_start(&c, f)) + { + return(LIB3DS_FALSE); + } + { + unsigned i; + + lib3ds_word_write((Lib3dsWord)mesh->faces, f); + for (i=0; ifaces; ++i) + { + lib3ds_word_write(mesh->faceL[i].points[0], f); + lib3ds_word_write(mesh->faceL[i].points[1], f); + lib3ds_word_write(mesh->faceL[i].points[2], f); + lib3ds_word_write(mesh->faceL[i].flags, f); + } + } + + { /*---- MSH_MAT_GROUP ----*/ + Lib3dsChunk c; + unsigned i,j; + Lib3dsWord num; + char *matf=(char *)calloc(sizeof(char), mesh->faces); + if (!matf) + { + return(LIB3DS_FALSE); + } + + for (i=0; ifaces; ++i) + { + if (!matf[i]) + { + matf[i]=1; + num=1; + + for (j=i+1; jfaces; ++j) + { + if (strcmp(mesh->faceL[i].material, mesh->faceL[j].material)==0) ++num; + } + + c.chunk=LIB3DS_MSH_MAT_GROUP; + c.size=6+ strlen(mesh->faceL[i].material)+1 +2+2*num; + lib3ds_chunk_write(&c, f); + lib3ds_string_write(mesh->faceL[i].material, f); + lib3ds_word_write(num, f); + lib3ds_word_write((Lib3dsWord)i, f); + + for (j=i+1; jfaces; ++j) + { + if (strcmp(mesh->faceL[i].material, mesh->faceL[j].material)==0) + { + lib3ds_word_write((Lib3dsWord)j, f); + matf[j]=1; + } + } + } + } + free(matf); + } + + { /*---- SMOOTH_GROUP ----*/ + Lib3dsChunk c; + unsigned i; + + c.chunk=LIB3DS_SMOOTH_GROUP; + c.size=6+4*mesh->faces; + lib3ds_chunk_write(&c, f); + + for (i=0; ifaces; ++i) + { + lib3ds_dword_write(mesh->faceL[i].smoothing, f); + } + } + + { /*---- MSH_BOXMAP ----*/ + Lib3dsChunk c; + + if (strlen(mesh->box_map.front) || + strlen(mesh->box_map.back) || + strlen(mesh->box_map.left) || + strlen(mesh->box_map.right) || + strlen(mesh->box_map.top) || + strlen(mesh->box_map.bottom)) + { + + c.chunk=LIB3DS_MSH_BOXMAP; + if (!lib3ds_chunk_write_start(&c, f)) + { + return(LIB3DS_FALSE); + } + + lib3ds_string_write(mesh->box_map.front, f); + lib3ds_string_write(mesh->box_map.back, f); + lib3ds_string_write(mesh->box_map.left, f); + lib3ds_string_write(mesh->box_map.right, f); + lib3ds_string_write(mesh->box_map.top, f); + lib3ds_string_write(mesh->box_map.bottom, f); + + if (!lib3ds_chunk_write_end(&c, f)) + { + return(LIB3DS_FALSE); + } + } + } + + if (!lib3ds_chunk_write_end(&c, f)) + { + return(LIB3DS_FALSE); + } + return(LIB3DS_TRUE); +} + + +static Lib3dsBool +texel_array_write(Lib3dsMesh *mesh, FILE *f) +{ + Lib3dsChunk c; + unsigned i; + + if (!mesh->texels || !mesh->texelL) + { + return(LIB3DS_TRUE); + } + ASSERT(mesh->texels<0x10000); + c.chunk=LIB3DS_TEX_VERTS; + c.size=8+8*mesh->texels; + lib3ds_chunk_write(&c, f); + + lib3ds_word_write((Lib3dsWord)mesh->texels, f); + for (i=0; itexels; ++i) + { + lib3ds_float_write(mesh->texelL[i][0], f); + lib3ds_float_write(mesh->texelL[i][1], f); + } + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup mesh + */ +Lib3dsBool +lib3ds_mesh_write(Lib3dsMesh *mesh, FILE *f) +{ + Lib3dsChunk c; + + c.chunk=LIB3DS_N_TRI_OBJECT; + if (!lib3ds_chunk_write_start(&c,f)) + { + return(LIB3DS_FALSE); + } + if (!point_array_write(mesh, f)) + { + return(LIB3DS_FALSE); + } + if (!flag_array_write(mesh, f)) + { + return(LIB3DS_FALSE); + } + if (!face_array_write(mesh, f)) + { + return(LIB3DS_FALSE); + } + if (!texel_array_write(mesh, f)) + { + return(LIB3DS_FALSE); + } + { /*---- LIB3DS_MESH_MATRIX ----*/ + Lib3dsChunk c; + int i,j; + + c.chunk=LIB3DS_MESH_MATRIX; + c.size=54; + if (!lib3ds_chunk_write(&c,f)) + { + return(LIB3DS_FALSE); + } + for (i=0; i<4; i++) + { + for (j=0; j<3; j++) + { + lib3ds_float_write(mesh->matrix[i][j], f); + } + } + } + + { /*---- LIB3DS_MESH_COLOR ----*/ + Lib3dsChunk c; + + c.chunk=LIB3DS_MESH_COLOR; + c.size=7; + if (!lib3ds_chunk_write(&c,f)) + { + return(LIB3DS_FALSE); + } + lib3ds_byte_write(mesh->color, f); + } + + { /*---- LIB3DS_MESH_TEXTURE_INFO ----*/ + Lib3dsChunk c; + int i,j; + + c.chunk=LIB3DS_MESH_TEXTURE_INFO; + c.size=90; + if (!lib3ds_chunk_write(&c,f)) + { + return(LIB3DS_FALSE); + } + + for (i=0; i<2; ++i) + { + lib3ds_float_write(mesh->map_data.tile[i], f); + } + for (i=0; i<3; ++i) + { + lib3ds_float_write(mesh->map_data.pos[i], f); + } + lib3ds_float_write(mesh->map_data.scale, f); + + for (i=0; i<4; i++) + { + for (j=0; j<3; j++) + { + lib3ds_float_write(mesh->map_data.matrix[i][j], f); + } + } + for (i=0; i<2; ++i) + { + lib3ds_float_write(mesh->map_data.planar_size[i], f); + } + lib3ds_float_write(mesh->map_data.cylinder_height, f); + } + + if (!lib3ds_chunk_write_end(&c,f)) + { + return(LIB3DS_FALSE); + } + return(LIB3DS_TRUE); +} + + +/*! + +\typedef Lib3dsFace + \ingroup mesh + \sa _Lib3dsFace + +*/ +/*! + +\typedef Lib3dsBoxMap + \ingroup mesh + \sa _Lib3dsBoxMap + +*/ +/*! + +\typedef Lib3dsMapData + \ingroup mesh + \sa _Lib3dsMapData + +*/ +/*! + +\typedef Lib3dsMesh + \ingroup mesh + \sa _Lib3dsMesh + +*/ diff --git a/src/osgPlugins/lib3ds/mesh.h b/src/osgPlugins/lib3ds/mesh.h new file mode 100644 index 000000000..d70473d5e --- /dev/null +++ b/src/osgPlugins/lib3ds/mesh.h @@ -0,0 +1,122 @@ +/* -*- c -*- */ +#ifndef INCLUDED_LIB3DS_MESH_H +#define INCLUDED_LIB3DS_MESH_H +/* + * The 3D Studio File Format Library + * Copyright (C) 1996-2001 by J.E. Hoffmann + * All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or (at + * your option) any later version. + * + * 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 Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + * + * $Id$ + */ + +#ifndef INCLUDED_LIB3DS_TYPES_H +#include +#endif + +#ifdef __cplusplus +extern "C" { +#endif + +/*! + * Triangular mesh point + * \ingroup mesh + */ +typedef struct _Lib3dsPoint { + Lib3dsVector pos; +} Lib3dsPoint; + +/*! + * Triangular mesh face + * \ingroup mesh + */ +struct _Lib3dsFace { + Lib3dsUserData user; + char material[64]; + Lib3dsWord points[3]; + Lib3dsWord flags; + Lib3dsDword smoothing; + Lib3dsVector normal; +}; + +/*! + * Triangular mesh box mapping settings + * \ingroup mesh + */ +struct _Lib3dsBoxMap { + char front[64]; + char back[64]; + char left[64]; + char right[64]; + char top[64]; + char bottom[64]; +}; + +/*! + * Triangular mesh texture mapping data + * \ingroup mesh + */ +struct _Lib3dsMapData { + Lib3dsVector pos; + Lib3dsMatrix matrix; + Lib3dsFloat scale; + Lib3dsFloat tile[2]; + Lib3dsFloat planar_size[2]; + Lib3dsFloat cylinder_height; +}; + +/*! + * Triangular mesh object + * \ingroup mesh + */ +struct _Lib3dsMesh { + Lib3dsUserData user; + Lib3dsMesh *next; + char name[64]; + Lib3dsByte color; + Lib3dsMatrix matrix; + Lib3dsDword points; + Lib3dsPoint *pointL; + Lib3dsDword flags; + Lib3dsWord *flagL; + Lib3dsDword texels; + Lib3dsTexel *texelL; + Lib3dsDword faces; + Lib3dsFace *faceL; + Lib3dsBoxMap box_map; + Lib3dsMapData map_data; +}; + +extern LIB3DSAPI Lib3dsMesh* lib3ds_mesh_new(const char *name); +extern LIB3DSAPI void lib3ds_mesh_free(Lib3dsMesh *mesh); +extern LIB3DSAPI Lib3dsBool lib3ds_mesh_new_point_list(Lib3dsMesh *mesh, Lib3dsDword points); +extern LIB3DSAPI void lib3ds_mesh_free_point_list(Lib3dsMesh *mesh); +extern LIB3DSAPI Lib3dsBool lib3ds_mesh_new_flag_list(Lib3dsMesh *mesh, Lib3dsDword flags); +extern LIB3DSAPI void lib3ds_mesh_free_flag_list(Lib3dsMesh *mesh); +extern LIB3DSAPI Lib3dsBool lib3ds_mesh_new_texel_list(Lib3dsMesh *mesh, Lib3dsDword texels); +extern LIB3DSAPI void lib3ds_mesh_free_texel_list(Lib3dsMesh *mesh); +extern LIB3DSAPI Lib3dsBool lib3ds_mesh_new_face_list(Lib3dsMesh *mesh, Lib3dsDword flags); +extern LIB3DSAPI void lib3ds_mesh_free_face_list(Lib3dsMesh *mesh); +extern LIB3DSAPI void lib3ds_mesh_bounding_box(Lib3dsMesh *mesh, Lib3dsVector min, Lib3dsVector max); +extern LIB3DSAPI void lib3ds_mesh_dump(Lib3dsMesh *mesh); +extern LIB3DSAPI Lib3dsBool lib3ds_mesh_read(Lib3dsMesh *mesh, FILE *f); +extern LIB3DSAPI Lib3dsBool lib3ds_mesh_write(Lib3dsMesh *mesh, FILE *f); + +#ifdef __cplusplus +}; +#endif +#endif + diff --git a/src/osgPlugins/lib3ds/node.cpp b/src/osgPlugins/lib3ds/node.cpp new file mode 100644 index 000000000..e98cbe669 --- /dev/null +++ b/src/osgPlugins/lib3ds/node.cpp @@ -0,0 +1,1209 @@ +/* + * The 3D Studio File Format Library + * Copyright (C) 1996-2001 by J.E. Hoffmann + * All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or (at + * your option) any later version. + * + * 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 Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + * + * $Id$ + */ +#define LIB3DS_EXPORT +#include +#include +#include +#include +#include +#include +#include +//#include +#ifdef WITH_DMALLOC +#include +#endif + +/*! + * \defgroup node Animation Nodes + * + * \author J.E. Hoffmann + */ + +/*! + * \ingroup node + */ +Lib3dsNode* +lib3ds_node_new_ambient() +{ + Lib3dsNode *node=(Lib3dsNode*)calloc(sizeof(Lib3dsNode), 1); + node->type=LIB3DS_AMBIENT_NODE; + lib3ds_matrix_identity(node->matrix); + return(node); +} + + +/*! + * \ingroup node + */ +Lib3dsNode* +lib3ds_node_new_object() +{ + Lib3dsNode *node=(Lib3dsNode*)calloc(sizeof(Lib3dsNode), 1); + node->type=LIB3DS_OBJECT_NODE; + lib3ds_matrix_identity(node->matrix); + return(node); +} + + +/*! + * \ingroup node + */ +Lib3dsNode* +lib3ds_node_new_camera() +{ + Lib3dsNode *node=(Lib3dsNode*)calloc(sizeof(Lib3dsNode), 1); + node->type=LIB3DS_CAMERA_NODE; + lib3ds_matrix_identity(node->matrix); + return(node); +} + + +/*! + * \ingroup node + */ +Lib3dsNode* +lib3ds_node_new_target() +{ + Lib3dsNode *node=(Lib3dsNode*)calloc(sizeof(Lib3dsNode), 1); + node->type=LIB3DS_TARGET_NODE; + lib3ds_matrix_identity(node->matrix); + return(node); +} + + +/*! + * \ingroup node + */ +Lib3dsNode* +lib3ds_node_new_light() +{ + Lib3dsNode *node=(Lib3dsNode*)calloc(sizeof(Lib3dsNode), 1); + node->type=LIB3DS_LIGHT_NODE; + lib3ds_matrix_identity(node->matrix); + return(node); +} + + +/*! + * \ingroup node + */ +Lib3dsNode* +lib3ds_node_new_spot() +{ + Lib3dsNode *node=(Lib3dsNode*)calloc(sizeof(Lib3dsNode), 1); + node->type=LIB3DS_SPOT_NODE; + lib3ds_matrix_identity(node->matrix); + return(node); +} + + +static void +free_node_and_childs(Lib3dsNode *node) +{ + ASSERT(node); + switch (node->type) + { + case LIB3DS_UNKNOWN_NODE: + break; + case LIB3DS_AMBIENT_NODE: + { + Lib3dsAmbientData *n=&node->data.ambient; + lib3ds_lin3_track_free_keys(&n->col_track); + } + break; + case LIB3DS_OBJECT_NODE: + { + Lib3dsObjectData *n=&node->data.object; + + lib3ds_lin3_track_free_keys(&n->pos_track); + lib3ds_quat_track_free_keys(&n->rot_track); + lib3ds_lin3_track_free_keys(&n->scl_track); + lib3ds_bool_track_free_keys(&n->hide_track); + lib3ds_morph_track_free_keys(&n->morph_track); + } + break; + case LIB3DS_CAMERA_NODE: + { + Lib3dsCameraData *n=&node->data.camera; + lib3ds_lin3_track_free_keys(&n->pos_track); + lib3ds_lin1_track_free_keys(&n->fov_track); + lib3ds_lin1_track_free_keys(&n->roll_track); + } + break; + case LIB3DS_TARGET_NODE: + { + Lib3dsTargetData *n=&node->data.target; + lib3ds_lin3_track_free_keys(&n->pos_track); + } + break; + case LIB3DS_LIGHT_NODE: + { + Lib3dsLightData *n=&node->data.light; + lib3ds_lin3_track_free_keys(&n->pos_track); + lib3ds_lin3_track_free_keys(&n->col_track); + lib3ds_lin1_track_free_keys(&n->hotspot_track); + lib3ds_lin1_track_free_keys(&n->falloff_track); + lib3ds_lin1_track_free_keys(&n->roll_track); + } + break; + case LIB3DS_SPOT_NODE: + { + Lib3dsSpotData *n=&node->data.spot; + lib3ds_lin3_track_free_keys(&n->pos_track); + } + break; + } + { + Lib3dsNode *p,*q; + for (p=node->childs; p; p=q) + { + q=p->next; + free_node_and_childs(p); + } + } + node->type=LIB3DS_UNKNOWN_NODE; + free(node); +} + + +/*! + * \ingroup node + */ +void +lib3ds_node_free(Lib3dsNode *node) +{ + ASSERT(node); + free_node_and_childs(node); +} + + +/*! + * \ingroup node + */ +void +lib3ds_node_eval(Lib3dsNode *node, Lib3dsFloat t) +{ + ASSERT(node); + switch (node->type) + { + case LIB3DS_UNKNOWN_NODE: + { + ASSERT(LIB3DS_FALSE); + } + break; + case LIB3DS_AMBIENT_NODE: + { + Lib3dsAmbientData *n=&node->data.ambient; + if (node->parent) + { + lib3ds_matrix_copy(node->matrix, node->parent->matrix); + } + else + { + lib3ds_matrix_identity(node->matrix); + } + lib3ds_lin3_track_eval(&n->col_track, n->col, t); + } + break; + case LIB3DS_OBJECT_NODE: + { + Lib3dsMatrix M; + Lib3dsObjectData *n=&node->data.object; + + lib3ds_lin3_track_eval(&n->pos_track, n->pos, t); + lib3ds_quat_track_eval(&n->rot_track, n->rot, t); + lib3ds_lin3_track_eval(&n->scl_track, n->scl, t); + lib3ds_bool_track_eval(&n->hide_track, &n->hide, t); + lib3ds_morph_track_eval(&n->morph_track, n->morph, t); + + lib3ds_matrix_identity(M); + lib3ds_matrix_translate(M, n->pos); + lib3ds_matrix_rotate(M, n->rot); + lib3ds_matrix_scale(M, n->scl); + + if (node->parent) + { + lib3ds_matrix_mul(node->matrix, node->parent->matrix, M); + } + else + { + lib3ds_matrix_copy(node->matrix, M); + } + } + break; + case LIB3DS_CAMERA_NODE: + { + Lib3dsCameraData *n=&node->data.camera; + lib3ds_lin3_track_eval(&n->pos_track, n->pos, t); + lib3ds_lin1_track_eval(&n->fov_track, &n->fov, t); + lib3ds_lin1_track_eval(&n->roll_track, &n->roll, t); + if (node->parent) + { + lib3ds_matrix_copy(node->matrix, node->parent->matrix); + } + else + { + lib3ds_matrix_identity(node->matrix); + } + lib3ds_matrix_translate(node->matrix, n->pos); + } + break; + case LIB3DS_TARGET_NODE: + { + Lib3dsTargetData *n=&node->data.target; + lib3ds_lin3_track_eval(&n->pos_track, n->pos, t); + if (node->parent) + { + lib3ds_matrix_copy(node->matrix, node->parent->matrix); + } + else + { + lib3ds_matrix_identity(node->matrix); + } + lib3ds_matrix_translate(node->matrix, n->pos); + } + break; + case LIB3DS_LIGHT_NODE: + { + Lib3dsLightData *n=&node->data.light; + lib3ds_lin3_track_eval(&n->pos_track, n->pos, t); + lib3ds_lin3_track_eval(&n->col_track, n->col, t); + lib3ds_lin1_track_eval(&n->hotspot_track, &n->hotspot, t); + lib3ds_lin1_track_eval(&n->falloff_track, &n->falloff, t); + lib3ds_lin1_track_eval(&n->roll_track, &n->roll, t); + if (node->parent) + { + lib3ds_matrix_copy(node->matrix, node->parent->matrix); + } + else + { + lib3ds_matrix_identity(node->matrix); + } + lib3ds_matrix_translate(node->matrix, n->pos); + } + break; + case LIB3DS_SPOT_NODE: + { + Lib3dsSpotData *n=&node->data.spot; + lib3ds_lin3_track_eval(&n->pos_track, n->pos, t); + if (node->parent) + { + lib3ds_matrix_copy(node->matrix, node->parent->matrix); + } + else + { + lib3ds_matrix_identity(node->matrix); + } + lib3ds_matrix_translate(node->matrix, n->pos); + } + break; + } + { + Lib3dsNode *p; + + for (p=node->childs; p!=0; p=p->next) + { + lib3ds_node_eval(p, t); + } + } +} + + +/*! + * \ingroup node + */ +Lib3dsNode* +lib3ds_node_by_name(Lib3dsNode *node, const char* name, Lib3dsNodeTypes type) +{ + Lib3dsNode *p,*q; + + for (p=node->childs; p!=0; p=p->next) + { + if ((p->type==type) && (strcmp(p->name, name)==0)) + { + return(p); + } + q=lib3ds_node_by_name(p, name, type); + if (q) + { + return(q); + } + } + return(0); +} + + +/*! + * \ingroup node + */ +Lib3dsNode* +lib3ds_node_by_id(Lib3dsNode *node, Lib3dsWord id) +{ + Lib3dsNode *p,*q; + + for (p=node->childs; p!=0; p=p->next) + { + if (p->id==id) + { + return(p); + } + q=lib3ds_node_by_id(p, id); + if (q) + { + return(q); + } + } + return(0); +} + + +static const char* node_names_table[]= +{ + "***Unknown***", + "Ambient", + "Object", + "Camera", + "Target", + "Light", + "Spot" +}; + +/*! + * \ingroup node + */ +void +lib3ds_node_dump(Lib3dsNode *node, Lib3dsIntd level) +{ + Lib3dsNode *p; + char l[128]; + + ASSERT(node); + memset(l, ' ', 2*level); + l[2*level]=0; + + if (node->type==LIB3DS_OBJECT_NODE) + { + printf("%s%s [%s] (%s)\n", + l, + node->name, + node->data.object.instance, + node_names_table[node->type] + ); + } + else + { + printf("%s%s (%s)\n", + l, + node->name, + node_names_table[node->type] + ); + } + + for (p=node->childs; p!=0; p=p->next) + { + lib3ds_node_dump(p, level+1); + } +} + + +/*! + * \ingroup node + */ +Lib3dsBool +lib3ds_node_read(Lib3dsNode *node, Lib3dsFile *, FILE *f) +{ + // parameters lib3ds_node_read(Lib3dsNode *node, Lib3dsFile *file, FILE *f) + + Lib3dsChunk c; + Lib3dsWord chunk; + + ASSERT(node); + if (!lib3ds_chunk_read_start(&c, 0, f)) + { + return(LIB3DS_FALSE); + } + switch (c.chunk) + { + case LIB3DS_AMBIENT_NODE_TAG: + case LIB3DS_OBJECT_NODE_TAG: + case LIB3DS_CAMERA_NODE_TAG: + case LIB3DS_TARGET_NODE_TAG: + case LIB3DS_LIGHT_NODE_TAG: + case LIB3DS_SPOTLIGHT_NODE_TAG: + case LIB3DS_L_TARGET_NODE_TAG: + break; + default: + return(LIB3DS_FALSE); + } + + while ((chunk=lib3ds_chunk_read_next(&c, f))!=0) + { + switch (chunk) + { + case LIB3DS_NODE_ID: + { + node->id=lib3ds_word_read(f); + } + break; + case LIB3DS_NODE_HDR: + { + if (!lib3ds_string_read(node->name, 64, f)) + { + return(LIB3DS_FALSE); + } + node->flags1=lib3ds_word_read(f); + node->flags2=lib3ds_word_read(f); + node->parent_id=lib3ds_word_read(f); + } + break; + case LIB3DS_PIVOT: + { + if (node->type==LIB3DS_OBJECT_NODE) + { + int i; + for (i=0; i<3; ++i) + { + node->data.object.pivot[i]=lib3ds_float_read(f); + } + } + else + { + lib3ds_chunk_unknown(chunk); + } + } + break; + case LIB3DS_INSTANCE_NAME: + { + if (node->type==LIB3DS_OBJECT_NODE) + { + if (!lib3ds_string_read(node->data.object.instance, 64, f)) + { + return(LIB3DS_FALSE); + } + } + else + { + lib3ds_chunk_unknown(chunk); + } + } + break; + case LIB3DS_BOUNDBOX: + { + if (node->type==LIB3DS_OBJECT_NODE) + { + int i; + for (i=0; i<3; ++i) + { + node->data.object.bbox_min[i]=lib3ds_float_read(f); + } + for (i=0; i<3; ++i) + { + node->data.object.bbox_max[i]=lib3ds_float_read(f); + } + } + else + { + lib3ds_chunk_unknown(chunk); + } + } + break; + case LIB3DS_COL_TRACK_TAG: + { + Lib3dsBool result=LIB3DS_TRUE; + + switch (node->type) + { + case LIB3DS_AMBIENT_NODE: + result=lib3ds_lin3_track_read(&node->data.ambient.col_track, f); + break; + case LIB3DS_LIGHT_NODE: + result=lib3ds_lin3_track_read(&node->data.light.col_track, f); + break; + default: + lib3ds_chunk_unknown(chunk); + } + if (!result) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_POS_TRACK_TAG: + { + Lib3dsBool result=LIB3DS_TRUE; + + switch (node->type) + { + case LIB3DS_OBJECT_NODE: + result=lib3ds_lin3_track_read(&node->data.object.pos_track, f); + break; + case LIB3DS_CAMERA_NODE: + result=lib3ds_lin3_track_read(&node->data.camera.pos_track, f); + break; + case LIB3DS_TARGET_NODE: + result=lib3ds_lin3_track_read(&node->data.target.pos_track, f); + break; + case LIB3DS_LIGHT_NODE: + result=lib3ds_lin3_track_read(&node->data.light.pos_track, f); + break; + case LIB3DS_SPOT_NODE: + result=lib3ds_lin3_track_read(&node->data.spot.pos_track, f); + break; + default: + lib3ds_chunk_unknown(chunk); + } + if (!result) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_ROT_TRACK_TAG: + { + if (node->type==LIB3DS_OBJECT_NODE) + { + if (!lib3ds_quat_track_read(&node->data.object.rot_track, f)) + { + return(LIB3DS_FALSE); + } + } + else + { + lib3ds_chunk_unknown(chunk); + } + } + break; + case LIB3DS_SCL_TRACK_TAG: + { + if (node->type==LIB3DS_OBJECT_NODE) + { + if (!lib3ds_lin3_track_read(&node->data.object.scl_track, f)) + { + return(LIB3DS_FALSE); + } + } + else + { + lib3ds_chunk_unknown(chunk); + } + } + break; + case LIB3DS_FOV_TRACK_TAG: + { + if (node->type==LIB3DS_CAMERA_NODE) + { + if (!lib3ds_lin1_track_read(&node->data.camera.fov_track, f)) + { + return(LIB3DS_FALSE); + } + } + else + { + lib3ds_chunk_unknown(chunk); + } + } + break; + case LIB3DS_HOT_TRACK_TAG: + { + if (node->type==LIB3DS_LIGHT_NODE) + { + if (!lib3ds_lin1_track_read(&node->data.light.hotspot_track, f)) + { + return(LIB3DS_FALSE); + } + } + else + { + lib3ds_chunk_unknown(chunk); + } + } + break; + case LIB3DS_FALL_TRACK_TAG: + { + if (node->type==LIB3DS_LIGHT_NODE) + { + if (!lib3ds_lin1_track_read(&node->data.light.falloff_track, f)) + { + return(LIB3DS_FALSE); + } + } + else + { + lib3ds_chunk_unknown(chunk); + } + } + break; + case LIB3DS_ROLL_TRACK_TAG: + { + Lib3dsBool result=LIB3DS_TRUE; + + switch (node->type) + { + case LIB3DS_CAMERA_NODE: + result=lib3ds_lin1_track_read(&node->data.camera.roll_track, f); + break; + case LIB3DS_LIGHT_NODE: + result=lib3ds_lin1_track_read(&node->data.light.roll_track, f); + break; + default: + lib3ds_chunk_unknown(chunk); + } + if (!result) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_HIDE_TRACK_TAG: + { + if (node->type==LIB3DS_OBJECT_NODE) + { + if (!lib3ds_bool_track_read(&node->data.object.hide_track, f)) + { + return(LIB3DS_FALSE); + } + } + else + { + lib3ds_chunk_unknown(chunk); + } + } + break; + case LIB3DS_MORPH_SMOOTH: + { + if (node->type==LIB3DS_OBJECT_NODE) + { + node->data.object.morph_smooth=lib3ds_float_read(f); + } + else + { + lib3ds_chunk_unknown(chunk); + } + } + break; + case LIB3DS_MORPH_TRACK_TAG: + { + if (node->type==LIB3DS_OBJECT_NODE) + { + if (!lib3ds_morph_track_read(&node->data.object.morph_track, f)) + { + return(LIB3DS_FALSE); + } + } + else + { + lib3ds_chunk_unknown(chunk); + } + } + break; + default: + lib3ds_chunk_unknown(chunk); + } + } + + lib3ds_chunk_read_end(&c, f); + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup node + */ +Lib3dsBool +lib3ds_node_write(Lib3dsNode *node, Lib3dsFile *file, FILE *f) +{ + Lib3dsChunk c; + + switch (node->type) + { + case LIB3DS_AMBIENT_NODE: + c.chunk=LIB3DS_AMBIENT_NODE_TAG; + break; + case LIB3DS_OBJECT_NODE: + c.chunk=LIB3DS_OBJECT_NODE_TAG; + break; + case LIB3DS_CAMERA_NODE: + c.chunk=LIB3DS_CAMERA_NODE_TAG; + break; + case LIB3DS_TARGET_NODE: + c.chunk=LIB3DS_TARGET_NODE_TAG; + break; + case LIB3DS_LIGHT_NODE: + if (lib3ds_file_node_by_name(file, node->name, LIB3DS_SPOT_NODE)) + { + c.chunk=LIB3DS_SPOTLIGHT_NODE_TAG; + } + else + { + c.chunk=LIB3DS_LIGHT_NODE_TAG; + } + break; + case LIB3DS_SPOT_NODE: + c.chunk=LIB3DS_L_TARGET_NODE_TAG; + break; + default: + return(LIB3DS_FALSE); + } + if (!lib3ds_chunk_write_start(&c,f)) + { + return(LIB3DS_FALSE); + } + + { /*---- LIB3DS_NODE_ID ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_NODE_ID; + c.size=8; + lib3ds_chunk_write(&c,f); + lib3ds_intw_write(node->id,f); + } + + { /*---- LIB3DS_NODE_HDR ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_NODE_HDR; + c.size=6+ 1+strlen(node->name) +2+2+2; + lib3ds_chunk_write(&c,f); + lib3ds_string_write(node->name,f); + lib3ds_word_write(node->flags1,f); + lib3ds_word_write(node->flags2,f); + lib3ds_word_write(node->parent_id,f); + } + + switch (c.chunk) + { + case LIB3DS_AMBIENT_NODE_TAG: + { /*---- LIB3DS_COL_TRACK_TAG ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_COL_TRACK_TAG; + if (!lib3ds_chunk_write_start(&c,f)) + { + return(LIB3DS_FALSE); + } + if (!lib3ds_lin3_track_write(&node->data.ambient.col_track,f)) + { + return(LIB3DS_FALSE); + } + if (!lib3ds_chunk_write_end(&c,f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_OBJECT_NODE_TAG: + { /*---- LIB3DS_PIVOT ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_PIVOT; + c.size=18; + lib3ds_chunk_write(&c,f); + lib3ds_vector_write(node->data.object.pivot,f); + } + { /*---- LIB3DS_INSTANCE_NAME ----*/ + Lib3dsChunk c; + const char *name; + if (strlen(node->data.object.instance)) + { + name=node->data.object.instance; + } + else + { + name=node->name; + } + c.chunk=LIB3DS_INSTANCE_NAME; + c.size=6+1+strlen(name); + lib3ds_chunk_write(&c,f); + lib3ds_string_write(name,f); + } + { /*---- LIB3DS_BOUNDBOX ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_BOUNDBOX; + c.size=30; + lib3ds_chunk_write(&c,f); + lib3ds_vector_write(node->data.object.bbox_min, f); + lib3ds_vector_write(node->data.object.bbox_max, f); + } + { /*---- LIB3DS_POS_TRACK_TAG ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_POS_TRACK_TAG; + if (!lib3ds_chunk_write_start(&c,f)) + { + return(LIB3DS_FALSE); + } + if (!lib3ds_lin3_track_write(&node->data.object.pos_track,f)) + { + return(LIB3DS_FALSE); + } + if (!lib3ds_chunk_write_end(&c,f)) + { + return(LIB3DS_FALSE); + } + } + { /*---- LIB3DS_ROT_TRACK_TAG ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_ROT_TRACK_TAG; + if (!lib3ds_chunk_write_start(&c,f)) + { + return(LIB3DS_FALSE); + } + if (!lib3ds_quat_track_write(&node->data.object.rot_track,f)) + { + return(LIB3DS_FALSE); + } + if (!lib3ds_chunk_write_end(&c,f)) + { + return(LIB3DS_FALSE); + } + } + { /*---- LIB3DS_SCL_TRACK_TAG ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_SCL_TRACK_TAG; + if (!lib3ds_chunk_write_start(&c,f)) + { + return(LIB3DS_FALSE); + } + if (!lib3ds_lin3_track_write(&node->data.object.scl_track,f)) + { + return(LIB3DS_FALSE); + } + if (!lib3ds_chunk_write_end(&c,f)) + { + return(LIB3DS_FALSE); + } + } + { /*---- LIB3DS_HIDE_TRACK_TAG ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_HIDE_TRACK_TAG; + if (!lib3ds_chunk_write_start(&c,f)) + { + return(LIB3DS_FALSE); + } + if (!lib3ds_bool_track_write(&node->data.object.hide_track,f)) + { + return(LIB3DS_FALSE); + } + if (!lib3ds_chunk_write_end(&c,f)) + { + return(LIB3DS_FALSE); + } + } + { /*---- LIB3DS_MORPH_SMOOTH ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_MORPH_SMOOTH; + c.size=10; + lib3ds_chunk_write(&c,f); + lib3ds_float_write(node->data.object.morph_smooth,f); + } + break; + case LIB3DS_CAMERA_NODE_TAG: + { /*---- LIB3DS_POS_TRACK_TAG ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_POS_TRACK_TAG; + if (!lib3ds_chunk_write_start(&c,f)) + { + return(LIB3DS_FALSE); + } + if (!lib3ds_lin3_track_write(&node->data.camera.pos_track,f)) + { + return(LIB3DS_FALSE); + } + if (!lib3ds_chunk_write_end(&c,f)) + { + return(LIB3DS_FALSE); + } + } + { /*---- LIB3DS_FOV_TRACK_TAG ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_FOV_TRACK_TAG; + if (!lib3ds_chunk_write_start(&c,f)) + { + return(LIB3DS_FALSE); + } + if (!lib3ds_lin1_track_write(&node->data.camera.fov_track,f)) + { + return(LIB3DS_FALSE); + } + if (!lib3ds_chunk_write_end(&c,f)) + { + return(LIB3DS_FALSE); + } + } + { /*---- LIB3DS_ROLL_TRACK_TAG ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_ROLL_TRACK_TAG; + if (!lib3ds_chunk_write_start(&c,f)) + { + return(LIB3DS_FALSE); + } + if (!lib3ds_lin1_track_write(&node->data.camera.roll_track,f)) + { + return(LIB3DS_FALSE); + } + if (!lib3ds_chunk_write_end(&c,f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_TARGET_NODE_TAG: + { /*---- LIB3DS_POS_TRACK_TAG ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_POS_TRACK_TAG; + if (!lib3ds_chunk_write_start(&c,f)) + { + return(LIB3DS_FALSE); + } + if (!lib3ds_lin3_track_write(&node->data.target.pos_track,f)) + { + return(LIB3DS_FALSE); + } + if (!lib3ds_chunk_write_end(&c,f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_LIGHT_NODE_TAG: + { /*---- LIB3DS_POS_TRACK_TAG ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_POS_TRACK_TAG; + if (!lib3ds_chunk_write_start(&c,f)) + { + return(LIB3DS_FALSE); + } + if (!lib3ds_lin3_track_write(&node->data.light.pos_track,f)) + { + return(LIB3DS_FALSE); + } + if (!lib3ds_chunk_write_end(&c,f)) + { + return(LIB3DS_FALSE); + } + } + { /*---- LIB3DS_COL_TRACK_TAG ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_COL_TRACK_TAG; + if (!lib3ds_chunk_write_start(&c,f)) + { + return(LIB3DS_FALSE); + } + if (!lib3ds_lin3_track_write(&node->data.light.col_track,f)) + { + return(LIB3DS_FALSE); + } + if (!lib3ds_chunk_write_end(&c,f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_SPOTLIGHT_NODE_TAG: + { /*---- LIB3DS_POS_TRACK_TAG ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_POS_TRACK_TAG; + if (!lib3ds_chunk_write_start(&c,f)) + { + return(LIB3DS_FALSE); + } + if (!lib3ds_lin3_track_write(&node->data.light.pos_track,f)) + { + return(LIB3DS_FALSE); + } + if (!lib3ds_chunk_write_end(&c,f)) + { + return(LIB3DS_FALSE); + } + } + { /*---- LIB3DS_COL_TRACK_TAG ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_COL_TRACK_TAG; + if (!lib3ds_chunk_write_start(&c,f)) + { + return(LIB3DS_FALSE); + } + if (!lib3ds_lin3_track_write(&node->data.light.col_track,f)) + { + return(LIB3DS_FALSE); + } + if (!lib3ds_chunk_write_end(&c,f)) + { + return(LIB3DS_FALSE); + } + } + { /*---- LIB3DS_HOT_TRACK_TAG ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_HOT_TRACK_TAG; + if (!lib3ds_chunk_write_start(&c,f)) + { + return(LIB3DS_FALSE); + } + if (!lib3ds_lin1_track_write(&node->data.light.hotspot_track,f)) + { + return(LIB3DS_FALSE); + } + if (!lib3ds_chunk_write_end(&c,f)) + { + return(LIB3DS_FALSE); + } + } + { /*---- LIB3DS_FALL_TRACK_TAG ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_FALL_TRACK_TAG; + if (!lib3ds_chunk_write_start(&c,f)) + { + return(LIB3DS_FALSE); + } + if (!lib3ds_lin1_track_write(&node->data.light.falloff_track,f)) + { + return(LIB3DS_FALSE); + } + if (!lib3ds_chunk_write_end(&c,f)) + { + return(LIB3DS_FALSE); + } + } + { /*---- LIB3DS_ROLL_TRACK_TAG ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_ROLL_TRACK_TAG; + if (!lib3ds_chunk_write_start(&c,f)) + { + return(LIB3DS_FALSE); + } + if (!lib3ds_lin1_track_write(&node->data.light.roll_track,f)) + { + return(LIB3DS_FALSE); + } + if (!lib3ds_chunk_write_end(&c,f)) + { + return(LIB3DS_FALSE); + } + } + break; + case LIB3DS_L_TARGET_NODE_TAG: + { /*---- LIB3DS_POS_TRACK_TAG ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_POS_TRACK_TAG; + if (!lib3ds_chunk_write_start(&c,f)) + { + return(LIB3DS_FALSE); + } + if (!lib3ds_lin3_track_write(&node->data.spot.pos_track,f)) + { + return(LIB3DS_FALSE); + } + if (!lib3ds_chunk_write_end(&c,f)) + { + return(LIB3DS_FALSE); + } + } + break; + default: + return(LIB3DS_FALSE); + } + + if (!lib3ds_chunk_write_end(&c,f)) + { + return(LIB3DS_FALSE); + } + return(LIB3DS_TRUE); +} + + +/*! + +\typedef Lib3dsNodeTypes + \ingroup node + +*/ +/*! + +\enum _Lib3dsNodeTypes + \ingroup node + +*/ +/*! + +\typedef Lib3dsBoolKey + \ingroup node + \sa _Lib3dsBoolKey + +*/ +/*! + +\typedef Lib3dsBoolTrack + \ingroup node + \sa _Lib3dsBoolTrack + +*/ +/*! + +\typedef Lib3dsLin1Key + \ingroup node + \sa _Lib3dsLin1Key + +*/ +/*! + +\typedef Lib3dsLin1Track + \ingroup node + \sa _Lib3dsLin1Track + +*/ +/*! + +\typedef Lib3dsLin3Key + \ingroup node + \sa _Lib3dsLin3Key + +*/ +/*! + +\typedef Lib3dsLin3Track + \ingroup node + \sa _Lib3dsLin3Track + +*/ +/*! + +\typedef Lib3dsQuatKey + \ingroup node + \sa _Lib3dsQuatKey + +*/ +/*! + +\typedef Lib3dsQuatTrack + \ingroup node + \sa _Lib3dsLin3Key + +*/ +/*! + +\typedef Lib3dsMorphKey + \ingroup node + \sa _Lib3dsMorphKey + +*/ +/*! + +\typedef Lib3dsMorphTrack + \ingroup node + \sa _Lib3dsMorphTrack + +*/ diff --git a/src/osgPlugins/lib3ds/node.h b/src/osgPlugins/lib3ds/node.h new file mode 100644 index 000000000..78438c7ba --- /dev/null +++ b/src/osgPlugins/lib3ds/node.h @@ -0,0 +1,169 @@ +/* -*- c -*- */ +#ifndef INCLUDED_LIB3DS_NODE_H +#define INCLUDED_LIB3DS_NODE_H +/* + * The 3D Studio File Format Library + * Copyright (C) 1996-2001 by J.E. Hoffmann + * All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or (at + * your option) any later version. + * + * 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 Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + * + * $Id$ + */ + +#ifndef INCLUDED_LIB3DS_TRACKS_H +#include +#endif + +#ifdef __cplusplus +extern "C" { +#endif + +/*! + * Scene graph ambient color node data + * \ingroup node + */ +typedef struct _Lib3dsAmbientData { + Lib3dsRgb col; + Lib3dsLin3Track col_track; +} Lib3dsAmbientData; + +/*! + * Scene graph object instance node data + * \ingroup node + */ +typedef struct _Lib3dsObjectData { + Lib3dsVector pivot; + char instance[64]; + Lib3dsVector bbox_min; + Lib3dsVector bbox_max; + Lib3dsVector pos; + Lib3dsLin3Track pos_track; + Lib3dsQuat rot; + Lib3dsQuatTrack rot_track; + Lib3dsVector scl; + Lib3dsLin3Track scl_track; + Lib3dsFloat morph_smooth; + char morph[64]; + Lib3dsMorphTrack morph_track; + Lib3dsBool hide; + Lib3dsBoolTrack hide_track; +} Lib3dsObjectData; + +/*! + * Scene graph camera node data + * \ingroup node + */ +typedef struct _Lib3dsCameraData { + Lib3dsVector pos; + Lib3dsLin3Track pos_track; + Lib3dsFloat fov; + Lib3dsLin1Track fov_track; + Lib3dsFloat roll; + Lib3dsLin1Track roll_track; +} Lib3dsCameraData; + +/*! + * Scene graph camera target node data + * \ingroup node + */ +typedef struct _Lib3dsTargetData { + Lib3dsVector pos; + Lib3dsLin3Track pos_track; +} Lib3dsTargetData; + +/*! + * Scene graph light node data + * \ingroup node + */ +typedef struct _Lib3dsLightData { + Lib3dsVector pos; + Lib3dsLin3Track pos_track; + Lib3dsRgb col; + Lib3dsLin3Track col_track; + Lib3dsFloat hotspot; + Lib3dsLin1Track hotspot_track; + Lib3dsFloat falloff; + Lib3dsLin1Track falloff_track; + Lib3dsFloat roll; + Lib3dsLin1Track roll_track; +} Lib3dsLightData; + +/*! + * Scene graph spotlight target node data + * \ingroup node + */ +typedef struct _Lib3dsSpotData { + Lib3dsVector pos; + Lib3dsLin3Track pos_track; +} Lib3dsSpotData; + +/*! + * Scene graph node data union + * \ingroup node + */ +typedef union _Lib3dsNodeData { + Lib3dsAmbientData ambient; + Lib3dsObjectData object; + Lib3dsCameraData camera; + Lib3dsTargetData target; + Lib3dsLightData light; + Lib3dsSpotData spot; +} Lib3dsNodeData; + +/*! + * \ingroup node + */ +#define LIB3DS_NO_PARENT 65535 + +/*! + * Scene graph node + * \ingroup node + */ +struct _Lib3dsNode { + Lib3dsUserData user; + Lib3dsNode *next;\ + Lib3dsNode *childs;\ + Lib3dsNode *parent;\ + Lib3dsNodeTypes type;\ + Lib3dsWord id;\ + char name[64];\ + Lib3dsWord flags1;\ + Lib3dsWord flags2;\ + Lib3dsWord parent_id; + Lib3dsMatrix matrix; + Lib3dsNodeData data; +}; + +extern LIB3DSAPI Lib3dsNode* lib3ds_node_new_ambient(); +extern LIB3DSAPI Lib3dsNode* lib3ds_node_new_object(); +extern LIB3DSAPI Lib3dsNode* lib3ds_node_new_camera(); +extern LIB3DSAPI Lib3dsNode* lib3ds_node_new_target(); +extern LIB3DSAPI Lib3dsNode* lib3ds_node_new_light(); +extern LIB3DSAPI Lib3dsNode* lib3ds_node_new_spot(); +extern LIB3DSAPI void lib3ds_node_free(Lib3dsNode *node); +extern LIB3DSAPI void lib3ds_node_eval(Lib3dsNode *node, Lib3dsFloat t); +extern LIB3DSAPI Lib3dsNode* lib3ds_node_by_name(Lib3dsNode *node, const char* name, + Lib3dsNodeTypes type); +extern LIB3DSAPI Lib3dsNode* lib3ds_node_by_id(Lib3dsNode *node, Lib3dsWord id); +extern LIB3DSAPI void lib3ds_node_dump(Lib3dsNode *node, Lib3dsIntd level); +extern LIB3DSAPI Lib3dsBool lib3ds_node_read(Lib3dsNode *node, Lib3dsFile *file, FILE *f); +extern LIB3DSAPI Lib3dsBool lib3ds_node_write(Lib3dsNode *node, Lib3dsFile *file, FILE *f); + +#ifdef __cplusplus +}; +#endif +#endif + diff --git a/src/osgPlugins/lib3ds/quat.cpp b/src/osgPlugins/lib3ds/quat.cpp new file mode 100644 index 000000000..11e2ad242 --- /dev/null +++ b/src/osgPlugins/lib3ds/quat.cpp @@ -0,0 +1,412 @@ +/* + * The 3D Studio File Format Library + * Copyright (C) 1996-2001 by J.E. Hoffmann + * All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or (at + * your option) any later version. + * + * 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 Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + * + * $Id$ + */ +#define LIB3DS_EXPORT +#include +#include + +/*! + * \defgroup quat Quaternion Mathematics + * + * \author J.E. Hoffmann + */ +/*! + * \typedef Lib3dsQuat + * \ingroup quat + */ + +/*! + * \ingroup quat + */ +void +lib3ds_quat_zero(Lib3dsQuat c) +{ + c[0]=c[1]=c[2]=c[3]=0.0f; +} + + +/*! + * \ingroup quat + */ +void +lib3ds_quat_identity(Lib3dsQuat c) +{ + c[0]=c[1]=c[2]=0.0f; + c[3]=1.0f; +} + + +/*! + * \ingroup quat + */ +void +lib3ds_quat_copy(Lib3dsQuat dest, Lib3dsQuat src) +{ + int i; + for (i=0; i<4; ++i) + { + dest[i]=src[i]; + } +} + + +/*! + * \ingroup quat + */ +void +lib3ds_quat_axis_angle(Lib3dsQuat c, Lib3dsVector axis, Lib3dsFloat angle) +{ + Lib3dsDouble omega,s; + Lib3dsDouble l; + + l=sqrt(axis[0]*axis[0] + axis[1]*axis[1] + axis[2]*axis[2]); + if (lLIB3DS_EPSILON) + { + if (fabs(l)>1.0f) l/=fabs(l); + om=acos(l); + sinom=sin(om); + if (fabs(sinom)>LIB3DS_EPSILON) + { + sp=sin((1.0f-t)*om)/sinom; + sq=sin(t*om)/sinom; + } + else + { + sp=1.0f-t; + sq=t; + } + c[0]=(Lib3dsFloat)(sp*a[0] + sq*b[0]); + c[1]=(Lib3dsFloat)(sp*a[1] + sq*b[1]); + c[2]=(Lib3dsFloat)(sp*a[2] + sq*b[2]); + c[3]=(Lib3dsFloat)(sp*a[3] + sq*b[3]); + } + else + { + q[0]=-a[1]; + q[1]=a[0]; + q[2]=-a[3]; + q[3]=a[2]; + sp=sin((1.0-t)*LIB3DS_HALFPI); + sq=sin(t*LIB3DS_HALFPI); + c[0]=(Lib3dsFloat)(sp*a[0] + sq*q[0]); + c[1]=(Lib3dsFloat)(sp*a[1] + sq*q[1]); + c[2]=(Lib3dsFloat)(sp*a[2] + sq*q[2]); + c[3]=(Lib3dsFloat)(sp*a[3] + sq*q[3]); + } +} + + +/*! + * \ingroup quat + */ +void +lib3ds_quat_squad(Lib3dsQuat c, Lib3dsQuat a, Lib3dsQuat p, Lib3dsQuat q, +Lib3dsQuat b, Lib3dsFloat t) +{ + Lib3dsQuat ab; + Lib3dsQuat pq; + + lib3ds_quat_slerp(ab,a,b,t); + lib3ds_quat_slerp(pq,p,q,t); + lib3ds_quat_slerp(c,ab,pq,2*t*(1-t)); +} + + +/*! + * \ingroup quat + */ +void +lib3ds_quat_tangent(Lib3dsQuat c, Lib3dsQuat p, Lib3dsQuat q, Lib3dsQuat n) +{ + Lib3dsQuat dn,dp,x; + int i; + + lib3ds_quat_ln_dif(dn, q, n); + lib3ds_quat_ln_dif(dp, q, p); + + for (i=0; i<4; i++) + { + x[i]=-1.0f/4.0f*(dn[i]+dp[i]); + } + lib3ds_quat_exp(x); + lib3ds_quat_mul(c,q,x); +} + + +/*! + * \ingroup quat + */ +void +lib3ds_quat_dump(Lib3dsQuat q) +{ + printf("%f %f %f %f\n", q[0], q[1], q[2], q[3]); +} diff --git a/src/osgPlugins/lib3ds/quat.h b/src/osgPlugins/lib3ds/quat.h new file mode 100644 index 000000000..68baf2600 --- /dev/null +++ b/src/osgPlugins/lib3ds/quat.h @@ -0,0 +1,61 @@ +/* -*- c -*- */ +#ifndef INCLUDED_LIB3DS_QUAT_H +#define INCLUDED_LIB3DS_QUAT_H +/* + * The 3D Studio File Format Library + * Copyright (C) 1996-2001 by J.E. Hoffmann + * All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or (at + * your option) any later version. + * + * 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 Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + * + * $Id$ + */ + +#ifndef INCLUDED_LIB3DS_TYPES_H +#include +#endif + +#ifdef __cplusplus +extern "C" { +#endif + +extern LIB3DSAPI void lib3ds_quat_zero(Lib3dsQuat c); +extern LIB3DSAPI void lib3ds_quat_identity(Lib3dsQuat c); +extern LIB3DSAPI void lib3ds_quat_copy(Lib3dsQuat dest, Lib3dsQuat src); +extern LIB3DSAPI void lib3ds_quat_axis_angle(Lib3dsQuat c, Lib3dsVector axis, Lib3dsFloat angle); +extern LIB3DSAPI void lib3ds_quat_neg(Lib3dsQuat c); +extern LIB3DSAPI void lib3ds_quat_abs(Lib3dsQuat c); +extern LIB3DSAPI void lib3ds_quat_cnj(Lib3dsQuat c); +extern LIB3DSAPI void lib3ds_quat_mul(Lib3dsQuat c, Lib3dsQuat a, Lib3dsQuat b); +extern LIB3DSAPI void lib3ds_quat_scalar(Lib3dsQuat c, Lib3dsFloat k); +extern LIB3DSAPI void lib3ds_quat_normalize(Lib3dsQuat c); +extern LIB3DSAPI void lib3ds_quat_inv(Lib3dsQuat c); +extern LIB3DSAPI Lib3dsFloat lib3ds_quat_dot(Lib3dsQuat a, Lib3dsQuat b); +extern LIB3DSAPI Lib3dsFloat lib3ds_quat_squared(Lib3dsQuat c); +extern LIB3DSAPI Lib3dsFloat lib3ds_quat_length(Lib3dsQuat c); +extern LIB3DSAPI void lib3ds_quat_ln(Lib3dsQuat c); +extern LIB3DSAPI void lib3ds_quat_ln_dif(Lib3dsQuat c, Lib3dsQuat a, Lib3dsQuat b); +extern LIB3DSAPI void lib3ds_quat_exp(Lib3dsQuat c); +extern LIB3DSAPI void lib3ds_quat_slerp(Lib3dsQuat c, Lib3dsQuat a, Lib3dsQuat b, Lib3dsFloat t); +extern LIB3DSAPI void lib3ds_quat_squad(Lib3dsQuat c, Lib3dsQuat a, Lib3dsQuat p, Lib3dsQuat q, + Lib3dsQuat b, Lib3dsFloat t); +extern LIB3DSAPI void lib3ds_quat_tangent(Lib3dsQuat c, Lib3dsQuat p, Lib3dsQuat q, Lib3dsQuat n); +extern LIB3DSAPI void lib3ds_quat_dump(Lib3dsQuat q); + +#ifdef __cplusplus +}; +#endif +#endif + diff --git a/src/osgPlugins/lib3ds/readwrite.cpp b/src/osgPlugins/lib3ds/readwrite.cpp new file mode 100644 index 000000000..e5d2a7c55 --- /dev/null +++ b/src/osgPlugins/lib3ds/readwrite.cpp @@ -0,0 +1,518 @@ +/* + * The 3D Studio File Format Library + * Copyright (C) 1996-2001 by J.E. Hoffmann + * All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or (at + * your option) any later version. + * + * 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 Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + * + * $Id$ + */ +#define LIB3DS_EXPORT +#include + +/*! + * \defgroup readwrite Portable Binary Input/Ouput + * + * \author J.E. Hoffmann + */ + +/*! + * \ingroup readwrite + * + * Read a byte from a file stream. + * + * \param f Input file stream. + * + * \return The byte read. + */ +Lib3dsByte +lib3ds_byte_read(FILE *f) +{ + Lib3dsByte b; + + ASSERT(f); + fread(&b,1,1,f); + return(b); +} + + +/** + * Read a word from a file stream in little endian format. + * + * \param f Input file stream. + * + * \return The word read. + */ +Lib3dsWord +lib3ds_word_read(FILE *f) +{ + Lib3dsByte b[2]; + Lib3dsWord w; + + ASSERT(f); + fread(b,2,1,f); + w=((Lib3dsWord)b[1] << 8) | + ((Lib3dsWord)b[0]); + return(w); +} + + +/*! + * \ingroup readwrite + * + * Read a dword from file a stream in little endian format. + * + * \param f Input file stream. + * + * \return The dword read. + */ +Lib3dsDword +lib3ds_dword_read(FILE *f) +{ + Lib3dsByte b[4]; + Lib3dsDword d; + + ASSERT(f); + fread(b,4,1,f); + d=((Lib3dsDword)b[3] << 24) | + ((Lib3dsDword)b[2] << 16) | + ((Lib3dsDword)b[1] << 8) | + ((Lib3dsDword)b[0]); + return(d); +} + + +/*! + * \ingroup readwrite + * + * Read a signed byte from a file stream. + * + * \param f Input file stream. + * + * \return The signed byte read. + */ +Lib3dsIntb +lib3ds_intb_read(FILE *f) +{ + Lib3dsIntb b; + + ASSERT(f); + fread(&b,1,1,f); + return(b); +} + + +/*! + * \ingroup readwrite + * + * Read a signed word from a file stream in little endian format. + * + * \param f Input file stream. + * + * \return The signed word read. + */ +Lib3dsIntw +lib3ds_intw_read(FILE *f) +{ + Lib3dsByte b[2]; + Lib3dsWord w; + + ASSERT(f); + fread(b,2,1,f); + w=((Lib3dsWord)b[1] << 8) | + ((Lib3dsWord)b[0]); + return((Lib3dsIntw)w); +} + + +/*! + * \ingroup readwrite + * + * Read a signed dword a from file stream in little endian format. + * + * \param f Input file stream. + * + * \return The signed dword read. + */ +Lib3dsIntd +lib3ds_intd_read(FILE *f) +{ + Lib3dsByte b[4]; + Lib3dsDword d; + + ASSERT(f); + fread(b,4,1,f); + d=((Lib3dsDword)b[3] << 24) | + ((Lib3dsDword)b[2] << 16) | + ((Lib3dsDword)b[1] << 8) | + ((Lib3dsDword)b[0]); + return((Lib3dsIntd)d); +} + + +/*! + * \ingroup readwrite + * + * Read a float from a file stream in little endian format. + * + * \param f Input file stream. + * + * \return The float read. + */ +Lib3dsFloat +lib3ds_float_read(FILE *f) +{ + Lib3dsByte b[4]; + Lib3dsDword d; + + ASSERT(f); + fread(b,4,1,f); + d=((Lib3dsDword)b[3] << 24) | + ((Lib3dsDword)b[2] << 16) | + ((Lib3dsDword)b[1] << 8) | + ((Lib3dsDword)b[0]); + return(*((Lib3dsFloat*)&d)); +} + + +/*! + * \ingroup readwrite + * \ingroup vector + * + * Read a vector from a file stream in little endian format. + * + * \param v The vector to store the data. + * \param f Input file stream. + * + * \return The float read. + */ +Lib3dsBool +lib3ds_vector_read(Lib3dsVector v, FILE *f) +{ + v[0]=lib3ds_float_read(f); + v[1]=lib3ds_float_read(f); + v[2]=lib3ds_float_read(f); + + if (ferror(f)) + { + return(LIB3DS_FALSE); + } + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup readwrite + */ +Lib3dsBool +lib3ds_rgb_read(Lib3dsRgb rgb, FILE *f) +{ + rgb[0]=lib3ds_float_read(f); + rgb[1]=lib3ds_float_read(f); + rgb[2]=lib3ds_float_read(f); + + if (ferror(f)) + { + return(LIB3DS_FALSE); + } + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup readwrite + * + * Read a zero-terminated string from a file stream. + * + * \param s The buffer to store the read string. + * \param buflen Buffer length. + * \param f The input file stream. + * + * \return True on success, False otherwise. + */ +Lib3dsBool +lib3ds_string_read(char *s, int buflen, FILE *f) +{ + int k=0; + ASSERT(f); + while ((*s++=fgetc(f))!=0) + { + if (++k>buflen) + { + return(LIB3DS_FALSE); + } + } + if (ferror(f)) + { + return(LIB3DS_FALSE); + } + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup readwrite + * + * Writes a byte into a file stream. + * + * \param b The byte to write to the file stream. + * \param f The input file stream. + * + * \return True on success, False otherwise. + */ +Lib3dsBool +lib3ds_byte_write(Lib3dsByte b, FILE *f) +{ + ASSERT(f); + if (fwrite(&b,1,1,f)!=1) + { + return(LIB3DS_FALSE); + } + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup readwrite + * + * Writes a word into a little endian file stream. + * + * \param w The word to write to the file stream. + * \param f The input file stream. + * + * \return True on success, False otherwise. + */ +Lib3dsBool +lib3ds_word_write(Lib3dsWord w, FILE *f) +{ + Lib3dsByte b[2]; + + ASSERT(f); + b[1]=((Lib3dsWord)w & 0xFF00) >> 8; + b[0]=((Lib3dsWord)w & 0x00FF); + if (fwrite(b,2,1,f)!=1) + { + return(LIB3DS_FALSE); + } + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup readwrite + * + * Writes a dword into a little endian file stream. + * + * \param d The dword to write to the file stream. + * \param f The input file stream. + * + * \return True on success, False otherwise. + */ +Lib3dsBool +lib3ds_dword_write(Lib3dsDword d, FILE *f) +{ + Lib3dsByte b[4]; + + ASSERT(f); + b[3]=(Lib3dsByte)(((Lib3dsDword)d & 0xFF000000) >> 24); + b[2]=(Lib3dsByte)(((Lib3dsDword)d & 0x00FF0000) >> 16); + b[1]=(Lib3dsByte)(((Lib3dsDword)d & 0x0000FF00) >> 8); + b[0]=(Lib3dsByte)(((Lib3dsDword)d & 0x000000FF)); + if (fwrite(b,4,1,f)!=1) + { + return(LIB3DS_FALSE); + } + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup readwrite + * + * Writes a signed byte in a file stream. + * + * \param b The signed byte to write to the file stream. + * \param f The input file stream. + * + * \return True on success, False otherwise. + */ +Lib3dsBool +lib3ds_intb_write(Lib3dsIntb b, FILE *f) +{ + ASSERT(f); + if (fwrite(&b,1,1,f)!=1) + { + return(LIB3DS_FALSE); + } + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup readwrite + * + * Writes a signed word into a little endian file stream. + * + * \param w The signed word to write to the file stream. + * \param f The input file stream. + * + * \return True on success, False otherwise. + */ +Lib3dsBool +lib3ds_intw_write(Lib3dsIntw w, FILE *f) +{ + Lib3dsByte b[2]; + + ASSERT(f); + b[1]=((Lib3dsWord)w & 0xFF00) >> 8; + b[0]=((Lib3dsWord)w & 0x00FF); + if (fwrite(b,2,1,f)!=1) + { + return(LIB3DS_FALSE); + } + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup readwrite + * + * Writes a signed dword into a little endian file stream. + * + * \param d The signed dword to write to the file stream. + * \param f The input file stream. + * + * \return True on success, False otherwise. + */ +Lib3dsBool +lib3ds_intd_write(Lib3dsIntd d, FILE *f) +{ + Lib3dsByte b[4]; + + ASSERT(f); + b[3]=(Lib3dsByte)(((Lib3dsDword)d & 0xFF000000) >> 24); + b[2]=(Lib3dsByte)(((Lib3dsDword)d & 0x00FF0000) >> 16); + b[1]=(Lib3dsByte)(((Lib3dsDword)d & 0x0000FF00) >> 8); + b[0]=(Lib3dsByte)(((Lib3dsDword)d & 0x000000FF)); + if (fwrite(b,4,1,f)!=1) + { + return(LIB3DS_FALSE); + } + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup readwrite + * + * Writes a float into a little endian file stream. + * + * \param f The float to write to the file stream. + * \param f The input file stream. + * + * \return True on success, False otherwise. + */ +Lib3dsBool +lib3ds_float_write(Lib3dsFloat l, FILE *f) +{ + Lib3dsByte b[4]; + Lib3dsDword d; + + ASSERT(f); + d=*((Lib3dsDword*)&l); + b[3]=(Lib3dsByte)(((Lib3dsDword)d & 0xFF000000) >> 24); + b[2]=(Lib3dsByte)(((Lib3dsDword)d & 0x00FF0000) >> 16); + b[1]=(Lib3dsByte)(((Lib3dsDword)d & 0x0000FF00) >> 8); + b[0]=(Lib3dsByte)(((Lib3dsDword)d & 0x000000FF)); + if (fwrite(b,4,1,f)!=1) + { + return(LIB3DS_FALSE); + } + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup readwrite + * \ingroup vector + * + * Writes a vector into a file stream in little endian format. + * + * \param v The vector to write to the file stream. + * \param f Input file stream. + */ +Lib3dsBool +lib3ds_vector_write(Lib3dsVector v, FILE *f) +{ + if (!lib3ds_float_write(v[0], f)) + { + return(LIB3DS_FALSE); + } + if (!lib3ds_float_write(v[1], f)) + { + return(LIB3DS_FALSE); + } + if (!lib3ds_float_write(v[2], f)) + { + return(LIB3DS_FALSE); + } + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup readwrite + */ +Lib3dsBool +lib3ds_rgb_write(Lib3dsRgb rgb, FILE *f) +{ + if (!lib3ds_float_write(rgb[0], f)) + { + return(LIB3DS_FALSE); + } + if (!lib3ds_float_write(rgb[1], f)) + { + return(LIB3DS_FALSE); + } + if (!lib3ds_float_write(rgb[2], f)) + { + return(LIB3DS_FALSE); + } + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup readwrite + * + * Writes a zero-terminated string into a file stream. + * + * \param f The float to write to the file stream. + * \param f The input file stream. + * + * \return True on success, False otherwise. + */ +Lib3dsBool +lib3ds_string_write(const char *s, FILE *f) +{ + ASSERT(s); + ASSERT(f); + do fputc(*s,f); while (*s++); + if (ferror(f)) + { + return(LIB3DS_FALSE); + } + return(LIB3DS_TRUE); +} diff --git a/src/osgPlugins/lib3ds/readwrite.h b/src/osgPlugins/lib3ds/readwrite.h new file mode 100644 index 000000000..bd05cf8e3 --- /dev/null +++ b/src/osgPlugins/lib3ds/readwrite.h @@ -0,0 +1,59 @@ +/* -*- c -*- */ +#ifndef INCLUDED_LIB3DS_READWRITE_H +#define INCLUDED_LIB3DS_READWRITE_H +/* + * The 3D Studio File Format Library + * Copyright (C) 1996-2001 by J.E. Hoffmann + * All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or (at + * your option) any later version. + * + * 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 Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + * + * $Id$ + */ + +#ifndef INCLUDED_LIB3DS_TYPES_H +#include +#endif + +#ifdef __cplusplus +extern "C" { +#endif + +extern LIB3DSAPI Lib3dsByte lib3ds_byte_read(FILE *f); +extern LIB3DSAPI Lib3dsWord lib3ds_word_read(FILE *f); +extern LIB3DSAPI Lib3dsDword lib3ds_dword_read(FILE *f); +extern LIB3DSAPI Lib3dsIntb lib3ds_intb_read(FILE *f); +extern LIB3DSAPI Lib3dsIntw lib3ds_intw_read(FILE *f); +extern LIB3DSAPI Lib3dsIntd lib3ds_intd_read(FILE *f); +extern LIB3DSAPI Lib3dsFloat lib3ds_float_read(FILE *f); +extern LIB3DSAPI Lib3dsBool lib3ds_vector_read(Lib3dsVector v, FILE *f); +extern LIB3DSAPI Lib3dsBool lib3ds_rgb_read(Lib3dsRgb rgb, FILE *f); +extern LIB3DSAPI Lib3dsBool lib3ds_string_read(char *s, int buflen, FILE *f); +extern LIB3DSAPI Lib3dsBool lib3ds_byte_write(Lib3dsByte b, FILE *f); +extern LIB3DSAPI Lib3dsBool lib3ds_word_write(Lib3dsWord w, FILE *f); +extern LIB3DSAPI Lib3dsBool lib3ds_dword_write(Lib3dsDword d, FILE *f); +extern LIB3DSAPI Lib3dsBool lib3ds_intb_write(Lib3dsIntb b, FILE *f); +extern LIB3DSAPI Lib3dsBool lib3ds_intw_write(Lib3dsIntw w, FILE *f); +extern LIB3DSAPI Lib3dsBool lib3ds_intd_write(Lib3dsIntd d, FILE *f); +extern LIB3DSAPI Lib3dsBool lib3ds_float_write(Lib3dsFloat l, FILE *f); +extern LIB3DSAPI Lib3dsBool lib3ds_vector_write(Lib3dsVector v, FILE *f); +extern LIB3DSAPI Lib3dsBool lib3ds_rgb_write(Lib3dsRgb rgb, FILE *f); +extern LIB3DSAPI Lib3dsBool lib3ds_string_write(const char *s, FILE *f); + +#ifdef __cplusplus +}; +#endif +#endif + diff --git a/src/osgPlugins/lib3ds/shadow.cpp b/src/osgPlugins/lib3ds/shadow.cpp new file mode 100644 index 000000000..60e1c2de5 --- /dev/null +++ b/src/osgPlugins/lib3ds/shadow.cpp @@ -0,0 +1,154 @@ +/* + * The 3D Studio File Format Library + * Copyright (C) 1996-2001 by J.E. Hoffmann + * All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or (at + * your option) any later version. + * + * 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 Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + * + * $Id$ + */ +#define LIB3DS_EXPORT +#include +#include +#include + +/*! + * \defgroup shadow Shadow Map Settings + * + * \author J.E. Hoffmann + */ + +/*! + * \ingroup shadow + */ +Lib3dsBool +lib3ds_shadow_read(Lib3dsShadow *shadow, FILE *f) +{ + Lib3dsChunk c; + + if (!lib3ds_chunk_read(&c, f)) + { + return(LIB3DS_FALSE); + } + + switch (c.chunk) + { + case LIB3DS_SHADOW_MAP_SIZE: + { + shadow->map_size=lib3ds_intw_read(f); + } + break; + case LIB3DS_LO_SHADOW_BIAS: + { + shadow->lo_bias=lib3ds_float_read(f); + } + break; + case LIB3DS_HI_SHADOW_BIAS: + { + shadow->hi_bias=lib3ds_float_read(f); + } + break; + case LIB3DS_SHADOW_SAMPLES: + { + shadow->samples=lib3ds_intw_read(f); + } + break; + case LIB3DS_SHADOW_RANGE: + { + shadow->range=lib3ds_intw_read(f); + } + break; + case LIB3DS_SHADOW_FILTER: + { + shadow->filter=lib3ds_float_read(f); + } + break; + case LIB3DS_RAY_BIAS: + { + shadow->ray_bias=lib3ds_float_read(f); + } + break; + } + + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup shadow + */ +Lib3dsBool +lib3ds_shadow_write(Lib3dsShadow *shadow, FILE *f) +{ + { /*---- LIB3DS_LO_SHADOW_BIAS ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_LO_SHADOW_BIAS; + c.size=10; + lib3ds_chunk_write(&c,f); + lib3ds_float_write(shadow->lo_bias,f); + } + { /*---- LIB3DS_HI_SHADOW_BIAS ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_HI_SHADOW_BIAS; + c.size=10; + lib3ds_chunk_write(&c,f); + lib3ds_float_write(shadow->hi_bias,f); + } + { /*---- LIB3DS_SHADOW_MAP_SIZE ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_SHADOW_MAP_SIZE; + c.size=8; + lib3ds_chunk_write(&c,f); + lib3ds_intw_write(shadow->map_size,f); + } + { /*---- LIB3DS_SHADOW_SAMPLES ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_SHADOW_SAMPLES; + c.size=8; + lib3ds_chunk_write(&c,f); + lib3ds_intw_write(shadow->samples,f); + } + { /*---- LIB3DS_SHADOW_RANGE ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_SHADOW_RANGE; + c.size=8; + lib3ds_chunk_write(&c,f); + lib3ds_intw_write(shadow->range,f); + } + { /*---- LIB3DS_SHADOW_FILTER ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_SHADOW_FILTER; + c.size=10; + lib3ds_chunk_write(&c,f); + lib3ds_float_write(shadow->filter,f); + } + { /*---- LIB3DS_RAY_BIAS ----*/ + Lib3dsChunk c; + c.chunk=LIB3DS_RAY_BIAS; + c.size=10; + lib3ds_chunk_write(&c,f); + lib3ds_float_write(shadow->ray_bias,f); + } + return(LIB3DS_TRUE); +} + + +/*! + +\typedef Lib3dsShadow + \ingroup shadow + \sa _Lib3dsShadow + +*/ diff --git a/src/osgPlugins/lib3ds/shadow.h b/src/osgPlugins/lib3ds/shadow.h new file mode 100644 index 000000000..48d26bea9 --- /dev/null +++ b/src/osgPlugins/lib3ds/shadow.h @@ -0,0 +1,59 @@ +/* -*- c -*- */ +#ifndef INCLUDED_LIB3DS_SHADOW_H +#define INCLUDED_LIB3DS_SHADOW_H +/* + * The 3D Studio File Format Library + * Copyright (C) 1996-2001 by J.E. Hoffmann + * All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or (at + * your option) any later version. + * + * 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 Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + * + * $Id$ + */ + +#ifndef INCLUDED_LIB3DS_TYPES_H +#include +#endif + +#ifdef __cplusplus +extern "C" { +#endif + +/*! + * Shadow map settings + * \ingroup shadow + */ +struct _Lib3dsShadow { + Lib3dsIntw map_size; + Lib3dsFloat lo_bias; + Lib3dsFloat hi_bias; + Lib3dsIntw samples; + Lib3dsIntw range; + Lib3dsFloat filter; + Lib3dsFloat ray_bias; +}; + +extern LIB3DSAPI Lib3dsBool lib3ds_shadow_read(Lib3dsShadow *shadow, FILE *f); +extern LIB3DSAPI Lib3dsBool lib3ds_shadow_write(Lib3dsShadow *shadow, FILE *f); + +#ifdef __cplusplus +}; +#endif +#endif + + + + + diff --git a/src/osgPlugins/lib3ds/tcb.cpp b/src/osgPlugins/lib3ds/tcb.cpp new file mode 100644 index 000000000..6c62e8c87 --- /dev/null +++ b/src/osgPlugins/lib3ds/tcb.cpp @@ -0,0 +1,148 @@ +/* + * The 3D Studio File Format Library + * Copyright (C) 1996-2001 by J.E. Hoffmann + * All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or (at + * your option) any later version. + * + * 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 Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + * + * $Id$ + */ +#define LIB3DS_EXPORT +#include +#include +#include + +/*! + * \defgroup tcb Tension/Continuity/Bias Splines + * + * \author J.E. Hoffmann + */ + +/*! + * \ingroup tcb + */ +void +lib3ds_tcb(Lib3dsTcb *p, Lib3dsTcb *pc, Lib3dsTcb *c, Lib3dsTcb *nc, Lib3dsTcb *n, +Lib3dsFloat *ksm, Lib3dsFloat *ksp, Lib3dsFloat *kdm, Lib3dsFloat *kdp) +{ + Lib3dsFloat tm,cm,cp,bm,bp,tmcm,tmcp,cc; + Lib3dsFloat dt,fp,fn; + + if (!pc) + { + pc=c; + } + if (!nc) + { + nc=c; + } + + fp=fn=1.0f; + if (p&&n) + { + dt=0.5f*(Lib3dsFloat)(pc->frame-p->frame+n->frame-nc->frame); + fp=((Lib3dsFloat)(pc->frame-p->frame))/dt; + fn=((Lib3dsFloat)(n->frame-nc->frame))/dt; + cc=(Lib3dsFloat)fabs(c->cont); + fp=fp+cc-cc*fp; + fn=fn+cc-cc*fn; + } + + cm=1.0f-c->cont; + tm=0.5f*(1.0f-c->tens); + cp=2.0f-cm; + bm=1.0f-c->bias; + bp=2.0f-bm; + tmcm=tm*cm; + tmcp=tm*cp; + *ksm=tmcm*bp*fp; + *ksp=tmcp*bm*fp; + *kdm=tmcp*bp*fn; + *kdp=tmcm*bm*fn; +} + + +/*! + * \ingroup tcb + */ +Lib3dsBool +lib3ds_tcb_read(Lib3dsTcb *tcb, FILE *f) +{ + Lib3dsWord flags; + + tcb->frame=lib3ds_intd_read(f); + tcb->flags=flags=lib3ds_word_read(f); + if (flags&LIB3DS_USE_TENSION) + { + tcb->tens=lib3ds_float_read(f); + } + if (flags&LIB3DS_USE_CONTINUITY) + { + tcb->cont=lib3ds_float_read(f); + } + if (flags&LIB3DS_USE_BIAS) + { + tcb->bias=lib3ds_float_read(f); + } + if (flags&LIB3DS_USE_EASE_TO) + { + tcb->ease_to=lib3ds_float_read(f); + } + if (flags&LIB3DS_USE_EASE_FROM) + { + tcb->ease_from=lib3ds_float_read(f); + } + if (ferror(f)) + { + return(LIB3DS_FALSE); + } + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup tcb + */ +Lib3dsBool +lib3ds_tcb_write(Lib3dsTcb *tcb, FILE *f) +{ + lib3ds_intd_write(tcb->frame,f); + lib3ds_word_write(tcb->flags,f); + if (tcb->flags&LIB3DS_USE_TENSION) + { + lib3ds_float_write(tcb->tens,f); + } + if (tcb->flags&LIB3DS_USE_CONTINUITY) + { + lib3ds_float_write(tcb->cont,f); + } + if (tcb->flags&LIB3DS_USE_BIAS) + { + lib3ds_float_write(tcb->bias,f); + } + if (tcb->flags&LIB3DS_USE_EASE_TO) + { + lib3ds_float_write(tcb->ease_to,f); + } + if (tcb->flags&LIB3DS_USE_EASE_FROM) + { + lib3ds_float_write(tcb->ease_from,f); + } + if (ferror(f)) + { + return(LIB3DS_FALSE); + } + return(LIB3DS_TRUE); +} diff --git a/src/osgPlugins/lib3ds/tcb.h b/src/osgPlugins/lib3ds/tcb.h new file mode 100644 index 000000000..f8ec1da41 --- /dev/null +++ b/src/osgPlugins/lib3ds/tcb.h @@ -0,0 +1,62 @@ +/* -*- c -*- */ +#ifndef INCLUDED_LIB3DS_TCB_H +#define INCLUDED_LIB3DS_TCB_H +/* + * The 3D Studio File Format Library + * Copyright (C) 1996-2001 by J.E. Hoffmann + * All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or (at + * your option) any later version. + * + * 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 Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + * + * $Id$ + */ + +#ifndef INCLUDED_LIB3DS_TYPES_H +#include +#endif + +#ifdef __cplusplus +extern "C" { +#endif + +typedef enum _Lib3dsTcbFlags{ + LIB3DS_USE_TENSION =0x0001, + LIB3DS_USE_CONTINUITY =0x0002, + LIB3DS_USE_BIAS =0x0004, + LIB3DS_USE_EASE_TO =0x0008, + LIB3DS_USE_EASE_FROM =0x0010 +} Lib3dsTcbFlags; + +typedef struct _Lib3dsTcb { + Lib3dsIntd frame; + Lib3dsWord flags; + Lib3dsFloat tens; + Lib3dsFloat cont; + Lib3dsFloat bias; + Lib3dsFloat ease_to; + Lib3dsFloat ease_from; +} Lib3dsTcb; + +extern LIB3DSAPI void lib3ds_tcb(Lib3dsTcb *p, Lib3dsTcb *pc, Lib3dsTcb *c, + Lib3dsTcb *nc, Lib3dsTcb *n, Lib3dsFloat *ksm, Lib3dsFloat *ksp, + Lib3dsFloat *kdm, Lib3dsFloat *kdp); +extern LIB3DSAPI Lib3dsBool lib3ds_tcb_read(Lib3dsTcb *tcb, FILE *f); +extern LIB3DSAPI Lib3dsBool lib3ds_tcb_write(Lib3dsTcb *tcb, FILE *f); + +#ifdef __cplusplus +}; +#endif +#endif + diff --git a/src/osgPlugins/lib3ds/tracks.cpp b/src/osgPlugins/lib3ds/tracks.cpp new file mode 100644 index 000000000..5f3987fb0 --- /dev/null +++ b/src/osgPlugins/lib3ds/tracks.cpp @@ -0,0 +1,1576 @@ +/* + * The 3D Studio File Format Library + * Copyright (C) 1996-2001 by J.E. Hoffmann + * All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or (at + * your option) any later version. + * + * 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 Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + * + * $Id$ + */ +#define LIB3DS_EXPORT +#include +#include +#include +#include +#include +#include +#include +#include +#include +//#include +#ifdef WITH_DMALLOC +#include +#endif + +/*! + * \defgroup tracks Keyframing Tracks + * + * \author J.E. Hoffmann + */ + +/*! + * \ingroup tracks + */ +Lib3dsBoolKey* +lib3ds_bool_key_new() +{ + Lib3dsBoolKey* k; + k=(Lib3dsBoolKey*)calloc(sizeof(Lib3dsBoolKey), 1); + return(k); +} + + +/*! + * \ingroup tracks + */ +void +lib3ds_bool_key_free(Lib3dsBoolKey *key) +{ + ASSERT(key); + free(key); +} + + +/*! + * \ingroup tracks + */ +void +lib3ds_bool_track_free_keys(Lib3dsBoolTrack *track) +{ + Lib3dsBoolKey *p,*q; + + ASSERT(track); + for (p=track->keyL; p; p=q) + { + q=p->next; + lib3ds_bool_key_free(p); + } +} + + +/*! + * \ingroup tracks + */ +void +lib3ds_bool_track_insert(Lib3dsBoolTrack *track, Lib3dsBoolKey *key) +{ + ASSERT(track); + ASSERT(key); + ASSERT(!key->next); + + if (!track->keyL) + { + track->keyL=key; + key->next=0; + } + else + { + Lib3dsBoolKey *k,*p; + + for (p=0,k=track->keyL; k!=0; p=k, k=k->next) + { + if (k->tcb.frame>key->tcb.frame) + { + break; + } + } + if (!p) + { + key->next=track->keyL; + track->keyL=key; + } + else + { + key->next=k; + p->next=key; + } + + if (k && (key->tcb.frame==k->tcb.frame)) + { + key->next=k->next; + lib3ds_bool_key_free(k); + } + } +} + + +/*! + * \ingroup tracks + */ +void +lib3ds_bool_track_remove(Lib3dsBoolTrack *track, Lib3dsIntd frame) +{ + Lib3dsBoolKey *k,*p; + + ASSERT(track); + if (!track->keyL) + { + return; + } + for (p=0,k=track->keyL; k!=0; p=k, k=k->next) + { + if (k->tcb.frame==frame) + { + if (!p) + { + track->keyL=track->keyL->next; + } + else + { + p->next=k->next; + } + lib3ds_bool_key_free(k); + break; + } + } +} + + +/*! + * \ingroup tracks + */ +void +lib3ds_bool_track_eval(Lib3dsBoolTrack *track, Lib3dsBool *p, Lib3dsFloat t) +{ + Lib3dsBoolKey *k; + Lib3dsBool result; + + ASSERT(p); + if (!track->keyL) + { + *p=LIB3DS_FALSE; + return; + } + if (!track->keyL->next) + { + *p = LIB3DS_TRUE; + return; + } + + result=LIB3DS_FALSE; + k=track->keyL; + while ((t<(Lib3dsFloat)k->tcb.frame) && (t>=(Lib3dsFloat)k->next->tcb.frame)) + { + if (result) + { + result=LIB3DS_FALSE; + } + else + { + result=LIB3DS_TRUE; + } + if (!k->next) + { + if (track->flags&LIB3DS_REPEAT) + { + t-=(Lib3dsFloat)k->tcb.frame; + k=track->keyL; + } + else + { + break; + } + } + else + { + k=k->next; + } + } + *p=result; +} + + +/*! + * \ingroup tracks + */ +Lib3dsBool +lib3ds_bool_track_read(Lib3dsBoolTrack *track, FILE *f) +{ + int keys; + int i; + Lib3dsBoolKey *k; + + track->flags=lib3ds_word_read(f); + lib3ds_dword_read(f); + lib3ds_dword_read(f); + keys=lib3ds_intd_read(f); + + for (i=0; itcb, f)) + { + return(LIB3DS_FALSE); + } + lib3ds_bool_track_insert(track, k); + } + + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup tracks + */ +Lib3dsBool +lib3ds_bool_track_write(Lib3dsBoolTrack *track, FILE *f) +{ + Lib3dsBoolKey *k; + Lib3dsDword num=0; + for (k=track->keyL; k; k=k->next) + { + ++num; + } + lib3ds_word_write((Lib3dsWord)track->flags,f); + lib3ds_dword_write(0,f); + lib3ds_dword_write(0,f); + lib3ds_dword_write(num,f); + + for (k=track->keyL; k; k=k->next) + { + if (!lib3ds_tcb_write(&k->tcb,f)) + { + return(LIB3DS_FALSE); + } + } + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup tracks + */ +Lib3dsLin1Key* +lib3ds_lin1_key_new() +{ + Lib3dsLin1Key* k; + k=(Lib3dsLin1Key*)calloc(sizeof(Lib3dsLin1Key), 1); + return(k); +} + + +/*! + * \ingroup tracks + */ +void +lib3ds_lin1_key_free(Lib3dsLin1Key *key) +{ + ASSERT(key); + free(key); +} + + +/*! + * \ingroup tracks + */ +void +lib3ds_lin1_track_free_keys(Lib3dsLin1Track *track) +{ + Lib3dsLin1Key *p,*q; + + ASSERT(track); + for (p=track->keyL; p; p=q) + { + q=p->next; + lib3ds_lin1_key_free(p); + } +} + + +/*! + * \ingroup tracks + */ +void +lib3ds_lin1_key_setup(Lib3dsLin1Key *p, Lib3dsLin1Key *cp, Lib3dsLin1Key *c, +Lib3dsLin1Key *cn, Lib3dsLin1Key *n) +{ + Lib3dsFloat np,nn; + Lib3dsFloat ksm,ksp,kdm,kdp; + + ASSERT(c); + if (!cp) + { + cp=c; + } + if (!cn) + { + cn=c; + } + if (!p && !n) + { + c->ds=0; + c->dd=0; + return; + } + + if (n && p) + { + lib3ds_tcb(&p->tcb, &cp->tcb, &c->tcb, &cn->tcb, &n->tcb, &ksm, &ksp, &kdm, &kdp); + np = c->value - p->value; + nn = n->value - c->value; + + c->ds=ksm*np + ksp*nn; + c->dd=kdm*np + kdp*nn; + } + else + { + if (p) + { + np = c->value - p->value; + c->ds = np; + c->dd = np; + } + if (n) + { + nn = n->value - c->value; + c->ds = nn; + c->dd = nn; + } + } +} + + +/*! + * \ingroup tracks + */ +void +lib3ds_lin1_track_setup(Lib3dsLin1Track *track) +{ + Lib3dsLin1Key *pp,*pc,*pn,*pl; + + ASSERT(track); + pc=track->keyL; + if (!pc) + { + return; + } + if (!pc->next) + { + pc->ds=0; + pc->dd=0; + return; + } + + if (track->flags&LIB3DS_SMOOTH) + { + for (pl=track->keyL; pl->next->next; pl=pl->next); + lib3ds_lin1_key_setup(pl, pl->next, pc, 0, pc->next); + } + else + { + lib3ds_lin1_key_setup(0, 0, pc, 0, pc->next); + } + for (;;) + { + pp=pc; + pc=pc->next; + pn=pc->next; + if (!pn) + { + break; + } + lib3ds_lin1_key_setup(pp, 0, pc, 0, pn); + } + + if (track->flags&LIB3DS_SMOOTH) + { + lib3ds_lin1_key_setup(pp, 0, pc, track->keyL, track->keyL->next); + } + else + { + lib3ds_lin1_key_setup(pp, 0, pc, 0, 0); + } +} + + +/*! + * \ingroup tracks + */ +void +lib3ds_lin1_track_insert(Lib3dsLin1Track *track, Lib3dsLin1Key *key) +{ + ASSERT(track); + ASSERT(key); + ASSERT(!key->next); + + if (!track->keyL) + { + track->keyL=key; + key->next=0; + } + else + { + Lib3dsLin1Key *k,*p; + + for (p=0,k=track->keyL; k!=0; p=k, k=k->next) + { + if (k->tcb.frame>key->tcb.frame) + { + break; + } + } + if (!p) + { + key->next=track->keyL; + track->keyL=key; + } + else + { + key->next=k; + p->next=key; + } + + if (k && (key->tcb.frame==k->tcb.frame)) + { + key->next=k->next; + lib3ds_lin1_key_free(k); + } + } +} + + +/*! + * \ingroup tracks + */ +void +lib3ds_lin1_track_remove(Lib3dsLin1Track *track, Lib3dsIntd frame) +{ + Lib3dsLin1Key *k,*p; + + ASSERT(track); + if (!track->keyL) + { + return; + } + for (p=0,k=track->keyL; k!=0; p=k, k=k->next) + { + if (k->tcb.frame==frame) + { + if (!p) + { + track->keyL=track->keyL->next; + } + else + { + p->next=k->next; + } + lib3ds_lin1_key_free(k); + break; + } + } +} + + +/*! + * \ingroup tracks + */ +void +lib3ds_lin1_track_eval(Lib3dsLin1Track *track, Lib3dsFloat *p, Lib3dsFloat t) +{ + Lib3dsLin1Key *k; + Lib3dsFloat nt; + Lib3dsFloat u; + + ASSERT(p); + if (!track->keyL) + { + *p=0; + return; + } + if (!track->keyL->next) + { + *p = track->keyL->value; + return; + } + + for (k=track->keyL; k->next!=0; k=k->next) + { + if ((t>=(Lib3dsFloat)k->tcb.frame) && (t<(Lib3dsFloat)k->next->tcb.frame)) + { + break; + } + } + if (!k->next) + { + if (track->flags&LIB3DS_REPEAT) + { + nt=(Lib3dsFloat)fmod(t, k->tcb.frame); + for (k=track->keyL; k->next!=0; k=k->next) + { + if ((nt>=(Lib3dsFloat)k->tcb.frame) && (nt<(Lib3dsFloat)k->next->tcb.frame)) + { + break; + } + } + ASSERT(k->next); + } + else + { + *p = k->value; + return; + } + } + else + { + nt=t; + } + u=nt - (Lib3dsFloat)k->tcb.frame; + u/=(Lib3dsFloat)(k->next->tcb.frame - k->tcb.frame); + + *p = lib3ds_float_cubic( + k->value, + k->dd, + k->next->ds, + k->next->value, + u + ); +} + + +/*! + * \ingroup tracks + */ +Lib3dsBool +lib3ds_lin1_track_read(Lib3dsLin1Track *track, FILE *f) +{ + int keys; + int i; + Lib3dsLin1Key *k; + + track->flags=lib3ds_word_read(f); + lib3ds_dword_read(f); + lib3ds_dword_read(f); + keys=lib3ds_intd_read(f); + + for (i=0; itcb, f)) + { + return(LIB3DS_FALSE); + } + k->value=lib3ds_float_read(f); + lib3ds_lin1_track_insert(track, k); + } + lib3ds_lin1_track_setup(track); + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup tracks + */ +Lib3dsBool +lib3ds_lin1_track_write(Lib3dsLin1Track *track, FILE *f) +{ + Lib3dsLin1Key *k; + Lib3dsDword num=0; + for (k=track->keyL; k; k=k->next) + { + ++num; + } + lib3ds_word_write((Lib3dsWord)track->flags,f); + lib3ds_dword_write(0,f); + lib3ds_dword_write(0,f); + lib3ds_dword_write(num,f); + + for (k=track->keyL; k; k=k->next) + { + if (!lib3ds_tcb_write(&k->tcb,f)) + { + return(LIB3DS_FALSE); + } + lib3ds_float_write(k->value,f); + } + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup tracks + */ +Lib3dsLin3Key* +lib3ds_lin3_key_new() +{ + Lib3dsLin3Key* k; + k=(Lib3dsLin3Key*)calloc(sizeof(Lib3dsLin3Key), 1); + return(k); +} + + +/*! + * \ingroup tracks + */ +void +lib3ds_lin3_key_free(Lib3dsLin3Key *key) +{ + ASSERT(key); + free(key); +} + + +/*! + * \ingroup tracks + */ +void +lib3ds_lin3_track_free_keys(Lib3dsLin3Track *track) +{ + Lib3dsLin3Key *p,*q; + + ASSERT(track); + for (p=track->keyL; p; p=q) + { + q=p->next; + lib3ds_lin3_key_free(p); + } +} + + +/*! + * \ingroup tracks + */ +void +lib3ds_lin3_key_setup(Lib3dsLin3Key *p, Lib3dsLin3Key *cp, Lib3dsLin3Key *c, +Lib3dsLin3Key *cn, Lib3dsLin3Key *n) +{ + Lib3dsVector np,nn; + Lib3dsFloat ksm,ksp,kdm,kdp; + int i; + + ASSERT(c); + if (!cp) + { + cp=c; + } + if (!cn) + { + cn=c; + } + if (!p && !n) + { + lib3ds_vector_zero(c->ds); + lib3ds_vector_zero(c->dd); + return; + } + + if (n && p) + { + lib3ds_tcb(&p->tcb, &cp->tcb, &c->tcb, &cn->tcb, &n->tcb, &ksm, &ksp, &kdm, &kdp); + lib3ds_vector_sub(np, c->value, p->value); + lib3ds_vector_sub(nn, n->value, c->value); + + for(i=0; i<3; ++i) + { + c->ds[i]=ksm*np[i] + ksp*nn[i]; + c->dd[i]=kdm*np[i] + kdp*nn[i]; + } + } + else + { + if (p) + { + lib3ds_vector_sub(np, c->value, p->value); + lib3ds_vector_copy(c->ds, np); + lib3ds_vector_copy(c->dd, np); + } + if (n) + { + lib3ds_vector_sub(nn, n->value, c->value); + lib3ds_vector_copy(c->ds, nn); + lib3ds_vector_copy(c->dd, nn); + } + } +} + + +/*! + * \ingroup tracks + */ +void +lib3ds_lin3_track_setup(Lib3dsLin3Track *track) +{ + Lib3dsLin3Key *pp,*pc,*pn,*pl; + + ASSERT(track); + pc=track->keyL; + if (!pc) + { + return; + } + if (!pc->next) + { + lib3ds_vector_zero(pc->ds); + lib3ds_vector_zero(pc->dd); + return; + } + + if (track->flags&LIB3DS_SMOOTH) + { + for (pl=track->keyL; pl->next->next; pl=pl->next); + lib3ds_lin3_key_setup(pl, pl->next, pc, 0, pc->next); + } + else + { + lib3ds_lin3_key_setup(0, 0, pc, 0, pc->next); + } + for (;;) + { + pp=pc; + pc=pc->next; + pn=pc->next; + if (!pn) + { + break; + } + lib3ds_lin3_key_setup(pp, 0, pc, 0, pn); + } + + if (track->flags&LIB3DS_SMOOTH) + { + lib3ds_lin3_key_setup(pp, 0, pc, track->keyL, track->keyL->next); + } + else + { + lib3ds_lin3_key_setup(pp, 0, pc, 0, 0); + } +} + + +/*! + * \ingroup tracks + */ +void +lib3ds_lin3_track_insert(Lib3dsLin3Track *track, Lib3dsLin3Key *key) +{ + ASSERT(track); + ASSERT(key); + ASSERT(!key->next); + + if (!track->keyL) + { + track->keyL=key; + key->next=0; + } + else + { + Lib3dsLin3Key *k,*p; + + for (p=0,k=track->keyL; k!=0; p=k, k=k->next) + { + if (k->tcb.frame>key->tcb.frame) + { + break; + } + } + if (!p) + { + key->next=track->keyL; + track->keyL=key; + } + else + { + key->next=k; + p->next=key; + } + + if (k && (key->tcb.frame==k->tcb.frame)) + { + key->next=k->next; + lib3ds_lin3_key_free(k); + } + } +} + + +/*! + * \ingroup tracks + */ +void +lib3ds_lin3_track_remove(Lib3dsLin3Track *track, Lib3dsIntd frame) +{ + Lib3dsLin3Key *k,*p; + + ASSERT(track); + if (!track->keyL) + { + return; + } + for (p=0,k=track->keyL; k!=0; p=k, k=k->next) + { + if (k->tcb.frame==frame) + { + if (!p) + { + track->keyL=track->keyL->next; + } + else + { + p->next=k->next; + } + lib3ds_lin3_key_free(k); + break; + } + } +} + + +/*! + * \ingroup tracks + */ +void +lib3ds_lin3_track_eval(Lib3dsLin3Track *track, Lib3dsVector p, Lib3dsFloat t) +{ + Lib3dsLin3Key *k; + Lib3dsFloat nt; + Lib3dsFloat u; + + if (!track->keyL) + { + lib3ds_vector_zero(p); + return; + } + if (!track->keyL->next) + { + lib3ds_vector_copy(p, track->keyL->value); + return; + } + + for (k=track->keyL; k->next!=0; k=k->next) + { + if ((t>=(Lib3dsFloat)k->tcb.frame) && (t<(Lib3dsFloat)k->next->tcb.frame)) + { + break; + } + } + if (!k->next) + { + if (track->flags&LIB3DS_REPEAT) + { + nt=(Lib3dsFloat)fmod(t, k->tcb.frame); + for (k=track->keyL; k->next!=0; k=k->next) + { + if ((nt>=(Lib3dsFloat)k->tcb.frame) && (nt<(Lib3dsFloat)k->next->tcb.frame)) + { + break; + } + } + ASSERT(k->next); + } + else + { + lib3ds_vector_copy(p, k->value); + return; + } + } + else + { + nt=t; + } + u=nt - (Lib3dsFloat)k->tcb.frame; + u/=(Lib3dsFloat)(k->next->tcb.frame - k->tcb.frame); + + lib3ds_vector_cubic( + p, + k->value, + k->dd, + k->next->ds, + k->next->value, + u + ); +} + + +/*! + * \ingroup tracks + */ +Lib3dsBool +lib3ds_lin3_track_read(Lib3dsLin3Track *track, FILE *f) +{ + int keys; + int i,j; + Lib3dsLin3Key *k; + + track->flags=lib3ds_word_read(f); + lib3ds_dword_read(f); + lib3ds_dword_read(f); + keys=lib3ds_intd_read(f); + + for (i=0; itcb, f)) + { + return(LIB3DS_FALSE); + } + for (j=0; j<3; ++j) + { + k->value[j]=lib3ds_float_read(f); + } + lib3ds_lin3_track_insert(track, k); + } + lib3ds_lin3_track_setup(track); + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup tracks + */ +Lib3dsBool +lib3ds_lin3_track_write(Lib3dsLin3Track *track, FILE *f) +{ + Lib3dsLin3Key *k; + Lib3dsDword num=0; + for (k=track->keyL; k; k=k->next) + { + ++num; + } + lib3ds_word_write((Lib3dsWord)track->flags,f); + lib3ds_dword_write(0,f); + lib3ds_dword_write(0,f); + lib3ds_dword_write(num,f); + + for (k=track->keyL; k; k=k->next) + { + if (!lib3ds_tcb_write(&k->tcb,f)) + { + return(LIB3DS_FALSE); + } + lib3ds_vector_write(k->value,f); + } + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup tracks + */ +Lib3dsQuatKey* +lib3ds_quat_key_new() +{ + Lib3dsQuatKey* k; + k=(Lib3dsQuatKey*)calloc(sizeof(Lib3dsQuatKey), 1); + return(k); +} + + +/*! + * \ingroup tracks + */ +void +lib3ds_quat_key_free(Lib3dsQuatKey *key) +{ + ASSERT(key); + free(key); +} + + +/*! + * \ingroup tracks + */ +void +lib3ds_quat_track_free_keys(Lib3dsQuatTrack *track) +{ + Lib3dsQuatKey *p,*q; + + ASSERT(track); + for (p=track->keyL; p; p=q) + { + q=p->next; + lib3ds_quat_key_free(p); + } +} + + +/*! + * \ingroup tracks + */ +void +lib3ds_quat_key_setup(Lib3dsQuatKey *p, Lib3dsQuatKey *cp, Lib3dsQuatKey *c, +Lib3dsQuatKey *cn, Lib3dsQuatKey *n) +{ + Lib3dsFloat ksm,ksp,kdm,kdp; + Lib3dsQuat q,qp,qn,qa,qb; + int i; + + ASSERT(c); + if (!cp) + { + cp=c; + } + if (!cn) + { + cn=c; + } + if (!p || !n) + { + lib3ds_quat_copy(c->ds, c->q); + lib3ds_quat_copy(c->dd, c->q); + return; + } + + if (p) + { + if (p->angle>LIB3DS_TWOPI-LIB3DS_EPSILON) + { + lib3ds_quat_axis_angle(qp, p->axis, 0.0f); + lib3ds_quat_ln(qp); + } + else + { + lib3ds_quat_copy(q, p->q); + if (lib3ds_quat_dot(q,c->q)<0) lib3ds_quat_neg(q); + lib3ds_quat_ln_dif(qp, c->q, q); + } + } + if (n) + { + if (n->angle>LIB3DS_TWOPI-LIB3DS_EPSILON) + { + lib3ds_quat_axis_angle(qn, n->axis, 0.0f); + lib3ds_quat_ln(qn); + } + else + { + lib3ds_quat_copy(q, n->q); + if (lib3ds_quat_dot(q,c->q)<0) lib3ds_quat_neg(q); + lib3ds_quat_ln_dif(qn, c->q, q); + } + } + + if (n && p) + { + lib3ds_tcb(&p->tcb, &cp->tcb, &c->tcb, &cn->tcb, &n->tcb, &ksm, &ksp, &kdm, &kdp); + for(i=0; i<4; i++) + { + qa[i]=-0.5f*(kdm*qn[i]+kdp*qp[i]); + qb[i]=-0.5f*(ksm*qn[i]+ksp*qp[i]); + } + lib3ds_quat_exp(qa); + lib3ds_quat_exp(qb); + + lib3ds_quat_mul(c->ds, c->q, qa); + lib3ds_quat_mul(c->dd, c->q, qb); + } + else + { + if (p) + { + lib3ds_quat_exp(qp); + lib3ds_quat_mul(c->ds, c->q, qp); + lib3ds_quat_mul(c->dd, c->q, qp); + } + if (n) + { + lib3ds_quat_exp(qn); + lib3ds_quat_mul(c->ds, c->q, qn); + lib3ds_quat_mul(c->dd, c->q, qn); + } + } +} + + +/*! + * \ingroup tracks + */ +void +lib3ds_quat_track_setup(Lib3dsQuatTrack *track) +{ + Lib3dsQuatKey *pp,*pc,*pn,*pl; + Lib3dsQuat q; + + ASSERT(track); + for (pp=0,pc=track->keyL; pc; pp=pc,pc=pc->next) + { + lib3ds_quat_axis_angle(q, pc->axis, pc->angle); + if (pp) + { + lib3ds_quat_mul(pc->q, q, pp->q); + } + else + { + lib3ds_quat_copy(pc->q, q); + } + } + + pc=track->keyL; + if (!pc) + { + return; + } + if (!pc->next) + { + lib3ds_quat_copy(pc->ds, pc->q); + lib3ds_quat_copy(pc->dd, pc->q); + return; + } + + if (track->flags&LIB3DS_SMOOTH) + { + for (pl=track->keyL; pl->next->next; pl=pl->next); + lib3ds_quat_key_setup(pl, pl->next, pc, 0, pc->next); + } + else + { + lib3ds_quat_key_setup(0, 0, pc, 0, pc->next); + } + for (;;) + { + pp=pc; + pc=pc->next; + pn=pc->next; + if (!pn) + { + break; + } + lib3ds_quat_key_setup(pp, 0, pc, 0, pn); + } + + if (track->flags&LIB3DS_SMOOTH) + { + lib3ds_quat_key_setup(pp, 0, pc, track->keyL, track->keyL->next); + } + else + { + lib3ds_quat_key_setup(pp, 0, pc, 0, 0); + } +} + + +/*! + * \ingroup tracks + */ +void +lib3ds_quat_track_insert(Lib3dsQuatTrack *track, Lib3dsQuatKey *key) +{ + ASSERT(track); + ASSERT(key); + ASSERT(!key->next); + + if (!track->keyL) + { + track->keyL=key; + key->next=0; + } + else + { + Lib3dsQuatKey *k,*p; + + for (p=0,k=track->keyL; k!=0; p=k, k=k->next) + { + if (k->tcb.frame>key->tcb.frame) + { + break; + } + } + if (!p) + { + key->next=track->keyL; + track->keyL=key; + } + else + { + key->next=k; + p->next=key; + } + + if (k && (key->tcb.frame==k->tcb.frame)) + { + key->next=k->next; + lib3ds_quat_key_free(k); + } + } +} + + +/*! + * \ingroup tracks + */ +void +lib3ds_quat_track_remove(Lib3dsQuatTrack *track, Lib3dsIntd frame) +{ + Lib3dsQuatKey *k,*p; + + ASSERT(track); + if (!track->keyL) + { + return; + } + for (p=0,k=track->keyL; k!=0; p=k, k=k->next) + { + if (k->tcb.frame==frame) + { + if (!p) + { + track->keyL=track->keyL->next; + } + else + { + p->next=k->next; + } + lib3ds_quat_key_free(k); + break; + } + } +} + + +/*! + * \ingroup tracks + */ +void +lib3ds_quat_track_eval(Lib3dsQuatTrack *track, Lib3dsQuat q, Lib3dsFloat t) +{ + Lib3dsQuatKey *k; + Lib3dsFloat nt; + Lib3dsFloat u; + + if (!track->keyL) + { + lib3ds_quat_identity(q); + return; + } + if (!track->keyL->next) + { + lib3ds_quat_copy(q, track->keyL->q); + return; + } + + for (k=track->keyL; k->next!=0; k=k->next) + { + if ((t>=k->tcb.frame) && (tnext->tcb.frame)) + { + break; + } + } + if (!k->next) + { + if (track->flags&LIB3DS_REPEAT) + { + nt=(Lib3dsFloat)fmod(t, k->tcb.frame); + for (k=track->keyL; k->next!=0; k=k->next) + { + if ((nt>=k->tcb.frame) && (ntnext->tcb.frame)) + { + break; + } + } + ASSERT(k->next); + } + else + { + lib3ds_quat_copy(q, k->q); + return; + } + } + else + { + nt=t; + } + u=nt - k->tcb.frame; + u/=(k->next->tcb.frame - k->tcb.frame); + + lib3ds_quat_squad( + q, + k->q, + k->dd, + k->next->ds, + k->next->q, + u + ); +} + + +/*! + * \ingroup tracks + */ +Lib3dsBool +lib3ds_quat_track_read(Lib3dsQuatTrack *track, FILE *f) +{ + int keys; + int i,j; + // removed p definiation since MipsPro says that it ain't used.. + //Lib3dsQuatKey *p; + Lib3dsQuatKey *k; + + track->flags=lib3ds_word_read(f); + lib3ds_dword_read(f); + lib3ds_dword_read(f); + keys=lib3ds_intd_read(f); + + for (/*p=0,*/i=0; itcb, f)) + { + return(LIB3DS_FALSE); + } + k->angle=lib3ds_float_read(f); + for (j=0; j<3; ++j) + { + k->axis[j]=lib3ds_float_read(f); + } + lib3ds_quat_track_insert(track, k); + } + lib3ds_quat_track_setup(track); + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup tracks + */ +Lib3dsBool +lib3ds_quat_track_write(Lib3dsQuatTrack *track, FILE *f) +{ + Lib3dsQuatKey *k; + Lib3dsDword num=0; + for (k=track->keyL; k; k=k->next) + { + ++num; + } + lib3ds_word_write((Lib3dsWord)track->flags,f); + lib3ds_dword_write(0,f); + lib3ds_dword_write(0,f); + lib3ds_dword_write(num,f); + + for (k=track->keyL; k; k=k->next) + { + if (!lib3ds_tcb_write(&k->tcb,f)) + { + return(LIB3DS_FALSE); + } + lib3ds_float_write(k->angle,f); + lib3ds_vector_write(k->axis,f); + } + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup tracks + */ +Lib3dsMorphKey* +lib3ds_morph_key_new() +{ + Lib3dsMorphKey* k; + k=(Lib3dsMorphKey*)calloc(sizeof(Lib3dsMorphKey), 1); + return(k); +} + + +/*! + * \ingroup tracks + */ +void +lib3ds_morph_key_free(Lib3dsMorphKey *key) +{ + ASSERT(key); + free(key); +} + + +/*! + * \ingroup tracks + */ +void +lib3ds_morph_track_free_keys(Lib3dsMorphTrack *track) +{ + Lib3dsMorphKey *p,*q; + + ASSERT(track); + for (p=track->keyL; p; p=q) + { + q=p->next; + lib3ds_morph_key_free(p); + } +} + + +/*! + * \ingroup tracks + */ +void +lib3ds_morph_track_insert(Lib3dsMorphTrack *track, Lib3dsMorphKey *key) +{ + ASSERT(track); + ASSERT(key); + ASSERT(!key->next); + + if (!track->keyL) + { + track->keyL=key; + key->next=0; + } + else + { + Lib3dsMorphKey *k,*p; + + for (p=0,k=track->keyL; k!=0; p=k, k=k->next) + { + if (k->tcb.frame>key->tcb.frame) + { + break; + } + } + if (!p) + { + key->next=track->keyL; + track->keyL=key; + } + else + { + key->next=k; + p->next=key; + } + + if (k && (key->tcb.frame==k->tcb.frame)) + { + key->next=k->next; + lib3ds_morph_key_free(k); + } + } +} + + +/*! + * \ingroup tracks + */ +void +lib3ds_morph_track_remove(Lib3dsMorphTrack *track, Lib3dsIntd frame) +{ + Lib3dsMorphKey *k,*p; + + ASSERT(track); + if (!track->keyL) + { + return; + } + for (p=0,k=track->keyL; k!=0; p=k, k=k->next) + { + if (k->tcb.frame==frame) + { + if (!p) + { + track->keyL=track->keyL->next; + } + else + { + p->next=k->next; + } + lib3ds_morph_key_free(k); + break; + } + } +} + + +/*! + * \ingroup tracks + */ +void +lib3ds_morph_track_eval(Lib3dsMorphTrack *track, char *p, Lib3dsFloat t) +{ + Lib3dsMorphKey *k; + char* result; + + ASSERT(p); + if (!track->keyL) + { + strcpy(p,""); + return; + } + if (!track->keyL->next) + { + strcpy(p,track->keyL->name); + return; + } + + result=0; + k=track->keyL; + while ((ttcb.frame) && (t>=k->next->tcb.frame)) + { + result=k->name; + if (!k->next) + { + if (track->flags&LIB3DS_REPEAT) + { + t-=k->tcb.frame; + k=track->keyL; + } + else + { + break; + } + } + else + { + k=k->next; + } + } + if (result) + { + strcpy(p,result); + } + else + { + strcpy(p,""); + } +} + + +/*! + * \ingroup tracks + */ +Lib3dsBool +lib3ds_morph_track_read(Lib3dsMorphTrack *, FILE *) +{ + // parameters lib3ds_morph_track_read(Lib3dsMorphTrack *track, FILE *f) + /* FIXME: */ + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup tracks + */ +Lib3dsBool +lib3ds_morph_track_write(Lib3dsMorphTrack *, FILE *) +{ + // parameters : lib3ds_morph_track_write(Lib3dsMorphTrack *track, FILE *f) + /* FIXME: */ + ASSERT(0); + return(LIB3DS_FALSE); +} diff --git a/src/osgPlugins/lib3ds/tracks.h b/src/osgPlugins/lib3ds/tracks.h new file mode 100644 index 000000000..fc0555029 --- /dev/null +++ b/src/osgPlugins/lib3ds/tracks.h @@ -0,0 +1,209 @@ +/* -*- c -*- */ +#ifndef INCLUDED_LIB3DS_TRACKS_H +#define INCLUDED_LIB3DS_TRACKS_H +/* + * The 3D Studio File Format Library + * Copyright (C) 1996-2001 by J.E. Hoffmann + * All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or (at + * your option) any later version. + * + * 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 Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + * + * $Id$ + */ + +#ifndef INCLUDED_LIB3DS_TCB_H +#include +#endif + +#ifdef __cplusplus +extern "C" { +#endif + +/*! + * Track flags + * \ingroup tracks + */ +typedef enum { + LIB3DS_REPEAT =0x0001, + LIB3DS_SMOOTH =0x0002, + LIB3DS_LOCK_X =0x0008, + LIB3DS_LOCK_Y =0x0010, + LIB3DS_LOCK_Z =0x0020, + LIB3DS_UNLINK_X =0x0100, + LIB3DS_UNLINK_Y =0x0200, + LIB3DS_UNLINK_Z =0x0400 +} Lib3dsTrackFlags; + +/*! + * Boolean track key + * \ingroup tracks + */ +struct _Lib3dsBoolKey { + Lib3dsTcb tcb; + Lib3dsBoolKey *next; +}; + +/*! + * Boolean track + * \ingroup tracks + */ +struct _Lib3dsBoolTrack { + Lib3dsDword flags; + Lib3dsBoolKey *keyL; +}; + +/*! + * Floating-point track key + * \ingroup tracks + */ +struct _Lib3dsLin1Key { + Lib3dsTcb tcb; + Lib3dsLin1Key *next; + Lib3dsFloat value; + Lib3dsFloat dd; + Lib3dsFloat ds; +}; + +/*! + * Floating-point track + * \ingroup tracks + */ +struct _Lib3dsLin1Track { + Lib3dsDword flags; + Lib3dsLin1Key *keyL; +}; + +/*! + * Vector track key + * \ingroup tracks + */ +struct _Lib3dsLin3Key { + Lib3dsTcb tcb; + Lib3dsLin3Key *next; + Lib3dsVector value; + Lib3dsVector dd; + Lib3dsVector ds; +}; + +/*! + * Vector track + * \ingroup tracks + */ +struct _Lib3dsLin3Track { + Lib3dsDword flags; + Lib3dsLin3Key *keyL; +}; + +/*! + * Rotation track key + * \ingroup tracks + */ +struct _Lib3dsQuatKey { + Lib3dsTcb tcb; + Lib3dsQuatKey *next; + Lib3dsVector axis; + Lib3dsFloat angle; + Lib3dsQuat q; + Lib3dsQuat dd; + Lib3dsQuat ds; +}; + +/*! + * Rotation track + * \ingroup tracks + */ +struct _Lib3dsQuatTrack { + Lib3dsDword flags; + Lib3dsQuatKey *keyL; +}; + +/*! + * Morph track key + * \ingroup tracks + */ +struct _Lib3dsMorphKey { + Lib3dsTcb tcb; + Lib3dsMorphKey *next; + char name[64]; +}; + +/*! + * Morph track + * \ingroup tracks + */ +struct _Lib3dsMorphTrack { + Lib3dsDword flags; + Lib3dsMorphKey *keyL; +}; + +extern LIB3DSAPI Lib3dsBoolKey* lib3ds_bool_key_new(); +extern LIB3DSAPI void lib3ds_bool_key_free(Lib3dsBoolKey* key); +extern LIB3DSAPI void lib3ds_bool_track_free_keys(Lib3dsBoolTrack *track); +extern LIB3DSAPI void lib3ds_bool_track_insert(Lib3dsBoolTrack *track, Lib3dsBoolKey* key); +extern LIB3DSAPI void lib3ds_bool_track_remove(Lib3dsBoolTrack *track, Lib3dsIntd frame); +extern LIB3DSAPI void lib3ds_bool_track_eval(Lib3dsBoolTrack *track, Lib3dsBool *p, Lib3dsFloat t); +extern LIB3DSAPI Lib3dsBool lib3ds_bool_track_read(Lib3dsBoolTrack *track, FILE *f); +extern LIB3DSAPI Lib3dsBool lib3ds_bool_track_write(Lib3dsBoolTrack *track, FILE *f); + +extern LIB3DSAPI Lib3dsLin1Key* lib3ds_lin1_key_new(); +extern LIB3DSAPI void lib3ds_lin1_key_free(Lib3dsLin1Key* key); +extern LIB3DSAPI void lib3ds_lin1_track_free_keys(Lib3dsLin1Track *track); +extern LIB3DSAPI void lib3ds_lin1_key_setup(Lib3dsLin1Key *p, Lib3dsLin1Key *cp, Lib3dsLin1Key *c, + Lib3dsLin1Key *cn, Lib3dsLin1Key *n); +extern LIB3DSAPI void lib3ds_lin1_track_setup(Lib3dsLin1Track *track); +extern LIB3DSAPI void lib3ds_lin1_track_insert(Lib3dsLin1Track *track, Lib3dsLin1Key *key); +extern LIB3DSAPI void lib3ds_lin1_track_remove(Lib3dsLin1Track *track, Lib3dsIntd frame); +extern LIB3DSAPI void lib3ds_lin1_track_eval(Lib3dsLin1Track *track, Lib3dsFloat *p, Lib3dsFloat t); +extern LIB3DSAPI Lib3dsBool lib3ds_lin1_track_read(Lib3dsLin1Track *track, FILE *f); +extern LIB3DSAPI Lib3dsBool lib3ds_lin1_track_write(Lib3dsLin1Track *track, FILE *f); + +extern LIB3DSAPI Lib3dsLin3Key* lib3ds_lin3_key_new(); +extern LIB3DSAPI void lib3ds_lin3_key_free(Lib3dsLin3Key* key); +extern LIB3DSAPI void lib3ds_lin3_track_free_keys(Lib3dsLin3Track *track); +extern LIB3DSAPI void lib3ds_lin3_key_setup(Lib3dsLin3Key *p, Lib3dsLin3Key *cp, Lib3dsLin3Key *c, + Lib3dsLin3Key *cn, Lib3dsLin3Key *n); +extern LIB3DSAPI void lib3ds_lin3_track_setup(Lib3dsLin3Track *track); +extern LIB3DSAPI void lib3ds_lin3_track_insert(Lib3dsLin3Track *track, Lib3dsLin3Key *key); +extern LIB3DSAPI void lib3ds_lin3_track_remove(Lib3dsLin3Track *track, Lib3dsIntd frame); +extern LIB3DSAPI void lib3ds_lin3_track_eval(Lib3dsLin3Track *track, Lib3dsVector p, Lib3dsFloat t); +extern LIB3DSAPI Lib3dsBool lib3ds_lin3_track_read(Lib3dsLin3Track *track, FILE *f); +extern LIB3DSAPI Lib3dsBool lib3ds_lin3_track_write(Lib3dsLin3Track *track, FILE *f); + +extern LIB3DSAPI Lib3dsQuatKey* lib3ds_quat_key_new(); +extern LIB3DSAPI void lib3ds_quat_key_free(Lib3dsQuatKey* key); +extern LIB3DSAPI void lib3ds_quat_track_free_keys(Lib3dsQuatTrack *track); +extern LIB3DSAPI void lib3ds_quat_key_setup(Lib3dsQuatKey *p, Lib3dsQuatKey *cp, Lib3dsQuatKey *c, + Lib3dsQuatKey *cn, Lib3dsQuatKey *n); +extern LIB3DSAPI void lib3ds_quat_track_setup(Lib3dsQuatTrack *track); +extern LIB3DSAPI void lib3ds_quat_track_insert(Lib3dsQuatTrack *track, Lib3dsQuatKey *key); +extern LIB3DSAPI void lib3ds_quat_track_remove(Lib3dsQuatTrack *track, Lib3dsIntd frame); +extern LIB3DSAPI void lib3ds_quat_track_eval(Lib3dsQuatTrack *track, Lib3dsQuat p, Lib3dsFloat t); +extern LIB3DSAPI Lib3dsBool lib3ds_quat_track_read(Lib3dsQuatTrack *track, FILE *f); +extern LIB3DSAPI Lib3dsBool lib3ds_quat_track_write(Lib3dsQuatTrack *track, FILE *f); + +extern LIB3DSAPI Lib3dsMorphKey* lib3ds_morph_key_new(); +extern LIB3DSAPI void lib3ds_morph_key_free(Lib3dsMorphKey* key); +extern LIB3DSAPI void lib3ds_morph_track_free_keys(Lib3dsMorphTrack *track); +extern LIB3DSAPI void lib3ds_morph_track_insert(Lib3dsMorphTrack *track, Lib3dsMorphKey *key); +extern LIB3DSAPI void lib3ds_morph_track_remove(Lib3dsMorphTrack *track, Lib3dsIntd frame); +extern LIB3DSAPI void lib3ds_morph_track_eval(Lib3dsMorphTrack *track, char *p, Lib3dsFloat t); +extern LIB3DSAPI Lib3dsBool lib3ds_morph_track_read(Lib3dsMorphTrack *track, FILE *f); +extern LIB3DSAPI Lib3dsBool lib3ds_morph_track_write(Lib3dsMorphTrack *track, FILE *f); + +#ifdef __cplusplus +}; +#endif +#endif + diff --git a/src/osgPlugins/lib3ds/types.h b/src/osgPlugins/lib3ds/types.h new file mode 100644 index 000000000..60ef60fad --- /dev/null +++ b/src/osgPlugins/lib3ds/types.h @@ -0,0 +1,144 @@ +/* -*- c -*- */ +#ifndef INCLUDED_LIB3DS_TYPES_H +#define INCLUDED_LIB3DS_TYPES_H +/* + * The 3D Studio File Format Library + * Copyright (C) 1996-2001 by J.E. Hoffmann + * All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or (at + * your option) any later version. + * + * 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 Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + * + * $Id$ + */ +#ifdef __cplusplus +extern "C" { +#endif + +#if defined(_WIN32) && (!defined(__GNUC__)) +#ifdef LIB3DS_EXPORT +#define LIB3DSAPI __declspec(dllexport) +#else +#define LIB3DSAPI __declspec(dllimport) +#endif +#else +#define LIB3DSAPI +#endif + +#define LIB3DS_TRUE 1 +#define LIB3DS_FALSE 0 + +typedef int Lib3dsBool; +typedef unsigned char Lib3dsByte; +typedef unsigned short int Lib3dsWord; +typedef unsigned long Lib3dsDword; +typedef signed char Lib3dsIntb; +typedef signed short int Lib3dsIntw; +typedef signed long Lib3dsIntd; +typedef float Lib3dsFloat; +typedef double Lib3dsDouble; + +typedef float Lib3dsVector[3]; +typedef float Lib3dsTexel[2]; +typedef float Lib3dsQuat[4]; +typedef float Lib3dsMatrix[4][4]; +typedef float Lib3dsRgb[3]; +typedef float Lib3dsRgba[4]; + +#define LIB3DS_EPSILON (1e-8) +#define LIB3DS_PI 3.14159265358979323846 +#define LIB3DS_TWOPI (2.0*LIB3DS_PI) +#define LIB3DS_HALFPI (LIB3DS_PI/2.0) +#define LIB3DS_DEG(x) ((180.0/LIB3DS_PI)*(x)) +#define LIB3DS_RAD(x) ((LIB3DS_PI/180.0)*(x)) + +#ifndef INCLUDED_STDIO_H +#define INCLUDED_STDIO_H +#include +#endif + +#ifdef _DEBUG + #ifndef ASSERT + #include + #define ASSERT(__expr) assert(__expr) + #endif + #define LIB3DS_ERROR_LOG \ + {printf("\t***LIB3DS_ERROR_LOG*** %s : %d\n", __FILE__, __LINE__);} +#else + #ifndef ASSERT + #define ASSERT(__expr) + #endif + #define LIB3DS_ERROR_LOG +#endif + +typedef struct _Lib3dsFile Lib3dsFile; +typedef struct _Lib3dsBackground Lib3dsBackground; +typedef struct _Lib3dsAtmosphere Lib3dsAtmosphere; +typedef struct _Lib3dsShadow Lib3dsShadow; +typedef struct _Lib3dsViewport Lib3dsViewport; +typedef struct _Lib3dsMaterial Lib3dsMaterial; +typedef struct _Lib3dsFace Lib3dsFace; +typedef struct _Lib3dsBoxMap Lib3dsBoxMap; +typedef struct _Lib3dsMapData Lib3dsMapData; +typedef struct _Lib3dsMesh Lib3dsMesh; +typedef struct _Lib3dsCamera Lib3dsCamera; +typedef struct _Lib3dsLight Lib3dsLight; +typedef struct _Lib3dsBoolKey Lib3dsBoolKey; +typedef struct _Lib3dsBoolTrack Lib3dsBoolTrack; +typedef struct _Lib3dsLin1Key Lib3dsLin1Key; +typedef struct _Lib3dsLin1Track Lib3dsLin1Track; +typedef struct _Lib3dsLin3Key Lib3dsLin3Key; +typedef struct _Lib3dsLin3Track Lib3dsLin3Track; +typedef struct _Lib3dsQuatKey Lib3dsQuatKey; +typedef struct _Lib3dsQuatTrack Lib3dsQuatTrack; +typedef struct _Lib3dsMorphKey Lib3dsMorphKey; +typedef struct _Lib3dsMorphTrack Lib3dsMorphTrack; + +typedef enum _Lib3dsNodeTypes { + LIB3DS_UNKNOWN_NODE =0, + LIB3DS_AMBIENT_NODE =1, + LIB3DS_OBJECT_NODE =2, + LIB3DS_CAMERA_NODE =3, + LIB3DS_TARGET_NODE =4, + LIB3DS_LIGHT_NODE =5, + LIB3DS_SPOT_NODE =6 +} Lib3dsNodeTypes; + +typedef struct _Lib3dsNode Lib3dsNode; + +typedef union _Lib3dsUserData { + void *p; + Lib3dsIntd i; + Lib3dsDword d; + Lib3dsFloat f; + Lib3dsMaterial *material; + Lib3dsMesh *mesh; + Lib3dsCamera *camera; + Lib3dsLight *light; + Lib3dsNode *node; +} Lib3dsUserData; + +#ifdef __cplusplus +}; +#endif +#endif + + + + + + + + + diff --git a/src/osgPlugins/lib3ds/vector.cpp b/src/osgPlugins/lib3ds/vector.cpp new file mode 100644 index 000000000..168144667 --- /dev/null +++ b/src/osgPlugins/lib3ds/vector.cpp @@ -0,0 +1,251 @@ +/* + * The 3D Studio File Format Library + * Copyright (C) 1996-2001 by J.E. Hoffmann + * All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or (at + * your option) any later version. + * + * 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 Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + * + * $Id$ + */ +#define LIB3DS_EXPORT +#include +#include + +/*! + * \defgroup vector Vector Mathematics + * + * \author J.E. Hoffmann + */ +/*! + * \typedef Lib3dsVector + * \ingroup vector + */ + +/*! + * \ingroup vector + */ +void +lib3ds_vector_zero(Lib3dsVector c) +{ + int i; + for (i=0; i<3; ++i) + { + c[i]=0.0f; + } +} + + +/*! + * \ingroup vector + */ +void +lib3ds_vector_copy(Lib3dsVector dest, Lib3dsVector src) +{ + int i; + for (i=0; i<3; ++i) + { + dest[i]=src[i]; + } +} + + +/*! + * \ingroup vector + */ +void +lib3ds_vector_neg(Lib3dsVector c) +{ + int i; + for (i=0; i<3; ++i) + { + c[i]=-c[i]; + } +} + + +/*! + * \ingroup vector + */ +void +lib3ds_vector_add(Lib3dsVector c, Lib3dsVector a, Lib3dsVector b) +{ + int i; + for (i=0; i<3; ++i) + { + c[i]=a[i]+b[i]; + } +} + + +/*! + * \ingroup vector + */ +void +lib3ds_vector_sub(Lib3dsVector c, Lib3dsVector a, Lib3dsVector b) +{ + int i; + for (i=0; i<3; ++i) + { + c[i]=a[i]-b[i]; + } +} + + +/*! + * \ingroup vector + */ +void +lib3ds_vector_scalar(Lib3dsVector c, Lib3dsFloat k) +{ + int i; + for (i=0; i<3; ++i) + { + c[i]*=k; + } +} + + +/*! + * \ingroup vector + */ +void +lib3ds_vector_cross(Lib3dsVector c, Lib3dsVector a, Lib3dsVector b) +{ + c[0]=a[1]*b[2] - a[2]*b[1]; + c[1]=a[2]*b[0] - a[0]*b[2]; + c[2]=a[0]*b[1] - a[1]*b[0]; +} + + +/*! + * \ingroup vector + */ +Lib3dsFloat +lib3ds_vector_dot(Lib3dsVector a, Lib3dsVector b) +{ + return(a[0]*b[0] + a[1]*b[1] + a[2]*b[2]); +} + + +/*! + * \ingroup vector + */ +Lib3dsFloat +lib3ds_vector_squared(Lib3dsVector c) +{ + return(c[0]*c[0] + c[1]*c[1] + c[2]*c[2]); +} + + +/*! + * \ingroup vector + */ +Lib3dsFloat +lib3ds_vector_length(Lib3dsVector c) +{ + return((Lib3dsFloat)sqrt(c[0]*c[0] + c[1]*c[1] + c[2]*c[2])); +} + + +/*! + * \ingroup vector + */ +void +lib3ds_vector_normalize(Lib3dsVector c) +{ + Lib3dsFloat l,m; + + l=(Lib3dsFloat)sqrt(c[0]*c[0] + c[1]*c[1] + c[2]*c[2]); + if (fabs(l)=c[1]) && (c[0]>=c[2])) + { + c[0]=1.0f; + } + else + if (c[1]>=c[2]) + { + c[1]=1.0f; + } + else + { + c[2]=1.0f; + } + } + else + { + m=1.0f/l; + c[0]*=m; + c[1]*=m; + c[2]*=m; + } +} + + +/*! + * \ingroup vector + */ +void +lib3ds_vector_normal(Lib3dsVector n, Lib3dsVector a, Lib3dsVector b, Lib3dsVector c) +{ + Lib3dsVector p,q; + + lib3ds_vector_sub(p,c,b); + lib3ds_vector_sub(q,a,b); + lib3ds_vector_cross(n,p,q); + lib3ds_vector_normalize(n); +} + + +/*! + * \ingroup vector + */ +void +lib3ds_vector_transform(Lib3dsVector c, Lib3dsMatrix m, Lib3dsVector a) +{ + c[0]= m[0][0]*a[0] + m[1][0]*a[1] + m[2][0]*a[2] + m[3][0]; + c[1]= m[0][1]*a[0] + m[1][1]*a[1] + m[2][1]*a[2] + m[3][1]; + c[2]= m[0][2]*a[0] + m[1][2]*a[1] + m[2][2]*a[2] + m[3][2]; +} + + +/*! + * \ingroup vector + */ +void +lib3ds_vector_cubic(Lib3dsVector c, Lib3dsVector a, Lib3dsVector p, Lib3dsVector q, +Lib3dsVector b, Lib3dsFloat t) +{ + Lib3dsDouble x,y,z,w; + + x=2*t*t*t - 3*t*t + 1; + y=-2*t*t*t + 3*t*t; + z=t*t*t - 2*t*t + t; + w=t*t*t - t*t; + c[0]=(Lib3dsFloat)(x*a[0] + y*b[0] + z*p[0] + w*q[0]); + c[1]=(Lib3dsFloat)(x*a[1] + y*b[1] + z*p[1] + w*q[1]); + c[2]=(Lib3dsFloat)(x*a[2] + y*b[2] + z*p[2] + w*q[2]); +} + + +/*! + * \ingroup vector + */ +void +lib3ds_vector_dump(Lib3dsVector c) +{ + fprintf(stderr, "%f %f %f\n", c[0], c[1], c[2]); +} diff --git a/src/osgPlugins/lib3ds/vector.h b/src/osgPlugins/lib3ds/vector.h new file mode 100644 index 000000000..606d84223 --- /dev/null +++ b/src/osgPlugins/lib3ds/vector.h @@ -0,0 +1,56 @@ +/* -*- c -*- */ +#ifndef INCLUDED_LIB3DS_VECTOR_H +#define INCLUDED_LIB3DS_VECTOR_H +/* + * The 3D Studio File Format Library + * Copyright (C) 1996-2001 by J.E. Hoffmann + * All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or (at + * your option) any later version. + * + * 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 Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + * + * $Id$ + */ + +#ifndef INCLUDED_LIB3DS_TYPES_H +#include +#endif + +#ifdef __cplusplus +extern "C" { +#endif + +extern LIB3DSAPI void lib3ds_vector_zero(Lib3dsVector c); +extern LIB3DSAPI void lib3ds_vector_copy(Lib3dsVector dest, Lib3dsVector src); +extern LIB3DSAPI void lib3ds_vector_neg(Lib3dsVector c); +extern LIB3DSAPI void lib3ds_vector_add(Lib3dsVector c, Lib3dsVector a, Lib3dsVector b); +extern LIB3DSAPI void lib3ds_vector_sub(Lib3dsVector c, Lib3dsVector a, Lib3dsVector b); +extern LIB3DSAPI void lib3ds_vector_scalar(Lib3dsVector c, Lib3dsFloat k); +extern LIB3DSAPI void lib3ds_vector_cross(Lib3dsVector c, Lib3dsVector a, Lib3dsVector b); +extern LIB3DSAPI Lib3dsFloat lib3ds_vector_dot(Lib3dsVector a, Lib3dsVector b); +extern LIB3DSAPI Lib3dsFloat lib3ds_vector_squared(Lib3dsVector c); +extern LIB3DSAPI Lib3dsFloat lib3ds_vector_length(Lib3dsVector c); +extern LIB3DSAPI void lib3ds_vector_normalize(Lib3dsVector c); +extern LIB3DSAPI void lib3ds_vector_normal(Lib3dsVector n, Lib3dsVector a, + Lib3dsVector b, Lib3dsVector c); +extern LIB3DSAPI void lib3ds_vector_transform(Lib3dsVector c, Lib3dsMatrix m, Lib3dsVector a); +extern LIB3DSAPI void lib3ds_vector_cubic(Lib3dsVector c, Lib3dsVector a, Lib3dsVector p, + Lib3dsVector q, Lib3dsVector b, Lib3dsFloat t); +extern LIB3DSAPI void lib3ds_vector_dump(Lib3dsVector c); + +#ifdef __cplusplus +}; +#endif +#endif + diff --git a/src/osgPlugins/lib3ds/viewport.cpp b/src/osgPlugins/lib3ds/viewport.cpp new file mode 100644 index 000000000..046d48633 --- /dev/null +++ b/src/osgPlugins/lib3ds/viewport.cpp @@ -0,0 +1,383 @@ +/* + * The 3D Studio File Format Library + * Copyright (C) 1996-2001 by J.E. Hoffmann + * All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or (at + * your option) any later version. + * + * 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 Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + * + * $Id$ + */ +#define LIB3DS_EXPORT +#include +#include +#include +#include +#include + +/*! + * \defgroup viewport Viewport and default view settings + * + * \author J.E. Hoffmann + */ + +/*! + * \ingroup viewport + */ +Lib3dsBool +lib3ds_viewport_read(Lib3dsViewport *viewport, FILE *f) +{ + Lib3dsChunk c; + Lib3dsWord chunk; + + if (!lib3ds_chunk_read(&c, f)) + { + return(LIB3DS_FALSE); + } + + switch (c.chunk) + { + case LIB3DS_VIEWPORT_LAYOUT: + { + int cur=0; + viewport->layout.style=lib3ds_word_read(f); + viewport->layout.active=lib3ds_intw_read(f); + lib3ds_intw_read(f); + viewport->layout.swap=lib3ds_intw_read(f); + lib3ds_intw_read(f); + viewport->layout.swap_prior=lib3ds_intw_read(f); + viewport->layout.swap_view=lib3ds_intw_read(f); + lib3ds_chunk_read_tell(&c, f); + while ((chunk=lib3ds_chunk_read_next(&c, f))!=0) + { + switch (chunk) + { + case LIB3DS_VIEWPORT_SIZE: + { + viewport->layout.position[0]=lib3ds_word_read(f); + viewport->layout.position[1]=lib3ds_word_read(f); + viewport->layout.size[0]=lib3ds_word_read(f); + viewport->layout.size[1]=lib3ds_word_read(f); + } + break; + case LIB3DS_VIEWPORT_DATA_3: + { + lib3ds_viewport_set_views(viewport,cur+1); + lib3ds_intw_read(f); + viewport->layout.viewL[cur].axis_lock=lib3ds_word_read(f); + viewport->layout.viewL[cur].position[0]=lib3ds_intw_read(f); + viewport->layout.viewL[cur].position[1]=lib3ds_intw_read(f); + viewport->layout.viewL[cur].size[0]=lib3ds_intw_read(f); + viewport->layout.viewL[cur].size[1]=lib3ds_intw_read(f); + viewport->layout.viewL[cur].type=lib3ds_word_read(f); + viewport->layout.viewL[cur].zoom=lib3ds_float_read(f); + lib3ds_vector_read(viewport->layout.viewL[cur].center,f); + viewport->layout.viewL[cur].horiz_angle=lib3ds_float_read(f); + viewport->layout.viewL[cur].vert_angle=lib3ds_float_read(f); + fread(viewport->layout.viewL[cur].camera,11,1,f); + ++cur; + } + break; + case LIB3DS_VIEWPORT_DATA: + /* 3DS R2 & R3 chunk + unsupported */ + break; + default: + lib3ds_chunk_unknown(chunk); + } + } + lib3ds_chunk_read_end(&c, f); + } + break; + case LIB3DS_DEFAULT_VIEW: + { + memset(&viewport->default_view,0,sizeof(Lib3dsDefaultView)); + while ((chunk=lib3ds_chunk_read_next(&c, f))!=0) + { + switch (chunk) + { + case LIB3DS_VIEW_TOP: + { + viewport->default_view.type=LIB3DS_VIEW_TYPE_TOP; + lib3ds_vector_read(viewport->default_view.position,f); + viewport->default_view.width=lib3ds_float_read(f); + } + break; + case LIB3DS_VIEW_BOTTOM: + { + viewport->default_view.type=LIB3DS_VIEW_TYPE_BOTTOM; + lib3ds_vector_read(viewport->default_view.position,f); + viewport->default_view.width=lib3ds_float_read(f); + } + break; + case LIB3DS_VIEW_LEFT: + { + viewport->default_view.type=LIB3DS_VIEW_TYPE_LEFT; + lib3ds_vector_read(viewport->default_view.position,f); + viewport->default_view.width=lib3ds_float_read(f); + } + break; + case LIB3DS_VIEW_RIGHT: + { + viewport->default_view.type=LIB3DS_VIEW_TYPE_RIGHT; + lib3ds_vector_read(viewport->default_view.position,f); + viewport->default_view.width=lib3ds_float_read(f); + } + break; + case LIB3DS_VIEW_FRONT: + { + viewport->default_view.type=LIB3DS_VIEW_TYPE_FRONT; + lib3ds_vector_read(viewport->default_view.position,f); + viewport->default_view.width=lib3ds_float_read(f); + } + break; + case LIB3DS_VIEW_BACK: + { + viewport->default_view.type=LIB3DS_VIEW_TYPE_BACK; + lib3ds_vector_read(viewport->default_view.position,f); + viewport->default_view.width=lib3ds_float_read(f); + } + break; + case LIB3DS_VIEW_USER: + { + viewport->default_view.type=LIB3DS_VIEW_TYPE_USER; + lib3ds_vector_read(viewport->default_view.position,f); + viewport->default_view.width=lib3ds_float_read(f); + viewport->default_view.horiz_angle=lib3ds_float_read(f); + viewport->default_view.vert_angle=lib3ds_float_read(f); + viewport->default_view.roll_angle=lib3ds_float_read(f); + } + break; + case LIB3DS_VIEW_CAMERA: + { + viewport->default_view.type=LIB3DS_VIEW_TYPE_CAMERA; + fread(viewport->default_view.camera,11,1,f); + } + break; + default: + lib3ds_chunk_unknown(chunk); + } + } + lib3ds_chunk_read_end(&c, f); + } + break; + } + return(LIB3DS_TRUE); +} + + +/*! + * \ingroup viewport + */ +void +lib3ds_viewport_set_views(Lib3dsViewport *viewport, Lib3dsDword views) +{ + ASSERT(viewport); + if (viewport->layout.views) + { + if (views) + { + viewport->layout.views=views; + viewport->layout.viewL=(Lib3dsView*)realloc(viewport->layout.viewL, sizeof(Lib3dsView)*views); + } + else + { + free(viewport->layout.viewL); + viewport->layout.views=0; + viewport->layout.viewL=0; + } + } + else + { + viewport->layout.views=views; + viewport->layout.viewL=(Lib3dsView*)calloc(sizeof(Lib3dsView),views); + } +} + + +/*! + * \ingroup viewport + */ +Lib3dsBool +lib3ds_viewport_write(Lib3dsViewport *viewport, FILE *f) +{ + if (viewport->layout.views) + { + Lib3dsChunk c; + unsigned i; + + c.chunk=LIB3DS_VIEWPORT_LAYOUT; + if (!lib3ds_chunk_write_start(&c,f)) + { + return(LIB3DS_FALSE); + } + + lib3ds_word_write(viewport->layout.style,f); + lib3ds_intw_write(viewport->layout.active,f); + lib3ds_intw_write(0,f); + lib3ds_intw_write(viewport->layout.swap,f); + lib3ds_intw_write(0,f); + lib3ds_intw_write(viewport->layout.swap_prior,f); + lib3ds_intw_write(viewport->layout.swap_view,f); + + { + Lib3dsChunk c; + c.chunk=LIB3DS_VIEWPORT_SIZE; + c.size=14; + lib3ds_chunk_write(&c,f); + lib3ds_intw_write(viewport->layout.position[0],f); + lib3ds_intw_write(viewport->layout.position[1],f); + lib3ds_intw_write(viewport->layout.size[0],f); + lib3ds_intw_write(viewport->layout.size[1],f); + } + + for (i=0; ilayout.views; ++i) + { + Lib3dsChunk c; + c.chunk=LIB3DS_VIEWPORT_DATA_3; + c.size=55; + lib3ds_chunk_write(&c,f); + + lib3ds_intw_write(0,f); + lib3ds_word_write(viewport->layout.viewL[i].axis_lock,f); + lib3ds_intw_write(viewport->layout.viewL[i].position[0],f); + lib3ds_intw_write(viewport->layout.viewL[i].position[1],f); + lib3ds_intw_write(viewport->layout.viewL[i].size[0],f); + lib3ds_intw_write(viewport->layout.viewL[i].size[1],f); + lib3ds_word_write(viewport->layout.viewL[i].type,f); + lib3ds_float_write(viewport->layout.viewL[i].zoom,f); + lib3ds_vector_write(viewport->layout.viewL[i].center,f); + lib3ds_float_write(viewport->layout.viewL[i].horiz_angle,f); + lib3ds_float_write(viewport->layout.viewL[i].vert_angle,f); + fwrite(viewport->layout.viewL[i].camera,11,1,f); + } + + if (!lib3ds_chunk_write_end(&c,f)) + { + return(LIB3DS_FALSE); + } + } + + if (viewport->default_view.type) + { + Lib3dsChunk c; + + c.chunk=LIB3DS_DEFAULT_VIEW; + if (!lib3ds_chunk_write_start(&c,f)) + { + return(LIB3DS_FALSE); + } + + switch (viewport->default_view.type) + { + case LIB3DS_VIEW_TYPE_TOP: + { + Lib3dsChunk c; + c.chunk=LIB3DS_VIEW_TOP; + c.size=22; + lib3ds_chunk_write(&c,f); + lib3ds_vector_write(viewport->default_view.position,f); + lib3ds_float_write(viewport->default_view.width,f); + } + break; + case LIB3DS_VIEW_TYPE_BOTTOM: + { + Lib3dsChunk c; + c.chunk=LIB3DS_VIEW_BOTTOM; + c.size=22; + lib3ds_chunk_write(&c,f); + lib3ds_vector_write(viewport->default_view.position,f); + lib3ds_float_write(viewport->default_view.width,f); + } + break; + case LIB3DS_VIEW_TYPE_LEFT: + { + Lib3dsChunk c; + c.chunk=LIB3DS_VIEW_LEFT; + c.size=22; + lib3ds_chunk_write(&c,f); + lib3ds_vector_write(viewport->default_view.position,f); + lib3ds_float_write(viewport->default_view.width,f); + } + break; + case LIB3DS_VIEW_TYPE_RIGHT: + { + Lib3dsChunk c; + c.chunk=LIB3DS_VIEW_RIGHT; + c.size=22; + lib3ds_chunk_write(&c,f); + lib3ds_vector_write(viewport->default_view.position,f); + lib3ds_float_write(viewport->default_view.width,f); + } + break; + case LIB3DS_VIEW_TYPE_FRONT: + { + Lib3dsChunk c; + c.chunk=LIB3DS_VIEW_FRONT; + c.size=22; + lib3ds_chunk_write(&c,f); + lib3ds_vector_write(viewport->default_view.position,f); + lib3ds_float_write(viewport->default_view.width,f); + } + break; + case LIB3DS_VIEW_TYPE_BACK: + { + Lib3dsChunk c; + c.chunk=LIB3DS_VIEW_BACK; + c.size=22; + lib3ds_chunk_write(&c,f); + lib3ds_vector_write(viewport->default_view.position,f); + lib3ds_float_write(viewport->default_view.width,f); + } + break; + case LIB3DS_VIEW_TYPE_USER: + { + Lib3dsChunk c; + c.chunk=LIB3DS_VIEW_USER; + c.size=34; + lib3ds_chunk_write(&c,f); + lib3ds_vector_write(viewport->default_view.position,f); + lib3ds_float_write(viewport->default_view.width,f); + lib3ds_float_write(viewport->default_view.horiz_angle,f); + lib3ds_float_write(viewport->default_view.vert_angle,f); + lib3ds_float_write(viewport->default_view.roll_angle,f); + } + break; + case LIB3DS_VIEW_TYPE_CAMERA: + { + Lib3dsChunk c; + c.chunk=LIB3DS_VIEW_CAMERA; + c.size=17; + lib3ds_chunk_write(&c,f); + fwrite(viewport->default_view.camera,1,11,f); + } + break; + } + + if (!lib3ds_chunk_write_end(&c,f)) + { + return(LIB3DS_FALSE); + } + } + return(LIB3DS_TRUE); +} + + +/*! + +\typedef Lib3dsViewport + \ingroup viewport + \sa _Lib3dsViewport + +*/ diff --git a/src/osgPlugins/lib3ds/viewport.h b/src/osgPlugins/lib3ds/viewport.h new file mode 100644 index 000000000..b9c0f3ae5 --- /dev/null +++ b/src/osgPlugins/lib3ds/viewport.h @@ -0,0 +1,136 @@ +/* -*- c -*- */ +#ifndef INCLUDED_LIB3DS_VIEWPORT_H +#define INCLUDED_LIB3DS_VIEWPORT_H +/* + * The 3D Studio File Format Library + * Copyright (C) 1996-2001 by J.E. Hoffmann + * All rights reserved. + * + * This program is free software; you can redistribute it and/or modify it + * under the terms of the GNU Lesser General Public License as published by + * the Free Software Foundation; either version 2.1 of the License, or (at + * your option) any later version. + * + * 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 Lesser General Public + * License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program; if not, write to the Free Software Foundation, + * Inc., 675 Mass Ave, Cambridge, MA 02139, USA. + * + * $Id$ + */ + +#ifndef INCLUDED_LIB3DS_TYPES_H +#include +#endif + +#ifdef __cplusplus +extern "C" { +#endif + +/*! + * Layout view types + * \ingroup viewport + */ +typedef enum _Lib3dsViewType { + LIB3DS_VIEW_TYPE_NOT_USED =0, + LIB3DS_VIEW_TYPE_TOP =1, + LIB3DS_VIEW_TYPE_BOTTOM =2, + LIB3DS_VIEW_TYPE_LEFT =3, + LIB3DS_VIEW_TYPE_RIGHT =4, + LIB3DS_VIEW_TYPE_FRONT =5, + LIB3DS_VIEW_TYPE_BACK =6, + LIB3DS_VIEW_TYPE_USER =7, + LIB3DS_VIEW_TYPE_SPOTLIGHT =18, + LIB3DS_VIEW_TYPE_CAMERA =65535 +} Lib3dsViewType; + +/*! + * Layout view settings + * \ingroup viewport + */ +typedef struct _Lib3dsView { + Lib3dsWord type; + Lib3dsWord axis_lock; + Lib3dsIntw position[2]; + Lib3dsIntw size[2]; + Lib3dsFloat zoom; + Lib3dsVector center; + Lib3dsFloat horiz_angle; + Lib3dsFloat vert_angle; + char camera[11]; +} Lib3dsView; + +/*! + * Layout styles + * \ingroup viewport + */ +typedef enum _Lib3dsLayoutStyle { + LIB3DS_LAYOUT_SINGLE =0, + LIB3DS_LAYOUT_TWO_PANE_VERT_SPLIT =1, + LIB3DS_LAYOUT_TWO_PANE_HORIZ_SPLIT =2, + LIB3DS_LAYOUT_FOUR_PANE =3, + LIB3DS_LAYOUT_THREE_PANE_LEFT_SPLIT =4, + LIB3DS_LAYOUT_THREE_PANE_BOTTOM_SPLIT =5, + LIB3DS_LAYOUT_THREE_PANE_RIGHT_SPLIT =6, + LIB3DS_LAYOUT_THREE_PANE_TOP_SPLIT =7, + LIB3DS_LAYOUT_THREE_PANE_VERT_SPLIT =8, + LIB3DS_LAYOUT_THREE_PANE_HORIZ_SPLIT =9, + LIB3DS_LAYOUT_FOUR_PANE_LEFT_SPLIT =10, + LIB3DS_LAYOUT_FOUR_PANE_RIGHT_SPLIT =11 +} Lib3dsLayoutStyle; + +/*! + * Viewport layout settings + * \ingroup viewport + */ +typedef struct _Lib3dsLayout { + Lib3dsWord style; + Lib3dsIntw active; + Lib3dsIntw swap; + Lib3dsIntw swap_prior; + Lib3dsIntw swap_view; + Lib3dsWord position[2]; + Lib3dsWord size[2]; + Lib3dsDword views; + Lib3dsView *viewL; +} Lib3dsLayout; + +/*! + * Default view settings + * \ingroup viewport + */ +typedef struct _Lib3dsDefaultView { + Lib3dsWord type; + Lib3dsVector position; + Lib3dsFloat width; + Lib3dsFloat horiz_angle; + Lib3dsFloat vert_angle; + Lib3dsFloat roll_angle; + char camera[64]; +} Lib3dsDefaultView; + +/*! + * Viewport and default view settings + * \ingroup viewport + */ +struct _Lib3dsViewport { + Lib3dsLayout layout; + Lib3dsDefaultView default_view; +}; + +extern LIB3DSAPI Lib3dsBool lib3ds_viewport_read(Lib3dsViewport *viewport, FILE *f); +extern LIB3DSAPI void lib3ds_viewport_set_views(Lib3dsViewport *viewport, Lib3dsDword views); +extern LIB3DSAPI Lib3dsBool lib3ds_viewport_write(Lib3dsViewport *viewport, FILE *f); + +#ifdef __cplusplus +}; +#endif +#endif + + + + diff --git a/src/osgPlugins/lwo/COPYING b/src/osgPlugins/lwo/COPYING new file mode 100644 index 000000000..223ede7de --- /dev/null +++ b/src/osgPlugins/lwo/COPYING @@ -0,0 +1,504 @@ + GNU LESSER GENERAL PUBLIC LICENSE + Version 2.1, February 1999 + + Copyright (C) 1991, 1999 Free Software Foundation, Inc. + 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + Everyone is permitted to copy and distribute verbatim copies + of this license document, but changing it is not allowed. + +[This is the first released version of the Lesser GPL. It also counts + as the successor of the GNU Library Public License, version 2, hence + the version number 2.1.] + + Preamble + + The licenses for most software are designed to take away your +freedom to share and change it. By contrast, the GNU General Public +Licenses are intended to guarantee your freedom to share and change +free software--to make sure the software is free for all its users. + + This license, the Lesser General Public License, applies to some +specially designated software packages--typically libraries--of the +Free Software Foundation and other authors who decide to use it. You +can use it too, but we suggest you first think carefully about whether +this license or the ordinary General Public License is the better +strategy to use in any particular case, based on the explanations below. + + When we speak of free software, we are referring to freedom of use, +not price. Our General Public Licenses are designed to make sure that +you have the freedom to distribute copies of free software (and charge +for this service if you wish); that you receive source code or can get +it if you want it; that you can change the software and use pieces of +it in new free programs; and that you are informed that you can do +these things. + + To protect your rights, we need to make restrictions that forbid +distributors to deny you these rights or to ask you to surrender these +rights. These restrictions translate to certain responsibilities for +you if you distribute copies of the library or if you modify it. + + For example, if you distribute copies of the library, whether gratis +or for a fee, you must give the recipients all the rights that we gave +you. You must make sure that they, too, receive or can get the source +code. If you link other code with the library, you must provide +complete object files to the recipients, so that they can relink them +with the library after making changes to the library and recompiling +it. And you must show them these terms so they know their rights. + + We protect your rights with a two-step method: (1) we copyright the +library, and (2) we offer you this license, which gives you legal +permission to copy, distribute and/or modify the library. + + To protect each distributor, we want to make it very clear that +there is no warranty for the free library. Also, if the library is +modified by someone else and passed on, the recipients should know +that what they have is not the original version, so that the original +author's reputation will not be affected by problems that might be +introduced by others. + + Finally, software patents pose a constant threat to the existence of +any free program. We wish to make sure that a company cannot +effectively restrict the users of a free program by obtaining a +restrictive license from a patent holder. Therefore, we insist that +any patent license obtained for a version of the library must be +consistent with the full freedom of use specified in this license. + + Most GNU software, including some libraries, is covered by the +ordinary GNU General Public License. This license, the GNU Lesser +General Public License, applies to certain designated libraries, and +is quite different from the ordinary General Public License. We use +this license for certain libraries in order to permit linking those +libraries into non-free programs. + + When a program is linked with a library, whether statically or using +a shared library, the combination of the two is legally speaking a +combined work, a derivative of the original library. The ordinary +General Public License therefore permits such linking only if the +entire combination fits its criteria of freedom. The Lesser General +Public License permits more lax criteria for linking other code with +the library. + + We call this license the "Lesser" General Public License because it +does Less to protect the user's freedom than the ordinary General +Public License. It also provides other free software developers Less +of an advantage over competing non-free programs. These disadvantages +are the reason we use the ordinary General Public License for many +libraries. However, the Lesser license provides advantages in certain +special circumstances. + + For example, on rare occasions, there may be a special need to +encourage the widest possible use of a certain library, so that it becomes +a de-facto standard. To achieve this, non-free programs must be +allowed to use the library. A more frequent case is that a free +library does the same job as widely used non-free libraries. In this +case, there is little to gain by limiting the free library to free +software only, so we use the Lesser General Public License. + + In other cases, permission to use a particular library in non-free +programs enables a greater number of people to use a large body of +free software. For example, permission to use the GNU C Library in +non-free programs enables many more people to use the whole GNU +operating system, as well as its variant, the GNU/Linux operating +system. + + Although the Lesser General Public License is Less protective of the +users' freedom, it does ensure that the user of a program that is +linked with the Library has the freedom and the wherewithal to run +that program using a modified version of the Library. + + The precise terms and conditions for copying, distribution and +modification follow. Pay close attention to the difference between a +"work based on the library" and a "work that uses the library". The +former contains code derived from the library, whereas the latter must +be combined with the library in order to run. + + GNU LESSER GENERAL PUBLIC LICENSE + TERMS AND CONDITIONS FOR COPYING, DISTRIBUTION AND MODIFICATION + + 0. This License Agreement applies to any software library or other +program which contains a notice placed by the copyright holder or +other authorized party saying it may be distributed under the terms of +this Lesser General Public License (also called "this License"). +Each licensee is addressed as "you". + + A "library" means a collection of software functions and/or data +prepared so as to be conveniently linked with application programs +(which use some of those functions and data) to form executables. + + The "Library", below, refers to any such software library or work +which has been distributed under these terms. A "work based on the +Library" means either the Library or any derivative work under +copyright law: that is to say, a work containing the Library or a +portion of it, either verbatim or with modifications and/or translated +straightforwardly into another language. (Hereinafter, translation is +included without limitation in the term "modification".) + + "Source code" for a work means the preferred form of the work for +making modifications to it. For a library, complete source code means +all the source code for all modules it contains, plus any associated +interface definition files, plus the scripts used to control compilation +and installation of the library. + + Activities other than copying, distribution and modification are not +covered by this License; they are outside its scope. The act of +running a program using the Library is not restricted, and output from +such a program is covered only if its contents constitute a work based +on the Library (independent of the use of the Library in a tool for +writing it). Whether that is true depends on what the Library does +and what the program that uses the Library does. + + 1. You may copy and distribute verbatim copies of the Library's +complete source code as you receive it, in any medium, provided that +you conspicuously and appropriately publish on each copy an +appropriate copyright notice and disclaimer of warranty; keep intact +all the notices that refer to this License and to the absence of any +warranty; and distribute a copy of this License along with the +Library. + + You may charge a fee for the physical act of transferring a copy, +and you may at your option offer warranty protection in exchange for a +fee. + + 2. You may modify your copy or copies of the Library or any portion +of it, thus forming a work based on the Library, and copy and +distribute such modifications or work under the terms of Section 1 +above, provided that you also meet all of these conditions: + + a) The modified work must itself be a software library. + + b) You must cause the files modified to carry prominent notices + stating that you changed the files and the date of any change. + + c) You must cause the whole of the work to be licensed at no + charge to all third parties under the terms of this License. + + d) If a facility in the modified Library refers to a function or a + table of data to be supplied by an application program that uses + the facility, other than as an argument passed when the facility + is invoked, then you must make a good faith effort to ensure that, + in the event an application does not supply such function or + table, the facility still operates, and performs whatever part of + its purpose remains meaningful. + + (For example, a function in a library to compute square roots has + a purpose that is entirely well-defined independent of the + application. Therefore, Subsection 2d requires that any + application-supplied function or table used by this function must + be optional: if the application does not supply it, the square + root function must still compute square roots.) + +These requirements apply to the modified work as a whole. If +identifiable sections of that work are not derived from the Library, +and can be reasonably considered independent and separate works in +themselves, then this License, and its terms, do not apply to those +sections when you distribute them as separate works. But when you +distribute the same sections as part of a whole which is a work based +on the Library, the distribution of the whole must be on the terms of +this License, whose permissions for other licensees extend to the +entire whole, and thus to each and every part regardless of who wrote +it. + +Thus, it is not the intent of this section to claim rights or contest +your rights to work written entirely by you; rather, the intent is to +exercise the right to control the distribution of derivative or +collective works based on the Library. + +In addition, mere aggregation of another work not based on the Library +with the Library (or with a work based on the Library) on a volume of +a storage or distribution medium does not bring the other work under +the scope of this License. + + 3. You may opt to apply the terms of the ordinary GNU General Public +License instead of this License to a given copy of the Library. To do +this, you must alter all the notices that refer to this License, so +that they refer to the ordinary GNU General Public License, version 2, +instead of to this License. (If a newer version than version 2 of the +ordinary GNU General Public License has appeared, then you can specify +that version instead if you wish.) Do not make any other change in +these notices. + + Once this change is made in a given copy, it is irreversible for +that copy, so the ordinary GNU General Public License applies to all +subsequent copies and derivative works made from that copy. + + This option is useful when you wish to copy part of the code of +the Library into a program that is not a library. + + 4. You may copy and distribute the Library (or a portion or +derivative of it, under Section 2) in object code or executable form +under the terms of Sections 1 and 2 above provided that you accompany +it with the complete corresponding machine-readable source code, which +must be distributed under the terms of Sections 1 and 2 above on a +medium customarily used for software interchange. + + If distribution of object code is made by offering access to copy +from a designated place, then offering equivalent access to copy the +source code from the same place satisfies the requirement to +distribute the source code, even though third parties are not +compelled to copy the source along with the object code. + + 5. A program that contains no derivative of any portion of the +Library, but is designed to work with the Library by being compiled or +linked with it, is called a "work that uses the Library". Such a +work, in isolation, is not a derivative work of the Library, and +therefore falls outside the scope of this License. + + However, linking a "work that uses the Library" with the Library +creates an executable that is a derivative of the Library (because it +contains portions of the Library), rather than a "work that uses the +library". The executable is therefore covered by this License. +Section 6 states terms for distribution of such executables. + + When a "work that uses the Library" uses material from a header file +that is part of the Library, the object code for the work may be a +derivative work of the Library even though the source code is not. +Whether this is true is especially significant if the work can be +linked without the Library, or if the work is itself a library. The +threshold for this to be true is not precisely defined by law. + + If such an object file uses only numerical parameters, data +structure layouts and accessors, and small macros and small inline +functions (ten lines or less in length), then the use of the object +file is unrestricted, regardless of whether it is legally a derivative +work. (Executables containing this object code plus portions of the +Library will still fall under Section 6.) + + Otherwise, if the work is a derivative of the Library, you may +distribute the object code for the work under the terms of Section 6. +Any executables containing that work also fall under Section 6, +whether or not they are linked directly with the Library itself. + + 6. As an exception to the Sections above, you may also combine or +link a "work that uses the Library" with the Library to produce a +work containing portions of the Library, and distribute that work +under terms of your choice, provided that the terms permit +modification of the work for the customer's own use and reverse +engineering for debugging such modifications. + + You must give prominent notice with each copy of the work that the +Library is used in it and that the Library and its use are covered by +this License. You must supply a copy of this License. If the work +during execution displays copyright notices, you must include the +copyright notice for the Library among them, as well as a reference +directing the user to the copy of this License. Also, you must do one +of these things: + + a) Accompany the work with the complete corresponding + machine-readable source code for the Library including whatever + changes were used in the work (which must be distributed under + Sections 1 and 2 above); and, if the work is an executable linked + with the Library, with the complete machine-readable "work that + uses the Library", as object code and/or source code, so that the + user can modify the Library and then relink to produce a modified + executable containing the modified Library. (It is understood + that the user who changes the contents of definitions files in the + Library will not necessarily be able to recompile the application + to use the modified definitions.) + + b) Use a suitable shared library mechanism for linking with the + Library. A suitable mechanism is one that (1) uses at run time a + copy of the library already present on the user's computer system, + rather than copying library functions into the executable, and (2) + will operate properly with a modified version of the library, if + the user installs one, as long as the modified version is + interface-compatible with the version that the work was made with. + + c) Accompany the work with a written offer, valid for at + least three years, to give the same user the materials + specified in Subsection 6a, above, for a charge no more + than the cost of performing this distribution. + + d) If distribution of the work is made by offering access to copy + from a designated place, offer equivalent access to copy the above + specified materials from the same place. + + e) Verify that the user has already received a copy of these + materials or that you have already sent this user a copy. + + For an executable, the required form of the "work that uses the +Library" must include any data and utility programs needed for +reproducing the executable from it. However, as a special exception, +the materials to be distributed need not include anything that is +normally distributed (in either source or binary form) with the major +components (compiler, kernel, and so on) of the operating system on +which the executable runs, unless that component itself accompanies +the executable. + + It may happen that this requirement contradicts the license +restrictions of other proprietary libraries that do not normally +accompany the operating system. Such a contradiction means you cannot +use both them and the Library together in an executable that you +distribute. + + 7. You may place library facilities that are a work based on the +Library side-by-side in a single library together with other library +facilities not covered by this License, and distribute such a combined +library, provided that the separate distribution of the work based on +the Library and of the other library facilities is otherwise +permitted, and provided that you do these two things: + + a) Accompany the combined library with a copy of the same work + based on the Library, uncombined with any other library + facilities. This must be distributed under the terms of the + Sections above. + + b) Give prominent notice with the combined library of the fact + that part of it is a work based on the Library, and explaining + where to find the accompanying uncombined form of the same work. + + 8. You may not copy, modify, sublicense, link with, or distribute +the Library except as expressly provided under this License. Any +attempt otherwise to copy, modify, sublicense, link with, or +distribute the Library is void, and will automatically terminate your +rights under this License. However, parties who have received copies, +or rights, from you under this License will not have their licenses +terminated so long as such parties remain in full compliance. + + 9. You are not required to accept this License, since you have not +signed it. However, nothing else grants you permission to modify or +distribute the Library or its derivative works. These actions are +prohibited by law if you do not accept this License. Therefore, by +modifying or distributing the Library (or any work based on the +Library), you indicate your acceptance of this License to do so, and +all its terms and conditions for copying, distributing or modifying +the Library or works based on it. + + 10. Each time you redistribute the Library (or any work based on the +Library), the recipient automatically receives a license from the +original licensor to copy, distribute, link with or modify the Library +subject to these terms and conditions. You may not impose any further +restrictions on the recipients' exercise of the rights granted herein. +You are not responsible for enforcing compliance by third parties with +this License. + + 11. If, as a consequence of a court judgment or allegation of patent +infringement or for any other reason (not limited to patent issues), +conditions are imposed on you (whether by court order, agreement or +otherwise) that contradict the conditions of this License, they do not +excuse you from the conditions of this License. If you cannot +distribute so as to satisfy simultaneously your obligations under this +License and any other pertinent obligations, then as a consequence you +may not distribute the Library at all. For example, if a patent +license would not permit royalty-free redistribution of the Library by +all those who receive copies directly or indirectly through you, then +the only way you could satisfy both it and this License would be to +refrain entirely from distribution of the Library. + +If any portion of this section is held invalid or unenforceable under any +particular circumstance, the balance of the section is intended to apply, +and the section as a whole is intended to apply in other circumstances. + +It is not the purpose of this section to induce you to infringe any +patents or other property right claims or to contest validity of any +such claims; this section has the sole purpose of protecting the +integrity of the free software distribution system which is +implemented by public license practices. Many people have made +generous contributions to the wide range of software distributed +through that system in reliance on consistent application of that +system; it is up to the author/donor to decide if he or she is willing +to distribute software through any other system and a licensee cannot +impose that choice. + +This section is intended to make thoroughly clear what is believed to +be a consequence of the rest of this License. + + 12. If the distribution and/or use of the Library is restricted in +certain countries either by patents or by copyrighted interfaces, the +original copyright holder who places the Library under this License may add +an explicit geographical distribution limitation excluding those countries, +so that distribution is permitted only in or among countries not thus +excluded. In such case, this License incorporates the limitation as if +written in the body of this License. + + 13. The Free Software Foundation may publish revised and/or new +versions of the Lesser General Public License from time to time. +Such new versions will be similar in spirit to the present version, +but may differ in detail to address new problems or concerns. + +Each version is given a distinguishing version number. If the Library +specifies a version number of this License which applies to it and +"any later version", you have the option of following the terms and +conditions either of that version or of any later version published by +the Free Software Foundation. If the Library does not specify a +license version number, you may choose any version ever published by +the Free Software Foundation. + + 14. If you wish to incorporate parts of the Library into other free +programs whose distribution conditions are incompatible with these, +write to the author to ask for permission. For software which is +copyrighted by the Free Software Foundation, write to the Free +Software Foundation; we sometimes make exceptions for this. Our +decision will be guided by the two goals of preserving the free status +of all derivatives of our free software and of promoting the sharing +and reuse of software generally. + + NO WARRANTY + + 15. BECAUSE THE LIBRARY IS LICENSED FREE OF CHARGE, THERE IS NO +WARRANTY FOR THE LIBRARY, TO THE EXTENT PERMITTED BY APPLICABLE LAW. +EXCEPT WHEN OTHERWISE STATED IN WRITING THE COPYRIGHT HOLDERS AND/OR +OTHER PARTIES PROVIDE THE LIBRARY "AS IS" WITHOUT WARRANTY OF ANY +KIND, EITHER EXPRESSED OR IMPLIED, INCLUDING, BUT NOT LIMITED TO, THE +IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR +PURPOSE. THE ENTIRE RISK AS TO THE QUALITY AND PERFORMANCE OF THE +LIBRARY IS WITH YOU. SHOULD THE LIBRARY PROVE DEFECTIVE, YOU ASSUME +THE COST OF ALL NECESSARY SERVICING, REPAIR OR CORRECTION. + + 16. IN NO EVENT UNLESS REQUIRED BY APPLICABLE LAW OR AGREED TO IN +WRITING WILL ANY COPYRIGHT HOLDER, OR ANY OTHER PARTY WHO MAY MODIFY +AND/OR REDISTRIBUTE THE LIBRARY AS PERMITTED ABOVE, BE LIABLE TO YOU +FOR DAMAGES, INCLUDING ANY GENERAL, SPECIAL, INCIDENTAL OR +CONSEQUENTIAL DAMAGES ARISING OUT OF THE USE OR INABILITY TO USE THE +LIBRARY (INCLUDING BUT NOT LIMITED TO LOSS OF DATA OR DATA BEING +RENDERED INACCURATE OR LOSSES SUSTAINED BY YOU OR THIRD PARTIES OR A +FAILURE OF THE LIBRARY TO OPERATE WITH ANY OTHER SOFTWARE), EVEN IF +SUCH HOLDER OR OTHER PARTY HAS BEEN ADVISED OF THE POSSIBILITY OF SUCH +DAMAGES. + + END OF TERMS AND CONDITIONS + + How to Apply These Terms to Your New Libraries + + If you develop a new library, and you want it to be of the greatest +possible use to the public, we recommend making it free software that +everyone can redistribute and change. You can do so by permitting +redistribution under these terms (or, alternatively, under the terms of the +ordinary General Public License). + + To apply these terms, attach the following notices to the library. It is +safest to attach them to the start of each source file to most effectively +convey the exclusion of warranty; and each file should have at least the +"copyright" line and a pointer to where the full notice is found. + + + Copyright (C) + + This library is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2 of the License, or (at your option) any later version. + + This library 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 + Lesser General Public License for more details. + + You should have received a copy of the GNU Lesser General Public + License along with this library; if not, write to the Free Software + Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + +Also add information on how to contact you by electronic and paper mail. + +You should also get your employer (if you work as a programmer) or your +school, if any, to sign a "copyright disclaimer" for the library, if +necessary. Here is a sample; alter the names: + + Yoyodyne, Inc., hereby disclaims all copyright interest in the + library `Frob' (a library for tweaking knobs) written by James Random Hacker. + + , 1 April 1990 + Ty Coon, President of Vice + +That's all there is to it! + + diff --git a/src/osgPlugins/lwo/Makedepend b/src/osgPlugins/lwo/Makedepend new file mode 100644 index 000000000..e69de29bb diff --git a/src/osgPlugins/lwo/Makefile b/src/osgPlugins/lwo/Makefile new file mode 100644 index 000000000..751eb1aad --- /dev/null +++ b/src/osgPlugins/lwo/Makefile @@ -0,0 +1,15 @@ +#!smake +include ../../../Make/makedefs + +C++FILES = ReaderWriterLWO.cpp lw.cpp + +LIB = ../../../lib/osgPlugins/osgdb_lwo.so + +TARGET_LOADER_FILES = osgPlugins/osgdb_lwo.so + +LIBS = -losg -losgDB -losgUtil + +C++FLAGS += -I. -I../../../include +LDFLAGS += -L../../../lib + +include ../../../Make/makerules diff --git a/src/osgPlugins/lwo/README b/src/osgPlugins/lwo/README new file mode 100644 index 000000000..6d914ffe7 --- /dev/null +++ b/src/osgPlugins/lwo/README @@ -0,0 +1,22 @@ +AUTHOR + + lw is Copyright (C) 1999 by Janne Löf + + +WHAT IS lw? + lw is a LightWave mesh reader, I lifted this source from one of the + examples of GtkGLArea. This is why you will also need glib from gtk+, + I will remove this restriction in the next release. + + +LICENSE + + lw is free software; you can redistribute it and/or + modify it under the terms of the GNU Lesser General Public + License as published by the Free Software Foundation; either + version 2 of the License, or (at your option) any later version. + +DOCUMENTATION + + Use the source! + diff --git a/src/osgPlugins/lwo/README.osg b/src/osgPlugins/lwo/README.osg new file mode 100644 index 000000000..b0a76a077 --- /dev/null +++ b/src/osgPlugins/lwo/README.osg @@ -0,0 +1,6 @@ +This LightWave object reader is based on the lw mesh reader by Janne Löf. +It can be obtained from http://www.student.oulu.fi/~jlof/free/. + +ReaderWriterLWO.cpp is the OSG code which adapts the library into a osg plugin. + +Copyright (C) Ulrich Hertlein diff --git a/src/osgPlugins/lwo/ReaderWriterLWO.cpp b/src/osgPlugins/lwo/ReaderWriterLWO.cpp new file mode 100644 index 000000000..db84673bb --- /dev/null +++ b/src/osgPlugins/lwo/ReaderWriterLWO.cpp @@ -0,0 +1,177 @@ +// -*-c++-*- + +/* + * Lightwave Object loader for Open Scene Graph + * + * Copyright (C) 2001 Ulrich Hertlein + * + * The Open Scene Graph (OSG) is a cross platform C++/OpenGL library for + * real-time rendering of large 3D photo-realistic models. + * The OSG homepage is http://www.openscenegraph.org/ + */ + +#if defined(_MSC_VER) + #pragma warning( disable : 4786 ) +#endif + +#include +#include + +#include +#include +#include +#include + +#include +#include +#include + +#include + +#include +#include + +#include "lw.h" + +class ReaderWriterLWO : public osgDB::ReaderWriter +{ +public: + ReaderWriterLWO() { } + + virtual const char* className() { return "Lightwave Object Reader"; } + virtual bool acceptsExtension(const std::string& extension) { + return (extension == "lwo" || extension == "lw" || extension == "geo"); + } + + virtual osg::Node* readNode(const std::string& fileName); + +protected: +}; + + +// register with Registry to instantiate the above reader/writer. +osgDB::RegisterReaderWriterProxy g_lwoReaderWriterProxy; + + +// read file and convert to OSG. +osg::Node* ReaderWriterLWO::readNode(const std::string& fileName) +{ + lwObject* lw = lw_object_read(fileName.c_str()); + if (!lw) + return NULL; + + osg::notify(osg::INFO) << "faces " << lw->face_cnt << endl; + osg::notify(osg::INFO) << "materials " << lw->material_cnt << endl; + osg::notify(osg::INFO) << "vertices " << lw->vertex_cnt << endl; + + // shared coordinates + typedef std::map MaterialTriangles; + MaterialTriangles mts; + + + osgUtil::Tesselator tess; + for (int i = 0; i < lw->face_cnt; i++) + { + if (lw->face[i].index_cnt>=3) + { + tess.tesselate((osg::Vec3*)lw->vertex,lw->face[i].index_cnt,lw->face[i].index,osgUtil::Tesselator::CLOCK_WISE); + osgUtil::Tesselator::IndexVec& iv = mts[lw->face[i].material]; + const osgUtil::Tesselator::IndexVec& result = tess.getResult(); + iv.insert(iv.end(),result.begin(),result.end()); + } + } + + typedef std::vector CoordIndexMap; + CoordIndexMap cim(lw->vertex_cnt,-1); + + // create geode, to fill in for loop below, a geoset per material. + osg::Geode* geode = new osg::Geode; + + osgUtil::SmoothingVisitor smoother; + + for(MaterialTriangles::iterator itr=mts.begin(); + itr!=mts.end(); + ++itr) + { + // set up material + lwMaterial& lw_material = lw->material[itr->first]; + osg::Material* osg_material = new osg::Material; + + osg::Vec4 diffuse(lw_material.r, + lw_material.g, + lw_material.b, + 1.0f); + osg::Vec4 ambient(lw_material.r * 0.25f, + lw_material.g * 0.25f, + lw_material.b * 0.25f, + 1.0f); + + osg_material->setAmbient(osg::Material::FRONT_AND_BACK, ambient); + osg_material->setDiffuse(osg::Material::FRONT_AND_BACK, diffuse); + + // create state + osg::StateSet* state = new osg::StateSet; + state->setAttribute(osg_material); + + // intialize cim vector with -1 to represent unassigned vertices. + std::fill(cim.begin(),cim.end(),-1); + + osgUtil::Tesselator::IndexVec& iv = itr->second; + + // first fill in the references. + int vertexCount = 0; + osgUtil::Tesselator::IndexVec::iterator iv_itr; + for(iv_itr=iv.begin(); + iv_itr!=iv.end(); + ++iv_itr) + { + int i = *iv_itr; + if (cim[i]<0) cim[i] = vertexCount++; + } + + // copy across lw shared coords into local osg coords. + osg::Vec3* coord = new osg::Vec3[vertexCount]; + for (int i=0;ivertex_cnt;++i) + { + // From the spec_low.lxt : + // "By convention, the +X direction is to the right or east, the +Y + // direction is upward, and the +Z direction is forward or north" + // However, the osg sticks to the more conventional, y to the north, + // z upwards, x is the same - rigth/east. To handle this difference + // simple exchange osg_z for lwo_y, and osg_y for lwo_z. + + if (cim[i]>=0) coord[cim[i]].set(lw->vertex[i*3], lw->vertex[i*3+2], lw->vertex[i*3+1]); + } + + // copy across indices and remap them to the local coords offsets. + osg::ushort* cindex = new osg::ushort[iv.size()]; + osg::ushort* cindex_ptr = cindex; + for (iv_itr=iv.begin(); + iv_itr!=iv.end(); + ++iv_itr) + { + (*cindex_ptr) = cim[*iv_itr]; + ++cindex_ptr; + } + + int numPrim = iv.size()/3; + + // create geoset + + osg::GeoSet* gset = new osg::GeoSet; + gset->setPrimType(osg::GeoSet::TRIANGLES); + gset->setNumPrims(numPrim); + gset->setCoords(coord, cindex); + gset->setStateSet(state); + + smoother.smooth(*gset); + + geode->addDrawable(gset); + + } + + // free + lw_object_free(lw); + + return geode; +} diff --git a/src/osgPlugins/lwo/lw.cpp b/src/osgPlugins/lwo/lw.cpp new file mode 100644 index 000000000..eeb5401bb --- /dev/null +++ b/src/osgPlugins/lwo/lw.cpp @@ -0,0 +1,356 @@ +/* + * Copyright (C) 1998,1999 Janne Löf + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2 of the License, or (at your option) any later version. + * + * This library 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 + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + */ + +#include "lw.h" +#include +#include +#include +#include + +#define MK_ID(a,b,c,d) ((((guint32)(a))<<24)| \ + (((guint32)(b))<<16)| \ + (((guint32)(c))<< 8)| \ + (((guint32)(d)) )) + +#define ID_FORM MK_ID('F','O','R','M') +#define ID_LWOB MK_ID('L','W','O','B') +#define ID_PNTS MK_ID('P','N','T','S') +#define ID_SRFS MK_ID('S','R','F','S') +#define ID_SURF MK_ID('S','U','R','F') +#define ID_POLS MK_ID('P','O','L','S') +#define ID_COLR MK_ID('C','O','L','R') + +#define FALSE 0 +#define TRUE 1 + +#define g_return_val_if_fail(expr,val) if (!(expr)) return val; +#define g_return_if_fail(expr) if (!(expr)) return; +#define g_realloc(exp1,exp2) realloc(exp1,exp2) +#define g_malloc0(exp) malloc(exp) +#define g_warning printf +#define g_free free + +static gint32 read_char(FILE *f) +{ + int c = fgetc(f); + g_return_val_if_fail(c != EOF, 0); + return c; +} + +static gint32 read_short(FILE *f) +{ + return (read_char(f)<<8) | read_char(f); +} + +static gint32 read_long(FILE *f) +{ + return (read_char(f)<<24) | (read_char(f)<<16) | (read_char(f)<<8) | read_char(f); +} + +static GLfloat read_float(FILE *f) +{ + gint32 x = read_long(f); + return *(GLfloat*)&x; +} + +static gint read_string(FILE *f, char *s) +{ + gint c; + gint cnt = 0; + do { + c = read_char(f); + if (cnt < LW_MAX_NAME_LEN) + s[cnt] = c; + else + s[LW_MAX_NAME_LEN-1] = 0; + cnt++; + } while (c != 0); + /* if length of string (including \0) is odd skip another byte */ + if (cnt%2) { + read_char(f); + cnt++; + } + return cnt; +} + +static void read_srfs(FILE *f, gint nbytes, lwObject *lwo) +{ + int guess_cnt = lwo->material_cnt; + + while (nbytes > 0) { + lwMaterial *material; + + /* allocate more memory for materials if needed */ + if (guess_cnt <= lwo->material_cnt) { + guess_cnt += guess_cnt/2 + 4; + lwo->material = (lwMaterial*) g_realloc(lwo->material, sizeof(lwMaterial)*guess_cnt); + } + material = lwo->material + lwo->material_cnt++; + + /* read name */ + nbytes -= read_string(f,material->name); + + /* defaults */ + material->r = 0.7f; + material->g = 0.7f; + material->b = 0.7f; + } + lwo->material = (lwMaterial*) g_realloc(lwo->material, sizeof(lwMaterial)*lwo->material_cnt); +} + + +static void read_surf(FILE *f, gint nbytes, lwObject *lwo) +{ + int i; + char name[LW_MAX_NAME_LEN]; + lwMaterial *material = NULL; + + /* read surface name */ + nbytes -= read_string(f,name); + + /* find material */ + for (i=0; i< lwo->material_cnt; i++) { + if (strcmp(lwo->material[i].name,name) == 0) { + material = &lwo->material[i]; + break; + } + } + g_return_if_fail(material != NULL); + + /* read values */ + while (nbytes > 0) { + gint id = read_long(f); + gint len = read_short(f); + nbytes -= 6 + len + (len%2); + + switch (id) { + case ID_COLR: + material->r = read_char(f) / 255.0f; + material->g = read_char(f) / 255.0f; + material->b = read_char(f) / 255.0f; + read_char(f); /* dummy */ + break; + default: + fseek(f, len+(len%2), SEEK_CUR); + } + } +} + + +static void read_pols(FILE *f, int nbytes, lwObject *lwo) +{ + int guess_cnt = lwo->face_cnt; + + while (nbytes > 0) { + lwFace *face; + int i; + + /* allocate more memory for polygons if necessary */ + if (guess_cnt <= lwo->face_cnt) { + guess_cnt += guess_cnt + 4; + lwo->face = (lwFace*) g_realloc(lwo->face, sizeof(lwFace)*guess_cnt); + } + face = lwo->face + lwo->face_cnt++; + + face->init(); + + /* number of points in this face */ + face->index_cnt = read_short(f); + nbytes -= 2; + + /* allocate space for points */ + face->index = (int*) g_malloc0(sizeof(int)*face->index_cnt); + + /* read points in */ + for (i=0; iindex_cnt; i++) { + face->index[i] = read_short(f); + nbytes -= 2; + } + + /* read surface material */ + face->material = read_short(f); + nbytes -= 2; + + /* skip over detail polygons */ + if (face->material < 0) { + printf("face->material=%i ",face->material); + int det_cnt; + face->material = -face->material; + det_cnt = read_short(f); + nbytes -= 2; + while (det_cnt-- > 0) { + int cnt = read_short(f); + fseek(f, cnt*2+2, SEEK_CUR); + nbytes -= cnt*2+2; + } + } + face->material -= 1; + } + /* readjust to true size */ + lwo->face = (lwFace*) g_realloc(lwo->face, sizeof(lwFace)*lwo->face_cnt); +} + + + +static void read_pnts(FILE *f, gint nbytes, lwObject *lwo) +{ + int i; + lwo->vertex_cnt = nbytes / 12; + lwo->vertex = (GLfloat*) g_malloc0(sizeof(GLfloat)*lwo->vertex_cnt*3); + for (i=0; ivertex_cnt; i++) { + lwo->vertex[i*3+0] = read_float(f); + lwo->vertex[i*3+1] = read_float(f); + lwo->vertex[i*3+2] = read_float(f); + } +} + + + + + + +gint lw_is_lwobject(const char *lw_file) +{ + FILE *f = fopen(lw_file, "rb"); + if (f) { + gint32 form = read_long(f); + gint32 nlen = read_long(f); + gint32 lwob = read_long(f); + fclose(f); + if (form == ID_FORM && nlen != 0 && lwob == ID_LWOB) + return TRUE; + } + return FALSE; +} + + +lwObject *lw_object_read(const char *lw_file) +{ + FILE *f = NULL; + lwObject *lw_object = NULL; + + gint32 form_bytes = 0; + gint32 read_bytes = 0; + + /* open file */ + f = fopen(lw_file, "rb"); + if (f == NULL) { + g_warning("can't open file %s", lw_file); + return NULL; + } + + /* check for headers */ + if (read_long(f) != ID_FORM) { + g_warning("file %s is not an IFF file", lw_file); + fclose(f); + return NULL; + } + form_bytes = read_long(f); + read_bytes += 4; + + if (read_long(f) != ID_LWOB) { + g_warning("file %s is not a LWOB file", lw_file); + fclose(f); + return NULL; + } + + /* create new lwObject */ + lw_object = (lwObject*) g_malloc0(sizeof(lwObject)); + + lw_object->init(); + + /* read chunks */ + while (read_bytes < form_bytes) { + gint32 id = read_long(f); + gint32 nbytes = read_long(f); + read_bytes += 8 + nbytes + (nbytes%2); + + switch (id) { + case ID_PNTS: + read_pnts(f, nbytes, lw_object); + break; + case ID_POLS: + read_pols(f, nbytes, lw_object); + break; + case ID_SRFS: + read_srfs(f, nbytes, lw_object); + break; + case ID_SURF: + read_surf(f, nbytes, lw_object); + break; + default: + fseek(f, nbytes + (nbytes%2), SEEK_CUR); + } + } + + fclose(f); + return lw_object; +} + + + + + + + +void lw_object_free(lwObject *lw_object) +{ + g_return_if_fail(lw_object != NULL); + + if (lw_object->face) { + int i; + for (i=0; iface_cnt; i++) + g_free(lw_object->face[i].index); + g_free(lw_object->face); + } + g_free(lw_object->material); + g_free(lw_object->vertex); + g_free(lw_object); +} + + +GLfloat lw_object_radius(const lwObject *lwo) +{ + int i; + double max_radius = 0.0; + + g_return_val_if_fail(lwo != NULL, 0.0); + + for (i=0; ivertex_cnt; i++) { + GLfloat *v = &lwo->vertex[i*3]; + double r = v[0]*v[0] + v[1]*v[1] + v[2]*v[2]; + if (r > max_radius) + max_radius = r; + } + return (float)sqrt(max_radius); +} + +void lw_object_scale(lwObject *lwo, GLfloat scale) +{ + int i; + + g_return_if_fail(lwo != NULL); + + for (i=0; ivertex_cnt; i++) { + lwo->vertex[i*3+0] *= scale; + lwo->vertex[i*3+1] *= scale; + lwo->vertex[i*3+2] *= scale; + } +} + + diff --git a/src/osgPlugins/lwo/lw.h b/src/osgPlugins/lwo/lw.h new file mode 100644 index 000000000..322561ca1 --- /dev/null +++ b/src/osgPlugins/lwo/lw.h @@ -0,0 +1,90 @@ +/* + * Copyright (C) 1998,1999 Janne Löf + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2 of the License, or (at your option) any later version. + * + * This library 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 + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA + */ + + +#ifndef LW_H +#define LW_H + +#include + +#define LW_MAX_POINTS 200 +#define LW_MAX_NAME_LEN 500 + +struct lwMaterial +{ + char name[LW_MAX_NAME_LEN]; + GLfloat r,g,b; +}; + +struct lwFace +{ + int material; /* material of this face */ + int index_cnt; /* number of vertices */ + int *index; /* index to vertex */ + float *texcoord; /* u,v texture coordinates */ + + void init() + { + material = 0; /* material of this face */ + index_cnt = 0; /* number of vertices */ + index = 0; /* index to vertex */ + texcoord = 0; /* u,v texture coordinates */ + } + +}; + +struct lwObject +{ + int face_cnt; + lwFace *face; + + int material_cnt; + lwMaterial *material; + + int vertex_cnt; + GLfloat *vertex; + + void init() + { + face_cnt = 0; + face = 0; + + material_cnt=0; + material = 0; + + vertex_cnt=0; + vertex = 0; + } + +}; + + +typedef int gint32; +typedef unsigned int guint32; +typedef int gint; + + +gint lw_is_lwobject(const char *lw_file); +lwObject *lw_object_read(const char *lw_file); +void lw_object_free( lwObject *lw_object); + +GLfloat lw_object_radius(const lwObject *lw_object); +void lw_object_scale (lwObject *lw_object, GLfloat scale); + +#endif /* LW_H */ + diff --git a/src/osgPlugins/lwo/spec_lwob.txt b/src/osgPlugins/lwo/spec_lwob.txt new file mode 100644 index 000000000..caaef85f4 --- /dev/null +++ b/src/osgPlugins/lwo/spec_lwob.txt @@ -0,0 +1,391 @@ + LIGHTWAVE 3D OBJECT FILE FORMAT + + by Allen Hastings + & Stuart Ferguson + revised 11/28/94 + + +Introduction + + LightWave 3D objects are stored as IFF files with a FORM type of + LWOB. A FORM LWOB must contain a PNTS chunk, a SRFS chunk, and a + POLS chunk. There may be zero or more SURF chunks anywhere in the + file and up to one CRVS chunk. The POLS and CRVS chunks must be + preceded by the PNTS chunk and the SRFS chunk. LightWave 2.0 also + has the ability to save and load surface descriptions as FORM LWOB + files that contain only a SURF chunk. + + This document explains the contents of each chunk and includes an + annotated listing of a FORM LWOB as an example. + + +PNTS Chunk + + This chunk contains a list of the X, Y, and Z coordinates of all + the points in an object. Each coordinate is stored as a four byte + floating point number in IEEE format. Therefore, the number of + points in an object can be determined by dividing the size in bytes + of the PNTS chunk by 12. + + By convention, the +X direction is to the right or east, the +Y + direction is upward, and the +Z direction is forward or north. + For models of real-world objects, the unit size is usually + considered to be one meter. The coordinates are specified relative + to an object's pivot point. See the LightWave Modeler manual for + more information about LightWave 3D's geometric conventions. + + +SRFS Chunk + + This chunk contains a list of the names of all the surfaces in an + object (note that in LightWave 3D terminology, the word "surface" + is defined as a set of attributes that describe the color and + shading characteristics of a group of polygons). Each surface name + appears as a null-terminated character string. If the length of + the string (including the null) is odd, an extra null byte is + added. Surface names should be read from the file until as many + bytes as the chunk size specifies have been read. + + +POLS Chunk + + This chunk contains a list of all the polygons in an object. Each + entry consists of a short integer specifying the number of vertices + in a polygon followed by that many short integers specifying the + vertices themselves (as indices into the points list) followed by a + short integer specifying which surface is used by the polygon (as + an index into the surfaces list). The number of vertices in a + polygon currently may vary from one to 200. The vertex list for + each polygon should begin at a convex vertex and proceed clockwise + as seen from the visible side of the polygon (LightWave 3D polygons + are single-sided, except for those whose surfaces have the double- + sided flag set). The points list in the PNTS chunk is numbered + starting with zero and the surfaces list in the SRFS chunk is + numbered starting with one (so that surface numbers can be made + negative to signal the presence of detail polygons as explained + below). Polygons should be read from the file until as many bytes + as the chunk size specifies have been read. + + A negative surface number for a polygon indicates that the polygon + has detail polygons (which are drawn on top of the main polygon and + may be coplanar with it). In this case, the next number in the + file is a short integer specifying how many detail polygons belong + to the current polygon. This is followed by a list of those detail + polygons, where each entry is of the same format as described above + for regular polygons (except that the detail polygons cannot have + details of their own). The list of regular polygons then resumes. + To determine which surface is used by a polygon with a negative + surface number, the absolute value of that number should be used. + + +CRVS Chunks + + This chunk contains a list of all the spline curves in an object. + Each entry consists of a short integer specifying the number of + vertices in a curve followed by that many short integers specifying + the vertices themselves in sequential order, followed by a short + integer specifying which surface is used by the curve, followed by + another short integer specifying bit-flags associated with the + curve. If bit zero is set then the first point is a continuity + control point, and if bit one is set then the last point is. The + point and surface indices are as they are in the POLS chunk, except + that curves cannot have details. Curves should be read from the + file until as many bytes as the chunk size specifies have been read. + + +SURF Chunks + + Each SURF chunk describes the surface attributes of a particular + surface. These chunks begin with the name of the surface being + described. The name is stored as a character string with either + one or two trailing nulls (as explained in the SRFS chunk section). + Following the name is a series of sub-chunks, which are like normal + IFF chunks except that their sizes are specified by short integers + instead of longs. It is likely that the variety of sub-chunks will + grow as new surface attributes are added to the program, but any + unknown sub-chunks may be skipped over in the usual IFF fashion. + Sub-chunks should be read from the file until as many bytes as the + chunk size specifies have been read. + + COLR Sub-Chunk + + This sub-chunk consists of three bytes that specify the red, + green, and blue color components of the current surface, followed + by a byte which is currently ignored and should be zero. A + surface can therefore be any of 16,777,216 possible colors. + + FLAG Sub-Chunk + + This sub-chunk contains a short integer whose bits specify + various options for the current surface. Currently only the + nine least significant bits are used. The options that set bits + indicate are (starting with the least significant bit): + Luminous, Outline, Smoothing, Color Highlights, Color Filter, + Opaque Edge, Transparent Edge, Sharp Terminator, Double Sided, + and Additive (which is new for LW 3.0). Note that the two edge + transparency bits should not both be set. + + LUMI, DIFF, SPEC, REFL, and TRAN Sub-Chunks + + Each of these sub-chunks contain a short integer that specifies + the current surface's luminosity, diffuse, specular, reflection, + or transparency settings (the LUMI sub-chunk is new for LW 3.0, + and replaces the Luminous bit of the FLAG sub-chunk). A value of + 256 in the file corresponds to a setting of 100% on the control + panel. If any of these sub-chunks are absent for a surface, a + value of zero is assumed for the corresponding parameter. + + GLOS Sub-Chunk + + This sub-chunk contains a short integer that specifies the + glossiness of the current surface, and is only needed if the + specular setting in the SPEC sub-chunk is non-zero. A value of + 16 indicates low glossiness, 64 indicates medium glossiness, 256 + indicates high glossiness, and 1024 indicates maximum glossiness + (the maximum setting is new for LW 3.0). This parameter is + related to the "specular exponent" used in many lighting models. + + RIMG Sub-Chunk + + This sub-chunk contains the filename (including any path the user + may have specified) of the image to be used as a reflection map + for the current surface. Once again, if the length of the string + (including the terminating null) is odd, another null is added. + If the last part of the string is " (sequence)", then the first + part of the string specifies the prefix of an image sequence (the + actual filename in this case is generated by appending a three + digit frame number to the prefix when loading the image file for + each frame). If the reflection setting in the REFL sub-chunk is + non-zero but no RIMG sub-chunk is present, then the surface is + assumed to reflect the sky and ground backdrop (or to use ray + traced reflection if ray tracing is enabled). + + RSAN Sub-Chunk + + This sub-chunk contains a four byte IEEE floating point number + that specifies the heading angle of the reflection map seam + (expressed in degrees). This is new for LW 3.0. + + RIND Sub-Chunk + + This sub-chunk contains a four byte IEEE floating point number + that specifies the current surface's refractive index, which is + defined as the ratio of the speed of light in a vacuum to the + speed of light in the material. Since light is fastest in a + vacuum, this value should therefore be greater than or equal to + 1.0. + + EDGE Sub-Chunk + + This sub-chunk contains a four byte IEEE floating point number + that specifies the edge transparency threshold of the current + surface. This value should lie between 0.0 and 1.0. + + SMAN Sub-Chunk + + This sub-chunk contains a four byte IEEE floating point number + that specifies the maximum angle between two adjacent polygons + that can be smooth shaded (expressed in degrees). Polygons with + a greater angle between them will appear to meet at a sharp seam. + This is new for LW 3.0. + + CTEX, DTEX, STEX, RTEX, TTEX, and BTEX Sub-Chunks + + The presence of one of these sub-chunks indicates that the + current surface has a color, diffuse, specular, reflection, + transparency, or bump texture. The contents of the sub-chunk is + a character string (terminated by one or two nulls as usual) + specifying the texture type as shown on the control panel. Once + one of these sub-chunks is encountered within a SURF chunk, all + subsequent texture-related sub-chunks (those described below) are + considered to pertain to the current texture, until another CTEX, + DTEX, STEX, RTEX, TTEX, or BTEX sub-chunk is read. Currently + there may be zero or one of each of these sub-chunks (up to six + textures) in each SURF chunk. + + TIMG Sub-Chunk + + This sub-chunk specifies the filename of the image (or the prefix + of the image sequence) to be used for image texture mapping. See + the description of the RIMG sub-chunk above for more details. + + TFLG Sub-Chunk + + This sub-chunk contains a short integer whose bits specify + various options for the current texture. Currently only the + seven least significant bits are used. The options that set bits + indicate are (starting with the least significant bit): X Axis, + Y Axis, Z Axis, World Coords, Negative Image, Pixel Blending, and + Antialiasing. Note that only one of the three axis bits should + be set. + + TSIZ, TCTR, TFAL, and TVEL Sub-Chunks + + These sub-chunks each consist of three IEEE four byte floating + point numbers that specify the X, Y, and Z components of the + current texture's size, center, falloff, or velocity. The TCTR, + TFAL, and TVEL sub-chunks are only needed if the corresponding + parameters are non-zero. + + TCLR Sub-Chunk + + This sub-chunk contains four bytes that specify the texture color + for the current texture, which should be of the color-modifying + variety (in other words, there should be a CTEX sub-chunk + somewhere before this sub-chunk). The bytes are interpreted as + described above in the COLR sub-chunk section. + + TVAL Sub-Chunk + + This sub-chunk contains a short integer that specifies the + texture value of a diffuse, specular, reflection, or transparency + texture, so it should appear somewhere after a DTEX, STEX, RTEX, + or TTEX sub-chunk. A value of 256 in the file corresponds to a + a setting of 100% on the control panel. + + TAMP Sub-Chunk + + This sub-chunk contains a four byte IEEE floating point number + that specifies the amplitude of the current bump texture, so it + should appear somewhere after a BTEX sub-chunk. A value of 1.0 + is equivalent to a setting of 100% on the control panel. + + TFRQ Sub-Chunk + + This sub-chunk contains a short integer that specifies the number + of noise frequencies or wave sources used by the current texture. + + TSP0, TSP1, and TSP2 Sub-Chunks + + These sub-chunks each contain a four byte IEEE floating point + number that specifies one of the special texture type-specific + parameters (such as Contrast, Turbulence, Wavelength, etc). + Which sub-chunk is used to record a particular parameter depends + on the order in which that parameter's button appears on the + control panel. In the future there may be more than three of + these per texture. + + +Object File Example + + A simple object (with somewhat complex surfaces) is listed below to + illustrate some of the features of a FORM LWOB. The object is an + image-mapped bumpy square polygon in the XY plane with a shiny + transparent yellow triangle as a detail polygon. Each line of the + listing shows 16 bytes in hexadecimal form followed by their ASCII + equivalents. The notes under each line should be read from left to + right rather than top to bottom. + + 464F524D 0000019C 4C574F42 504E5453 FORM....LWOBPNTS + 00000054 3F800000 3F800000 00000000 ...T?...?....... + ^^^^^^^^ ^^^^^^^^ ^^^^^^^^ + The X, Y, and Z coordinates of point number zero are 1.0, + 1.0, and 0.0 (in IEEE format). + ^^^^ + There are 84 bytes in the PNTS chunk, so there are seven points + in the object. + + BF800000 3F800000 00000000 3F800000 ....?.......?... + BF800000 00000000 BF800000 BF800000 ................ + 00000000 3F000000 BF000000 00000000 ....?........... + 00000000 3F000000 00000000 BF000000 ....?........... + BF000000 00000000 53524653 00000012 ........SRFS.... + 53717561 72650000 54726961 6E676C65 Square..Triangle + ^^^^ + The surface name "Square" is terminated with two nulls + to even out the number of bytes. + + 0000504F 4C530000 00180004 00010000 ..POLS.......... + ^^^^ + The first polygon has four vertices (which + are points 1, 0, 2, and 3). + + 00020003 FFFF0001 00030005 00040006 ................ + ^^^^ + The detail polygon has three vertices (which are + points 5, 4, and 6). + ^^^^ + One detail polygon follows. + ^^^^ + The first polygon's surface code is -1, so it uses surface + number one ("Square") and has detail polygons. + + 00025355 52460000 00AE5371 75617265 ..SURF....Square + ^^^^ ^^^^ + This begins the description of the surface called "Square". + ^^^^ + The detail polygon uses surface number two ("Triangle"). + + 0000434F 4C520004 C8C8C800 464C4147 ..COLR......FLAG + 00020000 44494646 00020100 43544558 ....DIFF....CTEX + ^^^^^^^^ + The next set of texture sub-chunks + pertain to the surface's color texture. + ^^^^ + The "Square" surface's diffuse setting is + 100% (256 out of 256). + + 0012506C 616E6172 20496D61 6765204D ..Planar Image M + ^^^^ ^^^^^^^^ ^^^^^^^^ ^^^^^^^^ + The color texture is planar mapping of the image in the IFF + file "RAM:Laura". + + 61700000 54494D47 000A5241 4D3A4C61 ap..TIMG..RAM:La + 75726100 54464C47 00020004 5453495A ura.TFLG....TSIZ + ^^^^ + The flag bits indicate that the image is to + be projected along the Z axis. + + 000C4000 00003FC0 00003F80 00005443 ..@...?...?...TC + ^^^^ ^^^^^^^^ ^^^^^^^^ ^^^^ + The X, Y, and Z texture sizes are 2.0, 1.5, and 1.0. + + 4C520004 00000000 42544558 000E4672 LR......BTEX..Fr + ^^^^^^^^ + The next set of texture sub-chunks pertain to the + "Square" surface's bump texture. + + 61637461 6C204275 6D707300 54464C47 actal Bumps.TFLG + 0002000A 5453495A 000C3DCC CCCD3DCC ....TSIZ..=...=. + ^^^^ + The flag bits indicate that "Worlds Coords" is turned on. + + CCCD3DCC CCCD5441 4D500004 3FC00000 ..=...TAMP..?... + ^^^^^^^^ + The amplitude of the bumps is 150% (1.5 + in IEEE format). + + 54465251 00020001 53555246 00000044 TFRQ....SURF...D + ^^^^^^^^ + This begins the description of the surface called + "Triangle". + ^^^^ + The bump texture uses one frequency of noise. + + 54726961 6E676C65 0000434F 4C520004 Triangle..COLR.. + F0B40000 464C4147 00020000 44494646 ....FLAG....DIFF + ^^^^^^^^ + The "Triangle" surface's color is yellow (240 red, 180 green, and 0 + blue). + + 0002009A 53504543 000200CD 474C4F53 ....SPEC....GLOS + ^^^^ + The surface's specular setting is 80 % (205 + out of 256). + + 00020100 5245464C 00020033 5452414E ....REFL...3TRAN + ^^^^ + The surface's reflection map setting is 20% + (51 out of 256), but there is no RIMG sub- + chunk, so the surface reflects the backdrop. + ^^^^ + The surface has a high glossiness (256). + + 00020066 ...f + ^^^^ + The surface is 40% transparent (102 out of 256). + + The "Triangle" surface has no textures, and there are no more + surfaces to be defined, so the object file ends here. + + diff --git a/src/osgPlugins/obj/Makedepend b/src/osgPlugins/obj/Makedepend new file mode 100644 index 000000000..e69de29bb diff --git a/src/osgPlugins/obj/Makefile b/src/osgPlugins/obj/Makefile new file mode 100644 index 000000000..da7e28f45 --- /dev/null +++ b/src/osgPlugins/obj/Makefile @@ -0,0 +1,14 @@ +#!smake +include ../../../Make/makedefs + +C++FILES = ReaderWriterOBJ.cpp glm.cpp + +LIB = ../../../lib/osgPlugins/osgdb_obj.so + +TARGET_LOADER_FILES = osgPlugins/osgdb_obj.so + +LIBS = +C++FLAGS += -I. -I../../../include +LDFLAGS += -L../../../lib + +include ../../../Make/makerules diff --git a/src/osgPlugins/obj/README.osg b/src/osgPlugins/obj/README.osg new file mode 100644 index 000000000..7b34d59e5 --- /dev/null +++ b/src/osgPlugins/obj/README.osg @@ -0,0 +1,6 @@ +This Wavefront OBJ reader is based on the glm file format reader by +Nate Robins - http://www.pobox.com/~ndr/ + +ReaderWriterOBJ.cpp is the OSG code which adapts the library into a osg plugin. + +Copyright (C) Ulrich Hertlein diff --git a/src/osgPlugins/obj/ReaderWriterOBJ.cpp b/src/osgPlugins/obj/ReaderWriterOBJ.cpp new file mode 100644 index 000000000..7e114be3e --- /dev/null +++ b/src/osgPlugins/obj/ReaderWriterOBJ.cpp @@ -0,0 +1,403 @@ +// -*-c++-*- + +/* + * Wavefront OBJ loader for Open Scene Graph + * + * Copyright (C) 2001 Ulrich Hertlein + * + * Modified by Robert Osfield to support per Drawable coord, normal and + * texture coord arrays, bug fixes, and support for texture mapping. + * + * The Open Scene Graph (OSG) is a cross platform C++/OpenGL library for + * real-time rendering of large 3D photo-realistic models. + * The OSG homepage is http://www.openscenegraph.org/ + */ + +#if defined(_MSC_VER) + #pragma warning( disable : 4786 ) +#endif + +#include + +#include +#include +#include +#include + +#include +#include +#include +#include +#include + +#include +#include +#include +#include + +#include "glm.h" + + +class ReaderWriterOBJ : public osgDB::ReaderWriter +{ +public: + ReaderWriterOBJ() { } + + virtual const char* className() { return "Wavefront OBJ Reader"; } + virtual bool acceptsExtension(const std::string& extension) { + return (extension == "obj"); + } + + virtual osg::Node* readNode(const std::string& fileName); + +protected: + osg::Drawable* makeDrawable(GLMmodel* obj, GLMgroup* grp, osg::StateSet**); +}; + + +// register with Registry to instantiate the above reader/writer. +osgDB::RegisterReaderWriterProxy g_objReaderWriterProxy; + + +// read file and convert to OSG. +osg::Node* ReaderWriterOBJ::readNode(const std::string& fileName) +{ + GLMmodel* obj = glmReadOBJ((char*) fileName.c_str()); + if (!obj) + return NULL; + + std::string directory = osgDB::getFilePath(fileName); + + + osg::notify(osg::INFO) << "vertices " << obj->numvertices << endl; + osg::notify(osg::INFO) << "normals " << obj->numnormals << endl; + osg::notify(osg::INFO) << "texcoords " << obj->numtexcoords << endl; + osg::notify(osg::INFO) << "face normals " << obj->numfacetnorms << endl; + osg::notify(osg::INFO) << "tris " << obj->numtriangles << endl; + osg::notify(osg::INFO) << "materials " << obj->nummaterials << endl; + osg::notify(osg::INFO) << "groups " << obj->numgroups << endl; + + if (obj->numnormals==0) + { + osg::notify(osg::NOTICE) << "No normals in .obj file, automatically calculating normals..."<nummaterials > 0) { + osg_mtl = new osg::StateSet*[obj->nummaterials]; + for (i = 0; i < obj->nummaterials; i++) { + GLMmaterial* omtl = &(obj->materials[i]); + cerr << "mtl: " << omtl->name << endl; + + osg::StateSet* stateset = new osg::StateSet; + osg_mtl[i] = stateset; + + osg::Material* mtl = new osg::Material; + mtl->setAmbient(osg::Material::FRONT_AND_BACK, + osg::Vec4(omtl->ambient[0], omtl->ambient[1], + omtl->ambient[2], omtl->ambient[3])); + mtl->setDiffuse(osg::Material::FRONT_AND_BACK, + osg::Vec4(omtl->diffuse[0], omtl->diffuse[1], + omtl->diffuse[2], omtl->diffuse[3])); + mtl->setSpecular(osg::Material::FRONT_AND_BACK, + osg::Vec4(omtl->specular[0], omtl->specular[1], + omtl->specular[2], omtl->specular[3])); + mtl->setEmission(osg::Material::FRONT_AND_BACK, + osg::Vec4(omtl->emmissive[0], omtl->emmissive[1], + omtl->emmissive[2], omtl->emmissive[3])); + // note, osg shininess scales between 0.0 and 1.0. + mtl->setShininess(osg::Material::FRONT_AND_BACK, omtl->shininess/128.0f); + + stateset->setAttribute(mtl); + + if (omtl->textureName) + { + std::string fileName = osgDB::findFileInDirectory(omtl->textureName,directory,true); + if (!fileName.empty()) + { + + osg::Image* osg_image = osgDB::readImageFile(fileName.c_str()); + if (osg_image) + { + osg::Texture* osg_texture = new osg::Texture; + osg_texture->setImage(osg_image); + stateset->setAttributeAndModes(osg_texture,osg::StateAttribute::ON); + + if (omtl->textureReflection) + { + osg::TexGen* osg_texgen = new osg::TexGen; + osg_texgen->setMode(osg::TexGen::SPHERE_MAP); + stateset->setAttributeAndModes(osg_texgen,osg::StateAttribute::ON); + } + } + else + { + osg::notify(osg::NOTICE) << "Warning: Cannot create texture "<textureName<textureName<<"' not found"<position[0] != 0.0f || obj->position[2] != 0.0f || obj->position[2] != 0.0f) { + osg::Transform* xform = new osg::Transform; + // note obj_x -> osg_x, + // obj_y -> osg_z, + // obj_z -> osg_y, + xform->preTranslate(obj->position[0], obj->position[2], obj->position[1]); + osg_top = xform; + } + else + osg_top = new osg::Group; + + osg_top->setName(obj->pathname); + + // subgroups + // XXX one Geode per group is probably not necessary... + GLMgroup* ogrp = obj->groups; + while (ogrp) { + if (ogrp->numtriangles > 0) { + + osg::Geode* osg_geo = new osg::Geode; + osg_geo->setName(ogrp->name); + osg_geo->addDrawable(makeDrawable(obj,ogrp, osg_mtl)); + osg_top->addChild(osg_geo); + } + ogrp = ogrp->next; + } + + // free + glmDelete(obj); + if (osg_mtl) + delete[] osg_mtl; + + return osg_top; +} + + +// make drawable from OBJ group +osg::Drawable* ReaderWriterOBJ::makeDrawable(GLMmodel* obj, + GLMgroup* grp, + osg::StateSet** mtl) +{ + + GLMtriangle* tris = obj->triangles; + + unsigned int ntris = grp->numtriangles; + unsigned int i = 0; + + // geoset + osg::GeoSet* gset = new osg::GeoSet; + + // primitives are only triangles + gset->setPrimType(osg::GeoSet::TRIANGLES); + gset->setNumPrims(ntris); + int* primLen = new int[ntris]; + gset->setPrimLengths(primLen); + + + // the following code for mapping the coords, normals and texcoords + // is complicated greatly by the need to create seperate out the + // sets of coords etc for each drawable. + + typedef std::vector IndexVec; + + // fill an vector full of 0's, one for each vertex. + IndexVec vcount(obj->numvertices+1,0); + IndexVec ncount(obj->numnormals+1,0); + IndexVec tcount(obj->numtexcoords+1,0); + + bool needNormals = obj->normals && obj->normals>0; + bool needTexcoords = obj->texcoords && obj->numtexcoords>0; + + // first count the number of vertices used in this group. + for (i = 0; i < ntris; i++) + { + GLMtriangle* tri = &(tris[grp->triangles[i]]); + + // increment the count once for each traingle corner. + ++vcount[tri->vindices[0]]; + ++vcount[tri->vindices[1]]; + ++vcount[tri->vindices[2]]; + + if (needNormals) + { + ++ncount[tri->nindices[0]]; + ++ncount[tri->nindices[1]]; + ++ncount[tri->nindices[2]]; + } + + if (needTexcoords) + { + ++tcount[tri->tindices[0]]; + ++tcount[tri->tindices[1]]; + ++tcount[tri->tindices[2]]; + } + } + + + IndexVec::iterator itr; + int numCoords = 0; + for(itr=vcount.begin(); + itr!=vcount.end(); + ++itr) + { + if ((*itr)>0) ++numCoords; + } + + if (numCoords==0) return NULL; + + int numNormals = 0; + for(itr=ncount.begin(); + itr!=ncount.end(); + ++itr) + { + if ((*itr)>0) ++numNormals; + } + + int numTexcoords = 0; + for(itr=tcount.begin(); + itr!=tcount.end(); + ++itr) + { + if ((*itr)>0) ++numTexcoords; + } + + + // allocate drawables vertices. + osg::Vec3* coords = new osg::Vec3[numCoords]; + + // allocate drawables normals. + osg::Vec3* normals = NULL; + if (numNormals>0) normals = new osg::Vec3[numNormals]; + + // allocate drawables textcoords. + osg::Vec2* texcoords = NULL; + if (numTexcoords>0) texcoords = new osg::Vec2[numTexcoords]; + + + // fill an vector full of 0's, one for each vertex. + IndexVec vmapping(obj->numvertices+1,-1); + IndexVec nmapping(obj->numnormals+1,-1); + IndexVec tmapping(obj->numtexcoords+1,-1); + + int coordCount = 0; + for (i = 0; i < vcount.size(); i++) + { + + if (vcount[i]>0) + { + + // note obj_x -> osg_x, + // obj_y -> -osg_z, + // obj_z -> osg_y, + coords[coordCount].set(obj->vertices[i*3+0], + -obj->vertices[i*3+2], + obj->vertices[i*3+1]); + + vmapping[i]=coordCount; + ++coordCount; + } + } + + + int normCount = 0; + for (i = 0; i < ncount.size(); i++) + { + + if (ncount[i]>0) + { + // note obj_x -> osg_x, + // obj_y -> osg_z, + // obj_z -> osg_y, + // to rotate the about x axis to have model z upwards. + normals[normCount].set(obj->normals[i*3+0], + -obj->normals[i*3+2], + obj->normals[i*3+1]); + nmapping[i]=normCount; + ++normCount; + } + } + + int texCount = 0; + for (i = 0; i < tcount.size(); i++) + { + if (tcount[i]>0) + { + texcoords[texCount].set(obj->texcoords[i*2+0], obj->texcoords[i*2+1]); + tmapping[i]=texCount; + ++texCount; + } + } + + // index arrays + unsigned int* cindex = NULL; + cindex = new unsigned int[ntris * 3]; + + unsigned int* nindex = NULL; + if (normals) + nindex = new unsigned int[ntris * 3]; + + unsigned int* tindex = NULL; + if (texcoords) + tindex = new unsigned int[ntris * 3]; + + // setup arrays + for (i = 0; i < ntris; i++) { + primLen[i] = 3; + GLMtriangle* tri = &(tris[grp->triangles[i]]); + + cindex[i*3+0] = vmapping[tri->vindices[0]]; + cindex[i*3+1] = vmapping[tri->vindices[1]]; + cindex[i*3+2] = vmapping[tri->vindices[2]]; + + if (nindex) { + nindex[i*3+0] = nmapping[tri->nindices[0]]; + nindex[i*3+1] = nmapping[tri->nindices[1]]; + nindex[i*3+2] = nmapping[tri->nindices[2]]; + } + + if (tindex) { + tindex[i*3+0] = tmapping[tri->tindices[0]]; + tindex[i*3+1] = tmapping[tri->tindices[1]]; + tindex[i*3+2] = tmapping[tri->tindices[2]]; + } + } + + if (coords && cindex) + gset->setCoords(coords, cindex); + + if (normals && nindex) { + gset->setNormals(normals, nindex); + gset->setNormalBinding(osg::GeoSet::BIND_PERVERTEX); + } + + if (texcoords && tindex) { + gset->setTextureCoords(texcoords, tindex); + gset->setTextureBinding(osg::GeoSet::BIND_PERVERTEX); + } + + // state and material (if any) + if (mtl) { + + gset->setStateSet(mtl[grp->material]); + } + else + osg::notify(osg::INFO) << "Group " << grp->name << " has no material" << endl; + + return gset; +} + diff --git a/src/osgPlugins/obj/glm.cpp b/src/osgPlugins/obj/glm.cpp new file mode 100644 index 000000000..31a160101 --- /dev/null +++ b/src/osgPlugins/obj/glm.cpp @@ -0,0 +1,1774 @@ +/* + * Wavefront .obj file format reader. + * + * author: Nate Robins + * email: ndr@pobox.com + * www: http://www.pobox.com/~ndr + */ + + +/* includes */ +#include +#include +#include +#include +#include +#include "glm.h" + + +/* defines */ +#define T(x) model->triangles[(x)] + + +/* enums */ +enum { X, Y, Z, W }; /* elements of a vertex */ + + +/* typedefs */ + +/* _GLMnode: general purpose node + */ +typedef struct _GLMnode { + GLuint index; + GLboolean averaged; + struct _GLMnode* next; +} GLMnode; + + +/* private functions */ + +/* _glmMax: returns the maximum of two floats */ +static GLfloat +_glmMax(GLfloat a, GLfloat b) +{ + if (a > b) + return a; + return b; +} + +/* _glmAbs: returns the absolute value of a float */ +static GLfloat +_glmAbs(GLfloat f) +{ + if (f < 0) + return -f; + return f; +} + +/* _glmDot: compute the dot product of two vectors + * + * u - array of 3 GLfloats (GLfloat u[3]) + * v - array of 3 GLfloats (GLfloat v[3]) + */ +static GLfloat +_glmDot(GLfloat* u, GLfloat* v) +{ + assert(u); + assert(v); + + /* compute the dot product */ + return u[X] * v[X] + u[Y] * v[Y] + u[Z] * v[Z]; +} + +/* _glmCross: compute the cross product of two vectors + * + * u - array of 3 GLfloats (GLfloat u[3]) + * v - array of 3 GLfloats (GLfloat v[3]) + * n - array of 3 GLfloats (GLfloat n[3]) to return the cross product in + */ +static GLvoid +_glmCross(GLfloat* u, GLfloat* v, GLfloat* n) +{ + assert(u); + assert(v); + assert(n); + + /* compute the cross product (u x v for right-handed [ccw]) */ + n[X] = u[Y] * v[Z] - u[Z] * v[Y]; + n[Y] = u[Z] * v[X] - u[X] * v[Z]; + n[Z] = u[X] * v[Y] - u[Y] * v[X]; +} + +/* _glmNormalize: normalize a vector + * + * n - array of 3 GLfloats (GLfloat n[3]) to be normalized + */ +static GLvoid +_glmNormalize(GLfloat* n) +{ + GLfloat l; + + assert(n); + + /* normalize */ + l = (GLfloat)sqrt(n[X] * n[X] + n[Y] * n[Y] + n[Z] * n[Z]); + n[0] /= l; + n[1] /= l; + n[2] /= l; +} + +/* _glmEqual: compares two vectors and returns GL_TRUE if they are + * equal (within a certain threshold) or GL_FALSE if not. An epsilon + * that works fairly well is 0.000001. + * + * u - array of 3 GLfloats (GLfloat u[3]) + * v - array of 3 GLfloats (GLfloat v[3]) + */ +static GLboolean +_glmEqual(GLfloat* u, GLfloat* v, GLfloat epsilon) +{ + if (_glmAbs(u[0] - v[0]) < epsilon && + _glmAbs(u[1] - v[1]) < epsilon && + _glmAbs(u[2] - v[2]) < epsilon) + { + return GL_TRUE; + } + return GL_FALSE; +} + +/* _glmWeldVectors: eliminate (weld) vectors that are within an + * epsilon of each other. + * + * vectors - array of GLfloat[3]'s to be welded + * numvectors - number of GLfloat[3]'s in vectors + * epsilon - maximum difference between vectors + * + */ +GLfloat* +_glmWeldVectors(GLfloat* vectors, GLuint* numvectors, GLfloat epsilon) +{ + GLfloat* copies; + GLuint copied; + GLuint i, j; + + copies = (GLfloat*)malloc(sizeof(GLfloat) * 3 * (*numvectors + 1)); + memcpy(copies, vectors, (sizeof(GLfloat) * 3 * (*numvectors + 1))); + + copied = 1; + for (i = 1; i <= *numvectors; i++) { + for (j = 1; j <= copied; j++) { + if (_glmEqual(&vectors[3 * i], &copies[3 * j], epsilon)) { + goto duplicate; + } + } + + /* must not be any duplicates -- add to the copies array */ + copies[3 * copied + 0] = vectors[3 * i + 0]; + copies[3 * copied + 1] = vectors[3 * i + 1]; + copies[3 * copied + 2] = vectors[3 * i + 2]; + j = copied; /* pass this along for below */ + copied++; + + duplicate: + /* set the first component of this vector to point at the correct + index into the new copies array */ + vectors[3 * i + 0] = (GLfloat)j; + } + + *numvectors = copied-1; + return copies; +} + +/* _glmFindGroup: Find a group in the model + */ +GLMgroup* +_glmFindGroup(GLMmodel* model, char* name) +{ + GLMgroup* group; + + assert(model); + + group = model->groups; + while(group) { + if (!strcmp(name, group->name)) + break; + group = group->next; + } + + return group; +} + +/* _glmAddGroup: Add a group to the model + */ +GLMgroup* +_glmAddGroup(GLMmodel* model, char* name) +{ + GLMgroup* group; + + group = _glmFindGroup(model, name); + if (!group) { + group = (GLMgroup*)malloc(sizeof(GLMgroup)); + group->init(); + group->name = strdup(name); + group->material = 0; + group->numtriangles = 0; + group->triangles = NULL; + group->next = model->groups; + model->groups = group; + model->numgroups++; + } + + return group; +} + +/* _glmFindGroup: Find a material in the model + */ +GLuint +_glmFindMaterial(GLMmodel* model, char* name) +{ + GLuint i; + + for (i = 0; i < model->nummaterials; i++) { + if (!strcmp(model->materials[i].name, name)) + goto found; + } + + /* didn't find the name, so set it as the default material */ + fprintf(stderr,"_glmFindMaterial(): can't find material \"%s\".\n", name); + i = 0; + +found: + return i; +} + + +/* _glmDirName: return the directory given a path + * + * path - filesystem path + * + * The return value should be free'd. + */ +static char* +_glmDirName(char* path) +{ + char* dir; + char* s; + + dir = strdup(path); + + s = strrchr(dir, '/'); + if (s) + s[1] = '\0'; + else + dir[0] = '\0'; + + return dir; +} + + +/* _glmReadMTL: read a wavefront material library file + * + * model - properly initialized GLMmodel structure + * name - name of the material library + */ +static GLvoid +_glmReadMTL(GLMmodel* model, char* name) +{ + FILE* file; + char* dir; + char* filename; + char buf[128]; + GLuint nummaterials, i; + + dir = _glmDirName(model->pathname); + filename = (char*)malloc(sizeof(char) * (strlen(dir) + strlen(name) + 1)); + strcpy(filename, dir); + strcat(filename, name); + free(dir); + + /* open the file */ + file = fopen(filename, "r"); + if (!file) { + fprintf(stderr, "_glmReadMTL() failed: can't open material file \"%s\".\n", + filename); + return; + } + free(filename); + + /* count the number of materials in the file */ + nummaterials = 1; + while(fscanf(file, "%s", buf) != EOF) { + switch(buf[0]) { + case '#': /* comment */ + /* eat up rest of line */ + fgets(buf, sizeof(buf), file); + break; + case 'n': /* newmtl */ + fgets(buf, sizeof(buf), file); + nummaterials++; + sscanf(buf, "%s %s", buf, buf); + break; + default: + /* eat up rest of line */ + fgets(buf, sizeof(buf), file); + break; + } + } + + rewind(file); + + /* allocate memory for the materials */ + model->materials = (GLMmaterial*)malloc(sizeof(GLMmaterial) * nummaterials); + model->nummaterials = nummaterials; + + /* set the default material */ + for (i = 0; i < nummaterials; i++) { + model->materials[i].init(); + model->materials[i].name = NULL; + model->materials[i].shininess = 0.0f; + model->materials[i].diffuse[0] = 0.8f; + model->materials[i].diffuse[1] = 0.8f; + model->materials[i].diffuse[2] = 0.8f; + model->materials[i].diffuse[3] = 1.0f; + model->materials[i].ambient[0] = 0.2f; + model->materials[i].ambient[1] = 0.2f; + model->materials[i].ambient[2] = 0.2f; + model->materials[i].ambient[3] = 1.0f; + model->materials[i].specular[0] = 0.0f; + model->materials[i].specular[1] = 0.0f; + model->materials[i].specular[2] = 0.0f; + model->materials[i].textureName = NULL; + model->materials[i].textureReflection = false; + } + model->materials[0].name = strdup("default"); + + /* now, read in the data */ + nummaterials = 0; + while(fscanf(file, "%s", buf) != EOF) { + switch(buf[0]) { + case '#': /* comment */ + /* eat up rest of line */ + fgets(buf, sizeof(buf), file); + break; + case 'n': /* newmtl */ + fgets(buf, sizeof(buf), file); + sscanf(buf, "%s %s", buf, buf); + nummaterials++; + model->materials[nummaterials].name = strdup(buf); + break; + case 'N': + fscanf(file, "%f", &model->materials[nummaterials].shininess); + /* wavefront shininess is from [0, 1000], so scale for OpenGL */ + model->materials[nummaterials].shininess /= 1000.0; + model->materials[nummaterials].shininess *= 128.0; + break; + case 'K': + switch(buf[1]) { + case 'd': + fscanf(file, "%f %f %f", + &model->materials[nummaterials].diffuse[0], + &model->materials[nummaterials].diffuse[1], + &model->materials[nummaterials].diffuse[2]); + break; + case 's': + fscanf(file, "%f %f %f", + &model->materials[nummaterials].specular[0], + &model->materials[nummaterials].specular[1], + &model->materials[nummaterials].specular[2]); + break; + case 'a': + fscanf(file, "%f %f %f", + &model->materials[nummaterials].ambient[0], + &model->materials[nummaterials].ambient[1], + &model->materials[nummaterials].ambient[2]); + break; + default: + /* eat up rest of line */ + fgets(buf, sizeof(buf), file); + break; + } + break; + + default: + + /* added by RO */ + if (strcmp(buf,"map_Kd")==0) + { + fgets(buf, sizeof(buf), file); + sscanf(buf, "%s %s", buf, buf); + model->materials[nummaterials].textureName = strdup(buf); + } + else if (strcmp(buf,"refl")==0) + { + model->materials[nummaterials].textureReflection = true; + } + else + { + /* eat up rest of line */ + fgets(buf, sizeof(buf), file); + } + break; + } + } +} + +/* _glmWriteMTL: write a wavefront material library file + * + * model - properly initialized GLMmodel structure + * modelpath - pathname of the model being written + * mtllibname - name of the material library to be written + */ +static GLvoid +_glmWriteMTL(GLMmodel* model, char* modelpath, char* mtllibname) +{ + FILE* file; + char* dir; + char* filename; + GLMmaterial* material; + GLuint i; + + dir = _glmDirName(modelpath); + filename = (char*)malloc(sizeof(char) * (strlen(dir) + strlen(mtllibname))); + strcpy(filename, dir); + strcat(filename, mtllibname); + free(dir); + + /* open the file */ + file = fopen(filename, "w"); + if (!file) { + fprintf(stderr, "_glmWriteMTL() failed: can't open file \"%s\".\n", + filename); + return; + } + free(filename); + + /* spit out a header */ + fprintf(file, "# \n"); + fprintf(file, "# Wavefront MTL generated by GLM library\n"); + fprintf(file, "# \n"); + fprintf(file, "# GLM library copyright (C) 1997 by Nate Robins\n"); + fprintf(file, "# email: ndr@pobox.com\n"); + fprintf(file, "# www: http://www.pobox.com/~ndr\n"); + fprintf(file, "# \n\n"); + + for (i = 0; i < model->nummaterials; i++) { + material = &model->materials[i]; + fprintf(file, "newmtl %s\n", material->name); + fprintf(file, "Ka %f %f %f\n", + material->ambient[0], material->ambient[1], material->ambient[2]); + fprintf(file, "Kd %f %f %f\n", + material->diffuse[0], material->diffuse[1], material->diffuse[2]); + fprintf(file, "Ks %f %f %f\n", + material->specular[0],material->specular[1],material->specular[2]); + fprintf(file, "Ns %f\n", material->shininess); + fprintf(file, "\n"); + } +} +/* Create by RO to help handle g %s %s groups */ +static void createCompositeName(char* buf,char* compositeName) +{ + char *ptr_b = buf; + char *ptr_c = compositeName; + + /* first skip over leading spaces */ + while(*ptr_b!=0 && *ptr_b==' ') ++ptr_b; + + /* copy over rest, changing spaces for underscores, + * to handle faces which are contained in several groups */ + while(*ptr_b>=' ') + { + if (*ptr_b==' ') *ptr_c = '_'; + else *ptr_c = *ptr_b; + ++ptr_c; + ++ptr_b; + } + *ptr_c = 0; +} +/* _glmFirstPass: first pass at a Wavefront OBJ file that gets all the + * statistics of the model (such as #vertices, #normals, etc) + * + * model - properly initialized GLMmodel structure + * file - (fopen'd) file descriptor + */ +static GLvoid +_glmFirstPass(GLMmodel* model, FILE* file) +{ + GLuint numvertices; /* number of vertices in model */ + GLuint numnormals; /* number of normals in model */ + GLuint numtexcoords; /* number of texcoords in model */ + GLuint numtriangles; /* number of triangles in model */ + GLMgroup* group; /* current group */ + unsigned v, n, t; + char buf[128]; + + /* make a default group */ + group = _glmAddGroup(model, "default"); + + numvertices = numnormals = numtexcoords = numtriangles = 0; + while(fscanf(file, "%s", buf) != EOF) { + switch(buf[0]) { + case '#': /* comment */ + /* eat up rest of line */ + fgets(buf, sizeof(buf), file); + break; + case 'v': /* v, vn, vt */ + switch(buf[1]) { + case '\0': /* vertex */ + /* eat up rest of line */ + fgets(buf, sizeof(buf), file); + numvertices++; + break; + case 'n': /* normal */ + /* eat up rest of line */ + fgets(buf, sizeof(buf), file); + numnormals++; + break; + case 't': /* texcoord */ + /* eat up rest of line */ + fgets(buf, sizeof(buf), file); + numtexcoords++; + break; + default: + printf("_glmFirstPass(): Unknown token \"%s\".\n", buf); + //exit(1); + return; + break; + } + break; + case 'm': + fgets(buf, sizeof(buf), file); + sscanf(buf, "%s %s", buf, buf); + model->mtllibname = strdup(buf); + _glmReadMTL(model, buf); + break; + case 'u': + /* eat up rest of line */ + fgets(buf, sizeof(buf), file); + break; + case 'g': /* group */ + { + /* eat up rest of line */ + fgets(buf, sizeof(buf), file); + + char compositeName[128]; + createCompositeName(buf,compositeName); + + group = _glmAddGroup(model, compositeName); + } + break; + case 'f': /* face */ + v = n = t = 0; + fscanf(file, "%s", buf); + /* can be one of %d, %d//%d, %d/%d, %d/%d/%d %d//%d */ + if (strstr(buf, "//")) { + /* v//n */ + sscanf(buf, "%d//%d", &v, &n); + fscanf(file, "%d//%d", &v, &n); + fscanf(file, "%d//%d", &v, &n); + numtriangles++; + group->numtriangles++; + while(fscanf(file, "%d//%d", &v, &n) > 0) { + numtriangles++; + group->numtriangles++; + } + } else if (sscanf(buf, "%d/%d/%d", &v, &t, &n) == 3) { + /* v/t/n */ + fscanf(file, "%d/%d/%d", &v, &t, &n); + fscanf(file, "%d/%d/%d", &v, &t, &n); + numtriangles++; + group->numtriangles++; + while(fscanf(file, "%d/%d/%d", &v, &t, &n) > 0) { + numtriangles++; + group->numtriangles++; + } + } else if (sscanf(buf, "%d/%d", &v, &t) == 2) { + /* v/t */ + fscanf(file, "%d/%d", &v, &t); + fscanf(file, "%d/%d", &v, &t); + numtriangles++; + group->numtriangles++; + while(fscanf(file, "%d/%d", &v, &t) > 0) { + numtriangles++; + group->numtriangles++; + } + } else { + /* v */ + fscanf(file, "%d", &v); + fscanf(file, "%d", &v); + numtriangles++; + group->numtriangles++; + while(fscanf(file, "%d", &v) > 0) { + numtriangles++; + group->numtriangles++; + } + } + break; + + default: + /* eat up rest of line */ + fgets(buf, sizeof(buf), file); + break; + } + } + +#if 0 + /* announce the model statistics */ + printf(" Vertices: %d\n", numvertices); + printf(" Normals: %d\n", numnormals); + printf(" Texcoords: %d\n", numtexcoords); + printf(" Triangles: %d\n", numtriangles); + printf(" Groups: %d\n", model->numgroups); +#endif + + /* set the stats in the model structure */ + model->numvertices = numvertices; + model->numnormals = numnormals; + model->numtexcoords = numtexcoords; + model->numtriangles = numtriangles; + + /* allocate memory for the triangles in each group */ + group = model->groups; + while(group) { + group->triangles = (GLuint*)malloc(sizeof(GLuint) * group->numtriangles); + group->numtriangles = 0; + group = group->next; + } +} + +/* _glmSecondPass: second pass at a Wavefront OBJ file that gets all + * the data. + * + * model - properly initialized GLMmodel structure + * file - (fopen'd) file descriptor + */ +static GLvoid +_glmSecondPass(GLMmodel* model, FILE* file) +{ + GLuint numvertices; /* number of vertices in model */ + GLuint numnormals; /* number of normals in model */ + GLuint numtexcoords; /* number of texcoords in model */ + GLuint numtriangles; /* number of triangles in model */ + GLfloat* vertices; /* array of vertices */ + GLfloat* normals; /* array of normals */ + GLfloat* texcoords; /* array of texture coordinates */ + GLMgroup* group; /* current group pointer */ + GLuint material; /* current material */ + GLuint v, n, t; + char buf[128]; + + /* set the pointer shortcuts */ + vertices = model->vertices; + normals = model->normals; + texcoords = model->texcoords; + group = model->groups; + + /* on the second pass through the file, read all the data into the + allocated arrays */ + numvertices = numnormals = numtexcoords = 1; + numtriangles = 0; + material = 0; + + bool firstGroup = true; + bool previousLineWas_g = false; + + while(fscanf(file, "%s", buf) != EOF) { + char c = buf[0]; + switch(c) { + case '#': /* comment */ + /* eat up rest of line */ + fgets(buf, sizeof(buf), file); + break; + case 'v': /* v, vn, vt */ + switch(buf[1]) { + case '\0': /* vertex */ + fscanf(file, "%f %f %f", + &vertices[3 * numvertices + X], + &vertices[3 * numvertices + Y], + &vertices[3 * numvertices + Z]); + numvertices++; + break; + case 'n': /* normal */ + fscanf(file, "%f %f %f", + &normals[3 * numnormals + X], + &normals[3 * numnormals + Y], + &normals[3 * numnormals + Z]); + numnormals++; + break; + case 't': /* texcoord */ + fscanf(file, "%f %f", + &texcoords[2 * numtexcoords + X], + &texcoords[2 * numtexcoords + Y]); + numtexcoords++; + break; + } + break; + case 'u': + fgets(buf, sizeof(buf), file); + sscanf(buf, "%s %s", buf, buf); + + /*group->material =*/ material = _glmFindMaterial(model, buf); + + // a hack by Robert Osfield to account for usemtl being infront + // or the group, or after - but only one line after. + // original code always assigned material to current group. + if (previousLineWas_g || firstGroup) group->material = material; + + break; + case 'g': /* group */ + /* eat up rest of line */ + fgets(buf, sizeof(buf), file); + char compositeName[128]; + createCompositeName(buf,compositeName); + + group = _glmFindGroup(model, compositeName); + group->material = material; + firstGroup = false; + break; + case 'f': /* face */ + v = n = t = 0; + fscanf(file, "%s", buf); + /* can be one of %d, %d//%d, %d/%d, %d/%d/%d %d//%d */ + if (strstr(buf, "//")) { + /* v//n */ + sscanf(buf, "%d//%d", &v, &n); + T(numtriangles).vindices[0] = v; + T(numtriangles).nindices[0] = n; + fscanf(file, "%d//%d", &v, &n); + T(numtriangles).vindices[1] = v; + T(numtriangles).nindices[1] = n; + fscanf(file, "%d//%d", &v, &n); + T(numtriangles).vindices[2] = v; + T(numtriangles).nindices[2] = n; + group->triangles[group->numtriangles++] = numtriangles; + numtriangles++; + while(fscanf(file, "%d//%d", &v, &n) > 0) { + T(numtriangles).vindices[0] = T(numtriangles-1).vindices[0]; + T(numtriangles).nindices[0] = T(numtriangles-1).nindices[0]; + T(numtriangles).vindices[1] = T(numtriangles-1).vindices[2]; + T(numtriangles).nindices[1] = T(numtriangles-1).nindices[2]; + T(numtriangles).vindices[2] = v; + T(numtriangles).nindices[2] = n; + group->triangles[group->numtriangles++] = numtriangles; + numtriangles++; + } + } else if (sscanf(buf, "%d/%d/%d", &v, &t, &n) == 3) { + /* v/t/n */ + T(numtriangles).vindices[0] = v; + T(numtriangles).tindices[0] = t; + T(numtriangles).nindices[0] = n; + fscanf(file, "%d/%d/%d", &v, &t, &n); + T(numtriangles).vindices[1] = v; + T(numtriangles).tindices[1] = t; + T(numtriangles).nindices[1] = n; + fscanf(file, "%d/%d/%d", &v, &t, &n); + T(numtriangles).vindices[2] = v; + T(numtriangles).tindices[2] = t; + T(numtriangles).nindices[2] = n; + group->triangles[group->numtriangles++] = numtriangles; + numtriangles++; + while(fscanf(file, "%d/%d/%d", &v, &t, &n) > 0) { + T(numtriangles).vindices[0] = T(numtriangles-1).vindices[0]; + T(numtriangles).tindices[0] = T(numtriangles-1).tindices[0]; + T(numtriangles).nindices[0] = T(numtriangles-1).nindices[0]; + T(numtriangles).vindices[1] = T(numtriangles-1).vindices[2]; + T(numtriangles).tindices[1] = T(numtriangles-1).tindices[2]; + T(numtriangles).nindices[1] = T(numtriangles-1).nindices[2]; + T(numtriangles).vindices[2] = v; + T(numtriangles).tindices[2] = t; + T(numtriangles).nindices[2] = n; + group->triangles[group->numtriangles++] = numtriangles; + numtriangles++; + } + } else if (sscanf(buf, "%d/%d", &v, &t) == 2) { + /* v/t */ + T(numtriangles).vindices[0] = v; + T(numtriangles).tindices[0] = t; + fscanf(file, "%d/%d", &v, &t); + T(numtriangles).vindices[1] = v; + T(numtriangles).tindices[1] = t; + fscanf(file, "%d/%d", &v, &t); + T(numtriangles).vindices[2] = v; + T(numtriangles).tindices[2] = t; + group->triangles[group->numtriangles++] = numtriangles; + numtriangles++; + while(fscanf(file, "%d/%d", &v, &t) > 0) { + T(numtriangles).vindices[0] = T(numtriangles-1).vindices[0]; + T(numtriangles).tindices[0] = T(numtriangles-1).tindices[0]; + T(numtriangles).vindices[1] = T(numtriangles-1).vindices[2]; + T(numtriangles).tindices[1] = T(numtriangles-1).tindices[2]; + T(numtriangles).vindices[2] = v; + T(numtriangles).tindices[2] = t; + group->triangles[group->numtriangles++] = numtriangles; + numtriangles++; + } + } else { + /* v */ + sscanf(buf, "%d", &v); + T(numtriangles).vindices[0] = v; + fscanf(file, "%d", &v); + T(numtriangles).vindices[1] = v; + fscanf(file, "%d", &v); + T(numtriangles).vindices[2] = v; + group->triangles[group->numtriangles++] = numtriangles; + numtriangles++; + while(fscanf(file, "%d", &v) > 0) { + T(numtriangles).vindices[0] = T(numtriangles-1).vindices[0]; + T(numtriangles).vindices[1] = T(numtriangles-1).vindices[2]; + T(numtriangles).vindices[2] = v; + group->triangles[group->numtriangles++] = numtriangles; + numtriangles++; + } + } + break; + + default: + /* eat up rest of line */ + fgets(buf, sizeof(buf), file); + break; + } + + // a hack by Robert Osfield to account for usemtl being infront + // or the group, or after - but only one line after. + previousLineWas_g = (c=='g'); + } + +#if 0 + /* announce the memory requirements */ + printf(" Memory: %d bytes\n", + numvertices * 3*sizeof(GLfloat) + + numnormals * 3*sizeof(GLfloat) * (numnormals ? 1 : 0) + + numtexcoords * 3*sizeof(GLfloat) * (numtexcoords ? 1 : 0) + + numtriangles * sizeof(GLMtriangle)); +#endif +} + + + + +/* public functions */ + +/* glmUnitize: "unitize" a model by translating it to the origin and + * scaling it to fit in a unit cube around the origin. Returns the + * scalefactor used. + * + * model - properly initialized GLMmodel structure + */ +GLfloat +glmUnitize(GLMmodel* model) +{ + GLuint i; + GLfloat maxx, minx, maxy, miny, maxz, minz; + GLfloat cx, cy, cz, w, h, d; + GLfloat scale; + + assert(model); + assert(model->vertices); + + /* get the max/mins */ + maxx = minx = model->vertices[3 + X]; + maxy = miny = model->vertices[3 + Y]; + maxz = minz = model->vertices[3 + Z]; + for (i = 1; i <= model->numvertices; i++) { + if (maxx < model->vertices[3 * i + X]) + maxx = model->vertices[3 * i + X]; + if (minx > model->vertices[3 * i + X]) + minx = model->vertices[3 * i + X]; + + if (maxy < model->vertices[3 * i + Y]) + maxy = model->vertices[3 * i + Y]; + if (miny > model->vertices[3 * i + Y]) + miny = model->vertices[3 * i + Y]; + + if (maxz < model->vertices[3 * i + Z]) + maxz = model->vertices[3 * i + Z]; + if (minz > model->vertices[3 * i + Z]) + minz = model->vertices[3 * i + Z]; + } + + /* calculate model width, height, and depth */ + w = _glmAbs(maxx) + _glmAbs(minx); + h = _glmAbs(maxy) + _glmAbs(miny); + d = _glmAbs(maxz) + _glmAbs(minz); + + /* calculate center of the model */ + cx = (maxx + minx) / 2.0f; + cy = (maxy + miny) / 2.0f; + cz = (maxz + minz) / 2.0f; + + /* calculate unitizing scale factor */ + scale = 2.0f / _glmMax(_glmMax(w, h), d); + + /* translate around center then scale */ + for (i = 1; i <= model->numvertices; i++) { + model->vertices[3 * i + X] -= cx; + model->vertices[3 * i + Y] -= cy; + model->vertices[3 * i + Z] -= cz; + model->vertices[3 * i + X] *= scale; + model->vertices[3 * i + Y] *= scale; + model->vertices[3 * i + Z] *= scale; + } + + return scale; +} + +/* glmDimensions: Calculates the dimensions (width, height, depth) of + * a model. + * + * model - initialized GLMmodel structure + * dimensions - array of 3 GLfloats (GLfloat dimensions[3]) + */ +GLvoid +glmDimensions(GLMmodel* model, GLfloat* dimensions) +{ + GLuint i; + GLfloat maxx, minx, maxy, miny, maxz, minz; + + assert(model); + assert(model->vertices); + assert(dimensions); + + /* get the max/mins */ + maxx = minx = model->vertices[3 + X]; + maxy = miny = model->vertices[3 + Y]; + maxz = minz = model->vertices[3 + Z]; + for (i = 1; i <= model->numvertices; i++) { + if (maxx < model->vertices[3 * i + X]) + maxx = model->vertices[3 * i + X]; + if (minx > model->vertices[3 * i + X]) + minx = model->vertices[3 * i + X]; + + if (maxy < model->vertices[3 * i + Y]) + maxy = model->vertices[3 * i + Y]; + if (miny > model->vertices[3 * i + Y]) + miny = model->vertices[3 * i + Y]; + + if (maxz < model->vertices[3 * i + Z]) + maxz = model->vertices[3 * i + Z]; + if (minz > model->vertices[3 * i + Z]) + minz = model->vertices[3 * i + Z]; + } + + /* calculate model width, height, and depth */ + dimensions[X] = _glmAbs(maxx) + _glmAbs(minx); + dimensions[Y] = _glmAbs(maxy) + _glmAbs(miny); + dimensions[Z] = _glmAbs(maxz) + _glmAbs(minz); +} + +/* glmScale: Scales a model by a given amount. + * + * model - properly initialized GLMmodel structure + * scale - scalefactor (0.5 = half as large, 2.0 = twice as large) + */ +GLvoid +glmScale(GLMmodel* model, GLfloat scale) +{ + GLuint i; + + for (i = 1; i <= model->numvertices; i++) { + model->vertices[3 * i + X] *= scale; + model->vertices[3 * i + Y] *= scale; + model->vertices[3 * i + Z] *= scale; + } +} + +/* glmReverseWinding: Reverse the polygon winding for all polygons in + * this model. Default winding is counter-clockwise. Also changes + * the direction of the normals. + * + * model - properly initialized GLMmodel structure + */ +GLvoid +glmReverseWinding(GLMmodel* model) +{ + GLuint i, swap; + + assert(model); + + for (i = 0; i < model->numtriangles; i++) { + swap = T(i).vindices[0]; + T(i).vindices[0] = T(i).vindices[2]; + T(i).vindices[2] = swap; + + if (model->numnormals) { + swap = T(i).nindices[0]; + T(i).nindices[0] = T(i).nindices[2]; + T(i).nindices[2] = swap; + } + + if (model->numtexcoords) { + swap = T(i).tindices[0]; + T(i).tindices[0] = T(i).tindices[2]; + T(i).tindices[2] = swap; + } + } + + /* reverse facet normals */ + for (i = 1; i <= model->numfacetnorms; i++) { + model->facetnorms[3 * i + X] = -model->facetnorms[3 * i + X]; + model->facetnorms[3 * i + Y] = -model->facetnorms[3 * i + Y]; + model->facetnorms[3 * i + Z] = -model->facetnorms[3 * i + Z]; + } + + /* reverse vertex normals */ + for (i = 1; i <= model->numnormals; i++) { + model->normals[3 * i + X] = -model->normals[3 * i + X]; + model->normals[3 * i + Y] = -model->normals[3 * i + Y]; + model->normals[3 * i + Z] = -model->normals[3 * i + Z]; + } +} + +/* glmFacetNormals: Generates facet normals for a model (by taking the + * cross product of the two vectors derived from the sides of each + * triangle). Assumes a counter-clockwise winding. + * + * model - initialized GLMmodel structure + */ +GLvoid +glmFacetNormals(GLMmodel* model) +{ + GLuint i; + GLfloat u[3]; + GLfloat v[3]; + + assert(model); + assert(model->vertices); + + /* clobber any old facetnormals */ + if (model->facetnorms) + free(model->facetnorms); + + /* allocate memory for the new facet normals */ + model->numfacetnorms = model->numtriangles; + model->facetnorms = (GLfloat*)malloc(sizeof(GLfloat) * + 3 * (model->numfacetnorms + 1)); + + for (i = 0; i < model->numtriangles; i++) { + model->triangles[i].findex = i+1; + + u[X] = model->vertices[3 * T(i).vindices[1] + X] - + model->vertices[3 * T(i).vindices[0] + X]; + u[Y] = model->vertices[3 * T(i).vindices[1] + Y] - + model->vertices[3 * T(i).vindices[0] + Y]; + u[Z] = model->vertices[3 * T(i).vindices[1] + Z] - + model->vertices[3 * T(i).vindices[0] + Z]; + + v[X] = model->vertices[3 * T(i).vindices[2] + X] - + model->vertices[3 * T(i).vindices[0] + X]; + v[Y] = model->vertices[3 * T(i).vindices[2] + Y] - + model->vertices[3 * T(i).vindices[0] + Y]; + v[Z] = model->vertices[3 * T(i).vindices[2] + Z] - + model->vertices[3 * T(i).vindices[0] + Z]; + + _glmCross(u, v, &model->facetnorms[3 * (i+1)]); + _glmNormalize(&model->facetnorms[3 * (i+1)]); + } +} + +/* glmVertexNormals: Generates smooth vertex normals for a model. + * First builds a list of all the triangles each vertex is in. Then + * loops through each vertex in the the list averaging all the facet + * normals of the triangles each vertex is in. Finally, sets the + * normal index in the triangle for the vertex to the generated smooth + * normal. If the dot product of a facet normal and the facet normal + * associated with the first triangle in the list of triangles the + * current vertex is in is greater than the cosine of the angle + * parameter to the function, that facet normal is not added into the + * average normal calculation and the corresponding vertex is given + * the facet normal. This tends to preserve hard edges. The angle to + * use depends on the model, but 90 degrees is usually a good start. + * + * model - initialized GLMmodel structure + * angle - maximum angle (in degrees) to smooth across + */ +GLvoid +glmVertexNormals(GLMmodel* model, GLfloat angle) +{ + GLMnode* node; + GLMnode* tail; + GLMnode** members; + GLfloat* normals; + GLuint numnormals; + GLfloat average[3]; + GLfloat dot, cos_angle; + GLuint i, avg; + + assert(model); + assert(model->facetnorms); + + /* calculate the cosine of the angle (in degrees) */ + cos_angle = (float)cos(angle * M_PI / 180.0); + + /* nuke any previous normals */ + if (model->normals) + free(model->normals); + + /* allocate space for new normals */ + model->numnormals = model->numtriangles * 3; /* 3 normals per triangle */ + model->normals = (GLfloat*)malloc(sizeof(GLfloat)* 3* (model->numnormals+1)); + + /* allocate a structure that will hold a linked list of triangle + indices for each vertex */ + members = (GLMnode**)malloc(sizeof(GLMnode*) * (model->numvertices + 1)); + for (i = 1; i <= model->numvertices; i++) + members[i] = NULL; + + /* for every triangle, create a node for each vertex in it */ + for (i = 0; i < model->numtriangles; i++) { + node = (GLMnode*)malloc(sizeof(GLMnode)); + node->index = i; + node->next = members[T(i).vindices[0]]; + members[T(i).vindices[0]] = node; + + node = (GLMnode*)malloc(sizeof(GLMnode)); + node->index = i; + node->next = members[T(i).vindices[1]]; + members[T(i).vindices[1]] = node; + + node = (GLMnode*)malloc(sizeof(GLMnode)); + node->index = i; + node->next = members[T(i).vindices[2]]; + members[T(i).vindices[2]] = node; + } + + /* calculate the average normal for each vertex */ + numnormals = 1; + for (i = 1; i <= model->numvertices; i++) { + /* calculate an average normal for this vertex by averaging the + facet normal of every triangle this vertex is in */ + node = members[i]; + if (!node) + fprintf(stderr, "glmVertexNormals(): vertex w/o a triangle\n"); + average[0] = 0.0; average[1] = 0.0; average[2] = 0.0; + avg = 0; + while (node) { + /* only average if the dot product of the angle between the two + facet normals is greater than the cosine of the threshold + angle -- or, said another way, the angle between the two + facet normals is less than (or equal to) the threshold angle */ + dot = _glmDot(&model->facetnorms[3 * T(node->index).findex], + &model->facetnorms[3 * T(members[i]->index).findex]); + if (dot > cos_angle) { + node->averaged = GL_TRUE; + average[0] += model->facetnorms[3 * T(node->index).findex + 0]; + average[1] += model->facetnorms[3 * T(node->index).findex + 1]; + average[2] += model->facetnorms[3 * T(node->index).findex + 2]; + avg = 1; /* we averaged at least one normal! */ + } else { + node->averaged = GL_FALSE; + } + node = node->next; + } + + if (avg) { + /* normalize the averaged normal */ + _glmNormalize(average); + + /* add the normal to the vertex normals list */ + model->normals[3 * numnormals + 0] = average[0]; + model->normals[3 * numnormals + 1] = average[1]; + model->normals[3 * numnormals + 2] = average[2]; + avg = numnormals; + numnormals++; + } + + /* set the normal of this vertex in each triangle it is in */ + node = members[i]; + while (node) { + if (node->averaged) { + /* if this node was averaged, use the average normal */ + if (T(node->index).vindices[0] == i) + T(node->index).nindices[0] = avg; + else if (T(node->index).vindices[1] == i) + T(node->index).nindices[1] = avg; + else if (T(node->index).vindices[2] == i) + T(node->index).nindices[2] = avg; + } else { + /* if this node wasn't averaged, use the facet normal */ + model->normals[3 * numnormals + 0] = + model->facetnorms[3 * T(node->index).findex + 0]; + model->normals[3 * numnormals + 1] = + model->facetnorms[3 * T(node->index).findex + 1]; + model->normals[3 * numnormals + 2] = + model->facetnorms[3 * T(node->index).findex + 2]; + if (T(node->index).vindices[0] == i) + T(node->index).nindices[0] = numnormals; + else if (T(node->index).vindices[1] == i) + T(node->index).nindices[1] = numnormals; + else if (T(node->index).vindices[2] == i) + T(node->index).nindices[2] = numnormals; + numnormals++; + } + node = node->next; + } + } + + model->numnormals = numnormals - 1; + + /* free the member information */ + for (i = 1; i <= model->numvertices; i++) { + node = members[i]; + while (node) { + tail = node; + node = node->next; + free(tail); + } + } + free(members); + + /* pack the normals array (we previously allocated the maximum + number of normals that could possibly be created (numtriangles * + 3), so get rid of some of them (usually alot unless none of the + facet normals were averaged)) */ + normals = model->normals; + model->normals = (GLfloat*)malloc(sizeof(GLfloat)* 3* (model->numnormals+1)); + for (i = 1; i <= model->numnormals; i++) { + model->normals[3 * i + 0] = normals[3 * i + 0]; + model->normals[3 * i + 1] = normals[3 * i + 1]; + model->normals[3 * i + 2] = normals[3 * i + 2]; + } + free(normals); + + printf("glmVertexNormals(): %d normals generated\n", model->numnormals); +} + + +/* glmLinearTexture: Generates texture coordinates according to a + * linear projection of the texture map. It generates these by + * linearly mapping the vertices onto a square. + * + * model - pointer to initialized GLMmodel structure + */ +GLvoid +glmLinearTexture(GLMmodel* model) +{ + GLMgroup *group; + GLfloat dimensions[3]; + GLfloat x, y, scalefactor; + GLuint i; + + assert(model); + + if (model->texcoords) + free(model->texcoords); + model->numtexcoords = model->numvertices; + model->texcoords=(GLfloat*)malloc(sizeof(GLfloat)*2*(model->numtexcoords+1)); + + glmDimensions(model, dimensions); + scalefactor = 2.0f / + _glmAbs(_glmMax(_glmMax(dimensions[0], dimensions[1]), dimensions[2])); + + /* do the calculations */ + for(i = 1; i <= model->numvertices; i++) { + x = model->vertices[3 * i + 0] * scalefactor; + y = model->vertices[3 * i + 2] * scalefactor; + model->texcoords[2 * i + 0] = (x + 1.0f) / 2.0f; + model->texcoords[2 * i + 1] = (y + 1.0f) / 2.0f; + } + + /* go through and put texture coordinate indices in all the triangles */ + group = model->groups; + while(group) { + for(i = 0; i < group->numtriangles; i++) { + T(group->triangles[i]).tindices[0] = T(group->triangles[i]).vindices[0]; + T(group->triangles[i]).tindices[1] = T(group->triangles[i]).vindices[1]; + T(group->triangles[i]).tindices[2] = T(group->triangles[i]).vindices[2]; + } + group = group->next; + } + +#if 0 + printf("glmLinearTexture(): generated %d linear texture coordinates\n", + model->numtexcoords); +#endif +} + +/* glmSpheremapTexture: Generates texture coordinates according to a + * spherical projection of the texture map. Sometimes referred to as + * spheremap, or reflection map texture coordinates. It generates + * these by using the normal to calculate where that vertex would map + * onto a sphere. Since it is impossible to map something flat + * perfectly onto something spherical, there is distortion at the + * poles. This particular implementation causes the poles along the X + * axis to be distorted. + * + * model - pointer to initialized GLMmodel structure + */ +GLvoid +glmSpheremapTexture(GLMmodel* model) +{ + GLMgroup* group; + GLfloat theta, phi, rho, x, y, z, r; + GLuint i; + + assert(model); + assert(model->normals); + + if (model->texcoords) + free(model->texcoords); + model->numtexcoords = model->numnormals; + model->texcoords=(GLfloat*)malloc(sizeof(GLfloat)*2*(model->numtexcoords+1)); + + /* do the calculations */ + for (i = 1; i <= model->numnormals; i++) { + z = model->normals[3 * i + 0]; /* re-arrange for pole distortion */ + y = model->normals[3 * i + 1]; + x = model->normals[3 * i + 2]; + r = sqrtf((x * x) + (y * y)); + rho = sqrtf((r * r) + (z * z)); + + if(r == 0.0f) { + theta = 0.0f; + phi = 0.0f; + } else { + if(z == 0.0) + phi = 3.14159265f / 2.0f; + else + phi = acosf(z / rho); + +#if WE_DONT_NEED_THIS_CODE + if(x == 0.0) + theta = 3.14159265f / 2.0f; /* asin(y / r); */ + else + theta = acos(x / r); +#endif + + if(y == 0.0) + theta = 3.141592365f / 2.0f; /* acos(x / r); */ + else + theta = asinf(y / r) + 3.14159265f / 2.0f; + } + + model->texcoords[2 * i + 0] = theta / 3.14159265f; + model->texcoords[2 * i + 1] = phi / 3.14159265f; + } + + /* go through and put texcoord indices in all the triangles */ + group = model->groups; + while(group) { + for (i = 0; i < group->numtriangles; i++) { + T(group->triangles[i]).tindices[0] = T(group->triangles[i]).nindices[0]; + T(group->triangles[i]).tindices[1] = T(group->triangles[i]).nindices[1]; + T(group->triangles[i]).tindices[2] = T(group->triangles[i]).nindices[2]; + } + group = group->next; + } + +#if 0 + printf("glmSpheremapTexture(): generated %d spheremap texture coordinates\n", + model->numtexcoords); +#endif +} + +/* glmDelete: Deletes a GLMmodel structure. + * + * model - initialized GLMmodel structure + */ +GLvoid +glmDelete(GLMmodel* model) +{ + GLMgroup* group; + GLuint i; + + assert(model); + + if (model->pathname) free(model->pathname); + if (model->mtllibname) free(model->mtllibname); + if (model->vertices) free(model->vertices); + if (model->normals) free(model->normals); + if (model->texcoords) free(model->texcoords); + if (model->facetnorms) free(model->facetnorms); + if (model->triangles) free(model->triangles); + if (model->materials) { + for (i = 0; i < model->nummaterials; i++) + { + free(model->materials[i].name); + free(model->materials[i].textureName); + } + } + free(model->materials); + while(model->groups) { + group = model->groups; + model->groups = model->groups->next; + free(group->name); + free(group->triangles); + free(group); + } + + free(model); +} + +/* glmReadOBJ: Reads a model description from a Wavefront .OBJ file. + * Returns a pointer to the created object which should be free'd with + * glmDelete(). + * + * filename - name of the file containing the Wavefront .OBJ format data. + */ +GLMmodel* +glmReadOBJ(char* filename) +{ + GLMmodel* model; + FILE* file; + + /* open the file */ + file = fopen(filename, "r"); + if (!file) { + fprintf(stderr, "glmReadOBJ() failed: can't open data file \"%s\".\n", + filename); + //exit(1); + return NULL; + } + +#if 0 + /* announce the model name */ + printf("Model: %s\n", filename); +#endif + + /* allocate a new model */ + model = (GLMmodel*)malloc(sizeof(GLMmodel)); + model->pathname = strdup(filename); + model->mtllibname = NULL; + model->numvertices = 0; + model->vertices = NULL; + model->numnormals = 0; + model->normals = NULL; + model->numtexcoords = 0; + model->texcoords = NULL; + model->numfacetnorms = 0; + model->facetnorms = NULL; + model->numtriangles = 0; + model->triangles = NULL; + model->nummaterials = 0; + model->materials = NULL; + model->numgroups = 0; + model->groups = NULL; + model->position[0] = 0.0; + model->position[1] = 0.0; + model->position[2] = 0.0; + + /* make a first pass through the file to get a count of the number + of vertices, normals, texcoords & triangles */ + _glmFirstPass(model, file); + + /* allocate memory */ + model->vertices = (GLfloat*)malloc(sizeof(GLfloat) * + 3 * (model->numvertices + 1)); + model->triangles = (GLMtriangle*)malloc(sizeof(GLMtriangle) * + model->numtriangles); + if (model->numnormals) { + model->normals = (GLfloat*)malloc(sizeof(GLfloat) * + 3 * (model->numnormals + 1)); + } + if (model->numtexcoords) { + model->texcoords = (GLfloat*)malloc(sizeof(GLfloat) * + 2 * (model->numtexcoords + 1)); + } + + /* rewind to beginning of file and read in the data this pass */ + rewind(file); + + _glmSecondPass(model, file); + + /* close the file */ + fclose(file); + + return model; +} + +/* glmWriteOBJ: Writes a model description in Wavefront .OBJ format to + * a file. + * + * model - initialized GLMmodel structure + * filename - name of the file to write the Wavefront .OBJ format data to + * mode - a bitwise or of values describing what is written to the file + * GLM_NONE - render with only vertices + * GLM_FLAT - render with facet normals + * GLM_SMOOTH - render with vertex normals + * GLM_TEXTURE - render with texture coords + * GLM_COLOR - render with colors (color material) + * GLM_MATERIAL - render with materials + * GLM_COLOR and GLM_MATERIAL should not both be specified. + * GLM_FLAT and GLM_SMOOTH should not both be specified. + */ +GLvoid +glmWriteOBJ(GLMmodel* model, char* filename, GLuint mode) +{ + GLuint i; + FILE* file; + GLMgroup* group; + + assert(model); + + /* do a bit of warning */ + if (mode & GLM_FLAT && !model->facetnorms) { + printf("glmWriteOBJ() warning: flat normal output requested " + "with no facet normals defined.\n"); + mode &= ~GLM_FLAT; + } + if (mode & GLM_SMOOTH && !model->normals) { + printf("glmWriteOBJ() warning: smooth normal output requested " + "with no normals defined.\n"); + mode &= ~GLM_SMOOTH; + } + if (mode & GLM_TEXTURE && !model->texcoords) { + printf("glmWriteOBJ() warning: texture coordinate output requested " + "with no texture coordinates defined.\n"); + mode &= ~GLM_TEXTURE; + } + if (mode & GLM_FLAT && mode & GLM_SMOOTH) { + printf("glmWriteOBJ() warning: flat normal output requested " + "and smooth normal output requested (using smooth).\n"); + mode &= ~GLM_FLAT; + } + + /* open the file */ + file = fopen(filename, "w"); + if (!file) { + fprintf(stderr, "glmWriteOBJ() failed: can't open file \"%s\" to write.\n", + filename); + //exit(1); + return; + } + + /* spit out a header */ + fprintf(file, "# \n"); + fprintf(file, "# Wavefront OBJ generated by GLM library\n"); + fprintf(file, "# \n"); + fprintf(file, "# GLM library copyright (C) 1997 by Nate Robins\n"); + fprintf(file, "# email: ndr@pobox.com\n"); + fprintf(file, "# www: http://www.pobox.com/~ndr\n"); + fprintf(file, "# \n"); + + if (mode & GLM_MATERIAL && model->mtllibname) { + fprintf(file, "\nmtllib %s\n\n", model->mtllibname); + _glmWriteMTL(model, filename, model->mtllibname); + } + + /* spit out the vertices */ + fprintf(file, "\n"); + fprintf(file, "# %d vertices\n", model->numvertices); + for (i = 1; i <= model->numvertices; i++) { + fprintf(file, "v %f %f %f\n", + model->vertices[3 * i + 0], + model->vertices[3 * i + 1], + model->vertices[3 * i + 2]); + } + + /* spit out the smooth/flat normals */ + if (mode & GLM_SMOOTH) { + fprintf(file, "\n"); + fprintf(file, "# %d normals\n", model->numnormals); + for (i = 1; i <= model->numnormals; i++) { + fprintf(file, "vn %f %f %f\n", + model->normals[3 * i + 0], + model->normals[3 * i + 1], + model->normals[3 * i + 2]); + } + } else if (mode & GLM_FLAT) { + fprintf(file, "\n"); + fprintf(file, "# %d normals\n", model->numfacetnorms); + for (i = 1; i <= model->numnormals; i++) { + fprintf(file, "vn %f %f %f\n", + model->facetnorms[3 * i + 0], + model->facetnorms[3 * i + 1], + model->facetnorms[3 * i + 2]); + } + } + + /* spit out the texture coordinates */ + if (mode & GLM_TEXTURE) { + fprintf(file, "\n"); + fprintf(file, "# %d texcoords\n", model->numtexcoords); + for (i = 1; i <= model->numtexcoords; i++) { + fprintf(file, "vt %f %f\n", + model->texcoords[2 * i + 0], + model->texcoords[2 * i + 1]); + } + } + + fprintf(file, "\n"); + fprintf(file, "# %d groups\n", model->numgroups); + fprintf(file, "# %d faces (triangles)\n", model->numtriangles); + fprintf(file, "\n"); + + group = model->groups; + while(group) { + fprintf(file, "g %s\n", group->name); + if (mode & GLM_MATERIAL) + fprintf(file, "usemtl %s\n", model->materials[group->material].name); + for (i = 0; i < group->numtriangles; i++) { + if (mode & GLM_SMOOTH && mode & GLM_TEXTURE) { + fprintf(file, "f %d/%d/%d %d/%d/%d %d/%d/%d\n", + T(group->triangles[i]).vindices[0], + T(group->triangles[i]).nindices[0], + T(group->triangles[i]).tindices[0], + T(group->triangles[i]).vindices[1], + T(group->triangles[i]).nindices[1], + T(group->triangles[i]).tindices[1], + T(group->triangles[i]).vindices[2], + T(group->triangles[i]).nindices[2], + T(group->triangles[i]).tindices[2]); + } else if (mode & GLM_FLAT && mode & GLM_TEXTURE) { + fprintf(file, "f %d/%d %d/%d %d/%d\n", + T(group->triangles[i]).vindices[0], + T(group->triangles[i]).findex, + T(group->triangles[i]).vindices[1], + T(group->triangles[i]).findex, + T(group->triangles[i]).vindices[2], + T(group->triangles[i]).findex); + } else if (mode & GLM_TEXTURE) { + fprintf(file, "f %d/%d %d/%d %d/%d\n", + T(group->triangles[i]).vindices[0], + T(group->triangles[i]).tindices[0], + T(group->triangles[i]).vindices[1], + T(group->triangles[i]).tindices[1], + T(group->triangles[i]).vindices[2], + T(group->triangles[i]).tindices[2]); + } else if (mode & GLM_SMOOTH) { + fprintf(file, "f %d//%d %d//%d %d//%d\n", + T(group->triangles[i]).vindices[0], + T(group->triangles[i]).nindices[0], + T(group->triangles[i]).vindices[1], + T(group->triangles[i]).nindices[1], + T(group->triangles[i]).vindices[2], + T(group->triangles[i]).nindices[2]); + } else if (mode & GLM_FLAT) { + fprintf(file, "f %d//%d %d//%d %d//%d\n", + T(group->triangles[i]).vindices[0], + T(group->triangles[i]).findex, + T(group->triangles[i]).vindices[1], + T(group->triangles[i]).findex, + T(group->triangles[i]).vindices[2], + T(group->triangles[i]).findex); + } else { + fprintf(file, "f %d %d %d\n", + T(group->triangles[i]).vindices[0], + T(group->triangles[i]).vindices[1], + T(group->triangles[i]).vindices[2]); + } + } + fprintf(file, "\n"); + group = group->next; + } + + fclose(file); +} + +/* glmWeld: eliminate (weld) vectors that are within an epsilon of + * each other. + * + * model - initialized GLMmodel structure + * epsilon - maximum difference between vertices + * ( 0.00001 is a good start for a unitized model) + * + */ +GLvoid +glmWeld(GLMmodel* model, GLfloat epsilon) +{ + GLfloat* vectors; + GLfloat* copies; + GLuint numvectors; + GLuint i; + + /* vertices */ + numvectors = model->numvertices; + vectors = model->vertices; + copies = _glmWeldVectors(vectors, &numvectors, epsilon); + + printf("glmWeld(): %d redundant vertices.\n", + model->numvertices - numvectors - 1); + + for (i = 0; i < model->numtriangles; i++) { + T(i).vindices[0] = (GLuint)vectors[3 * T(i).vindices[0] + 0]; + T(i).vindices[1] = (GLuint)vectors[3 * T(i).vindices[1] + 0]; + T(i).vindices[2] = (GLuint)vectors[3 * T(i).vindices[2] + 0]; + } + + /* free space for old vertices */ + free(vectors); + + /* allocate space for the new vertices */ + model->numvertices = numvectors; + model->vertices = (GLfloat*)malloc(sizeof(GLfloat) * + 3 * (model->numvertices + 1)); + + /* copy the optimized vertices into the actual vertex list */ + for (i = 1; i <= model->numvertices; i++) { + model->vertices[3 * i + 0] = copies[3 * i + 0]; + model->vertices[3 * i + 1] = copies[3 * i + 1]; + model->vertices[3 * i + 2] = copies[3 * i + 2]; + } + + free(copies); +} + + +#if 0 + /* normals */ + if (model->numnormals) { + numvectors = model->numnormals; + vectors = model->normals; + copies = _glmOptimizeVectors(vectors, &numvectors); + + printf("glmOptimize(): %d redundant normals.\n", + model->numnormals - numvectors); + + for (i = 0; i < model->numtriangles; i++) { + T(i).nindices[0] = (GLuint)vectors[3 * T(i).nindices[0] + 0]; + T(i).nindices[1] = (GLuint)vectors[3 * T(i).nindices[1] + 0]; + T(i).nindices[2] = (GLuint)vectors[3 * T(i).nindices[2] + 0]; + } + + /* free space for old normals */ + free(vectors); + + /* allocate space for the new normals */ + model->numnormals = numvectors; + model->normals = (GLfloat*)malloc(sizeof(GLfloat) * + 3 * (model->numnormals + 1)); + + /* copy the optimized vertices into the actual vertex list */ + for (i = 1; i <= model->numnormals; i++) { + model->normals[3 * i + 0] = copies[3 * i + 0]; + model->normals[3 * i + 1] = copies[3 * i + 1]; + model->normals[3 * i + 2] = copies[3 * i + 2]; + } + + free(copies); + } + + /* texcoords */ + if (model->numtexcoords) { + numvectors = model->numtexcoords; + vectors = model->texcoords; + copies = _glmOptimizeVectors(vectors, &numvectors); + + printf("glmOptimize(): %d redundant texcoords.\n", + model->numtexcoords - numvectors); + + for (i = 0; i < model->numtriangles; i++) { + for (j = 0; j < 3; j++) { + T(i).tindices[j] = (GLuint)vectors[3 * T(i).tindices[j] + 0]; + } + } + + /* free space for old texcoords */ + free(vectors); + + /* allocate space for the new texcoords */ + model->numtexcoords = numvectors; + model->texcoords = (GLfloat*)malloc(sizeof(GLfloat) * + 2 * (model->numtexcoords + 1)); + + /* copy the optimized vertices into the actual vertex list */ + for (i = 1; i <= model->numtexcoords; i++) { + model->texcoords[2 * i + 0] = copies[2 * i + 0]; + model->texcoords[2 * i + 1] = copies[2 * i + 1]; + } + + free(copies); + } +#endif + +#if 0 + /* look for unused vertices */ + /* look for unused normals */ + /* look for unused texcoords */ + for (i = 1; i <= model->numvertices; i++) { + for (j = 0; j < model->numtriangles; i++) { + if (T(j).vindices[0] == i || + T(j).vindices[1] == i || + T(j).vindices[1] == i) + break; + } + } +#endif diff --git a/src/osgPlugins/obj/glm.h b/src/osgPlugins/obj/glm.h new file mode 100644 index 000000000..ffaa499bf --- /dev/null +++ b/src/osgPlugins/obj/glm.h @@ -0,0 +1,291 @@ +/* + * Wavefront .obj file format reader. + * + * author: Nate Robins + * email: ndr@pobox.com + * www: http://www.pobox.com/~ndr + */ + + +/* includes */ +/* #include "glut.h" */ +//#include +//#include + +// Replace about glu/glut calls with the more x-platform friendly osg version, +// also neither glu or glut were requied?! Only gl.h... even this I think +// should be removed since all the GLfloat etc could just as easily be floats. +// Will leave for now as it works... Robert Osfield, June 5th 2001. +#include + +#ifndef M_PI +#define M_PI 3.14159265 +#endif + + +/* defines */ +#define GLM_NONE (0) /* render with only vertices */ +#define GLM_FLAT (1 << 0) /* render with facet normals */ +#define GLM_SMOOTH (1 << 1) /* render with vertex normals */ +#define GLM_TEXTURE (1 << 2) /* render with texture coords */ +#define GLM_COLOR (1 << 3) /* render with colors */ +#define GLM_MATERIAL (1 << 4) /* render with materials */ + + +/* structs */ + +/* GLMmaterial: Structure that defines a material in a model. + */ +struct GLMmaterial +{ + char* name; /* name of material */ + GLfloat diffuse[4]; /* diffuse component */ + GLfloat ambient[4]; /* ambient component */ + GLfloat specular[4]; /* specular component */ + GLfloat emmissive[4]; /* emmissive component */ + GLfloat shininess; /* specular exponent */ + char* textureName; /* name of any attached texture, add by RO */ + bool textureReflection; /* true if texture is a reflection map */ + + void init() + { + name = NULL; + diffuse[0] = diffuse[1] = diffuse[2] = 0.8f; diffuse[3] = 1.0f; + ambient[0] = ambient[1] = ambient[2] = 0.2f; ambient[3] = 1.0f; + specular[0] = specular[1] = specular[2] = 0.0f; specular[3] = 1.0f; + emmissive[0] = emmissive[1] = emmissive[2] = 0.0f; emmissive[3] = 1.0f; + shininess = 0.0f; + textureName = NULL; + textureReflection = false; + } + +}; + +/* GLMtriangle: Structure that defines a triangle in a model. + */ +struct GLMtriangle { + GLuint vindices[3]; /* array of triangle vertex indices */ + GLuint nindices[3]; /* array of triangle normal indices */ + GLuint tindices[3]; /* array of triangle texcoord indices*/ + GLuint findex; /* index of triangle facet normal */ + void init() + { + vindices[0] = vindices[2] = vindices[2] = 0 ; + nindices[0] = nindices[2] = nindices[2] = 0 ; + tindices[0] = tindices[2] = tindices[2] = 0 ; + findex=0; + } +}; + +/* GLMgroup: Structure that defines a group in a model. + */ +struct GLMgroup { + char* name; /* name of this group */ + GLuint numtriangles; /* number of triangles in this group */ + GLuint* triangles; /* array of triangle indices */ + GLuint material; /* index to material for group */ + struct GLMgroup* next; /* pointer to next group in model */ + + void init() + { + name = NULL; + numtriangles = 0; + triangles = NULL; + material = 0; + next = NULL; + } +}; + +/* GLMmodel: Structure that defines a model. + */ +struct GLMmodel { + char* pathname; /* path to this model */ + char* mtllibname; /* name of the material library */ + + GLuint numvertices; /* number of vertices in model */ + GLfloat* vertices; /* array of vertices */ + + GLuint numnormals; /* number of normals in model */ + GLfloat* normals; /* array of normals */ + + GLuint numtexcoords; /* number of texcoords in model */ + GLfloat* texcoords; /* array of texture coordinates */ + + GLuint numfacetnorms; /* number of facetnorms in model */ + GLfloat* facetnorms; /* array of facetnorms */ + + GLuint numtriangles; /* number of triangles in model */ + GLMtriangle* triangles; /* array of triangles */ + + GLuint nummaterials; /* number of materials in model */ + GLMmaterial* materials; /* array of materials */ + + GLuint numgroups; /* number of groups in model */ + GLMgroup* groups; /* linked list of groups */ + + GLfloat position[3]; /* position of the model */ + + + void init() + { + pathname = NULL; + mtllibname = NULL; + + numvertices = 0; + vertices = NULL; + + numnormals = 0; + normals = NULL; + + numtexcoords = 0; + texcoords = NULL; + + numfacetnorms = 0; + facetnorms = NULL; + + numtriangles = 0; + triangles = NULL; + + nummaterials = 0; + materials = NULL; + + numgroups = 0; + groups = NULL; + + position[0] = position[1] = position[2] = 0.0f; + + } + +}; + + +/* public functions */ + +/* glmUnitize: "unitize" a model by translating it to the origin and + * scaling it to fit in a unit cube around the origin. Returns the + * scalefactor used. + * + * model - properly initialized GLMmodel structure + */ +GLfloat +glmUnitize(GLMmodel* model); + +/* glmDimensions: Calculates the dimensions (width, height, depth) of + * a model. + * + * model - initialized GLMmodel structure + * dimensions - array of 3 GLfloats (GLfloat dimensions[3]) + */ +GLvoid +glmDimensions(GLMmodel* model, GLfloat* dimensions); + +/* glmScale: Scales a model by a given amount. + * + * model - properly initialized GLMmodel structure + * scale - scalefactor (0.5 = half as large, 2.0 = twice as large) + */ +GLvoid +glmScale(GLMmodel* model, GLfloat scale); + +/* glmReverseWinding: Reverse the polygon winding for all polygons in + * this model. Default winding is counter-clockwise. Also changes + * the direction of the normals. + * + * model - properly initialized GLMmodel structure + */ +GLvoid +glmReverseWinding(GLMmodel* model); + +/* glmFacetNormals: Generates facet normals for a model (by taking the + * cross product of the two vectors derived from the sides of each + * triangle). Assumes a counter-clockwise winding. + * + * model - initialized GLMmodel structure + */ +GLvoid +glmFacetNormals(GLMmodel* model); + +/* glmVertexNormals: Generates smooth vertex normals for a model. + * First builds a list of all the triangles each vertex is in. Then + * loops through each vertex in the the list averaging all the facet + * normals of the triangles each vertex is in. Finally, sets the + * normal index in the triangle for the vertex to the generated smooth + * normal. If the dot product of a facet normal and the facet normal + * associated with the first triangle in the list of triangles the + * current vertex is in is greater than the cosine of the angle + * parameter to the function, that facet normal is not added into the + * average normal calculation and the corresponding vertex is given + * the facet normal. This tends to preserve hard edges. The angle to + * use depends on the model, but 90 degrees is usually a good start. + * + * model - initialized GLMmodel structure + * angle - maximum angle (in degrees) to smooth across + */ +GLvoid +glmVertexNormals(GLMmodel* model, GLfloat angle); + +/* glmLinearTexture: Generates texture coordinates according to a + * linear projection of the texture map. It generates these by + * linearly mapping the vertices onto a square. + * + * model - pointer to initialized GLMmodel structure + */ +GLvoid +glmLinearTexture(GLMmodel* model); + +/* glmSpheremapTexture: Generates texture coordinates according to a + * spherical projection of the texture map. Sometimes referred to as + * spheremap, or reflection map texture coordinates. It generates + * these by using the normal to calculate where that vertex would map + * onto a sphere. Since it is impossible to map something flat + * perfectly onto something spherical, there is distortion at the + * poles. This particular implementation causes the poles along the X + * axis to be distorted. + * + * model - pointer to initialized GLMmodel structure + */ +GLvoid +glmSpheremapTexture(GLMmodel* model); + +/* glmDelete: Deletes a GLMmodel structure. + * + * model - initialized GLMmodel structure + */ +GLvoid +glmDelete(GLMmodel* model); + +/* glmReadOBJ: Reads a model description from a Wavefront .OBJ file. + * Returns a pointer to the created object which should be free'd with + * glmDelete(). + * + * filename - name of the file containing the Wavefront .OBJ format data. + */ +GLMmodel* +glmReadOBJ(char* filename); + +/* glmWriteOBJ: Writes a model description in Wavefront .OBJ format to + * a file. + * + * model - initialized GLMmodel structure + * filename - name of the file to write the Wavefront .OBJ format data to + * mode - a bitwise or of values describing what is written to the file + * GLM_NONE - write only vertices + * GLM_FLAT - write facet normals + * GLM_SMOOTH - write vertex normals + * GLM_TEXTURE - write texture coords + * GLM_FLAT and GLM_SMOOTH should not both be specified. + */ +GLvoid +glmWriteOBJ(GLMmodel* model, char* filename, GLuint mode); + + +/* glmWeld: eliminate (weld) vectors that are within an epsilon of + * each other. + * + * model - initialized GLMmodel structure + * epsilon - maximum difference between vertices + * ( 0.00001 is a good start for a unitized model) + * + */ +GLvoid +glmWeld(GLMmodel* model, GLfloat epsilon); diff --git a/src/osgPlugins/obj/spec_obj.txt b/src/osgPlugins/obj/spec_obj.txt new file mode 100644 index 000000000..09b6e7205 --- /dev/null +++ b/src/osgPlugins/obj/spec_obj.txt @@ -0,0 +1,3013 @@ +B1. Object Files (.obj) + +Object files define the geometry and other properties for objects in +Wavefront's Advanced Visualizer. Object files can also be used to +transfer geometric data back and forth between the Advanced Visualizer +and other applications. + +Object files can be in ASCII format (.obj) or binary format (.mod). +This appendix describes the ASCII format for object files. These files +must have the extension .obj. + +In this release, the .obj file format supports both polygonal objects +and free-form objects. Polygonal geometry uses points, lines, and faces +to define objects while free-form geometry uses curves and surfaces. + +About this section + +The .obj appendix is for those who want to use the .obj format to +translate geometric data from other software applications to Wavefront +products. It also provides information for Advanced Visualizer users +who want detailed information on the Wavefront .obj file format. + +If you are a 2.11 user and want to understand the significance of the +3.0 release and how it affects your existing files, you may be +especially interested in the section called "Superseded statements" at +the end of the appendix. The section, "Patches and free-form surfaces," +gives examples of how 2.11 patches look in 3.0. + +How this section is organized + +Most of this appendix describes the different parts of an .obj file and +how those parts are arranged in the file. The three sections at the end +of the appendix provide background information on the 3.0 release of +the .obj format. + +The .obj appendix includes the following sections: + +o File structure + +o General statement + +o Vertex data + +o Specifying free-form curves/surfaces + +o Free-form curve/surface attributes + +o Elements + +o Free-form curve/surface body statements + +o Connectivity between free-form surfaces + +o Grouping + +o Display/render attributes + +o Comments + +o Mathematics for free-form curves/surfaces + +o Superseded statements + +o Patches and free-form surfaces + +--------------- + + The curve and surface extensions to the .obj file format were + developed in conjunction with mental images GmbH&Co.KG, Berlin, + Germany, as part of a joint development project to incorporate + free-form surfaces into Wavefront's Advanced Visualizer. + +File structure + +The following types of data may be included in an .obj file. In this +list, the keyword (in parentheses) follows the data type. + +Vertex data + +o geometric vertices (v) + +o texture vertices (vt) + +o vertex normals (vn) + +o parameter space vertices (vp) + Free-form curve/surface attributes + +o rational or non-rational forms of curve or surface type: + basis matrix, Bezier, B-spline, Cardinal, Taylor (cstype) + +o degree (deg) + +o basis matrix (bmat) + +o step size (step) + +Elements + +o point (p) + +o line (l) + +o face (f) + +o curve (curv) + +o 2D curve (curv2) + +o surface (surf) + +Free-form curve/surface body statements + +o parameter values (parm) + +o outer trimming loop (trim) + +o inner trimming loop (hole) + +o special curve (scrv) + +o special point (sp) + +o end statement (end) + +Connectivity between free-form surfaces + + +o connect (con) + +Grouping + +o group name (g) + +o smoothing group (s) + +o merging group (mg) + +o object name (o) + +Display/render attributes + +o bevel interpolation (bevel) + +o color interpolation (c_interp) + +o dissolve interpolation (d_interp) + +o level of detail (lod) + +o material name (usemtl) + +o material library (mtllib) + +o shadow casting (shadow_obj) + +o ray tracing (trace_obj) + +o curve approximation technique (ctech) + +o surface approximation technique (stech) + + +The following diagram shows how these parts fit together in a typical +.obj file. + +Figure B1-1. Typical .obj file structure + +General statement + +call filename.ext arg1 arg2 . . . + + Reads the contents of the specified .obj or .mod file at this + location. The call statement can be inserted into .obj files using + a text editor. + + filename.ext is the name of the .obj or .mod file to be read. You + must include the extension with the filename. + + arg1 arg2 . . . specifies a series of optional integer arguments + that are passed to the called file. There is no limit to the number + of nested calls that can be made. + + Arguments passed to the called file are substituted in the same way + as in UNIX scripts; for example, $1 in the called file is replaced + by arg1, $2 in the called file is replaced by arg2, and so on. + + If the frame number is needed in the called file for variable + substitution, "$1" must be used as the first argument in the call + statement. For example: + + call filename.obj $1 + + Then the statement in the called file, + + scmp filename.pv $1 + + will work as expected. For more information on the scmp statement, + see appendix C, Variable Substitution for more information. + + Another method to do the same thing is: + + scmp filename.pv $1 + + call filename.obj + + Using this method, the scmp statement provides the .pv file for all + subsequently called .obj or .mod files. + +csh command + +csh -command + + Executes the requested UNIX command. If the UNIX command returns an + error, the parser flags an error during parsing. + + If a dash (-) precedes the UNIX command, the error is ignored. + + command is the UNIX command. + +Vertex data + +Vertex data provides coordinates for: + +o geometric vertices + +o texture vertices + +o vertex normals + +For free-form objects, the vertex data also provides: + +o parameter space vertices + +The vertex data is represented by four vertex lists; one for each type +of vertex coordinate. A right-hand coordinate system is used to specify +the coordinate locations. + +The following sample is a portion of an .obj file that contains the +four types of vertex information. + + v -5.000000 5.000000 0.000000 + v -5.000000 -5.000000 0.000000 + v 5.000000 -5.000000 0.000000 + v 5.000000 5.000000 0.000000 + vt -5.000000 5.000000 0.000000 + vt -5.000000 -5.000000 0.000000 + vt 5.000000 -5.000000 0.000000 + vt 5.000000 5.000000 0.000000 + vn 0.000000 0.000000 1.000000 + vn 0.000000 0.000000 1.000000 + vn 0.000000 0.000000 1.000000 + vn 0.000000 0.000000 1.000000 + vp 0.210000 3.590000 + vp 0.000000 0.000000 + vp 1.000000 0.000000 + vp 0.500000 0.500000 + + + +When vertices are loaded into the Advanced Visualizer, they are +sequentially numbered, starting with 1. These reference numbers are +used in element statements. + +Syntax + +The following syntax statements are listed in order of complexity. + +v x y z w + + Polygonal and free-form geometry statement. + + Specifies a geometric vertex and its x y z coordinates. Rational + curves and surfaces require a fourth homogeneous coordinate, also + called the weight. + + x y z are the x, y, and z coordinates for the vertex. These are + floating point numbers that define the position of the vertex in + three dimensions. + + w is the weight required for rational curves and surfaces. It is + not required for non-rational curves and surfaces. If you do not + specify a value for w, the default is 1.0. + + NOTE: A positive weight value is recommended. Using zero or + negative values may result in an undefined point in a curve or + surface. + +vp u v w + + Free-form geometry statement. + + Specifies a point in the parameter space of a curve or surface. + + The usage determines how many coordinates are required. Special + points for curves require a 1D control point (u only) in the + parameter space of the curve. Special points for surfaces require a + 2D point (u and v) in the parameter space of the surface. Control + points for non-rational trimming curves require u and v + coordinates. Control points for rational trimming curves require u, + v, and w (weight) coordinates. + + u is the point in the parameter space of a curve or the first + coordinate in the parameter space of a surface. + + v is the second coordinate in the parameter space of a surface. + + w is the weight required for rational trimming curves. If you do + not specify a value for w, it defaults to 1.0. + + NOTE: For additional information on parameter vertices, see the + curv2 and sp statements + +vn i j k + + Polygonal and free-form geometry statement. + + Specifies a normal vector with components i, j, and k. + + Vertex normals affect the smooth-shading and rendering of geometry. + For polygons, vertex normals are used in place of the actual facet + normals. For surfaces, vertex normals are interpolated over the + entire surface and replace the actual analytic surface normal. + + When vertex normals are present, they supersede smoothing groups. + + i j k are the i, j, and k coordinates for the vertex normal. They + are floating point numbers. + +vt u v w + + Vertex statement for both polygonal and free-form geometry. + + Specifies a texture vertex and its coordinates. A 1D texture + requires only u texture coordinates, a 2D texture requires both u + and v texture coordinates, and a 3D texture requires all three + coordinates. + + u is the value for the horizontal direction of the texture. + + v is an optional argument. + + v is the value for the vertical direction of the texture. The + default is 0. + + w is an optional argument. + + w is a value for the depth of the texture. The default is 0. + +Specifying free-form curves/surfaces + +There are three steps involved in specifying a free-form curve or +surface element. + +o Specify the type of curve or surface (basis matrix, Bezier, + B-spline, Cardinal, or Taylor) using free-form curve/surface + attributes. + +o Describe the curve or surface with element statements. + +o Supply additional information, using free-form curve/surface + body statements + +The next three sections of this appendix provide detailed information +on each of these steps. + +Data requirements for curves and surfaces + +All curves and surfaces require a certain set of data. This consists of +the following: + +Free-form curve/surface attributes + +o All curves and surfaces require type data, which is given with + the cstype statement. + +o All curves and surfaces require degree data, which is given + with the deg statement. + +o Basis matrix curves or surfaces require a bmat statement. + +o Basis matrix curves or surfaces also require a step size, which + is given with the step statement. + +Elements + +o All curves and surfaces require control points, which are + referenced in the curv, curv2, or surf statements. + +o 3D curves and surfaces require a parameter range, which is + given in the curv and surf statements, respectively. + +Free-form curve/surface body statements + +o All curves and surfaces require a set of global parameters or a + knot vector, both of which are given with the parm statement. + +o All curves and surfaces body statements require an explicit end + statement. + +Error checks + +The above set of data starts out empty with no default values when +reading of an .obj file begins. While the file is being read, +statements are encountered, information is accumulated, and some errors +may be reported. + +When the end statement is encountered, the following error checks, +which involve consistency between various statements, are performed: + +o All required information is present. + +o The number of control points, number of parameter values + (knots), and degree are consistent with the curve or surface + type. If the type is bmatrix, the step size is also consistent. + (For more information, refer to the parameter vector equations + in the section, "Mathematics of free-form curves/ surfaces" at + the end of appendix B1.) + +o If the type is bmatrix and the degree is n, the size of the + basis matrix is (n + 1) x (n + 1). + +Note that any information given by the state-setting statements remains +in effect from one curve or surface to the next. Information given +within a curve or surface body is only effective for the curve or +surface it is given with. + + + +Free-form curve/surface attributes + +Five types of free-form geometry are available in the .obj file +format: + +o Bezier + +o basis matrix + +o B-spline + +o Cardinal + +o Taylor + +You can apply these types only to curves and surfaces. Each of these +five types can be rational or non-rational. + +In addition to specifying the type, you must define the degree for the +curve or surface. For basis matrix curve and surface elements, you must +also specify the basis matrix and step size. + +All free-form curve and surface attribute statements are state-setting. +This means that once an attribute statement is set, it applies to all +elements that follow until it is reset to a different value. + +Syntax + +The following syntax statements are listed in order of use. + +cstype rat type + + Free-form geometry statement. + + Specifies the type of curve or surface and indicates a rational or + non-rational form. + + rat is an optional argument. + + rat specifies a rational form for the curve or surface type. If rat + is not included, the curve or surface is non-rational + + type specifies the curve or surface type. Allowed types are: + + bmatrix basis matrix + + bezier Bezier + + bspline B-spline + + cardinal Cardinal + + taylor Taylor + + There is no default. A value must be supplied. + +deg degu degv + + Free-form geometry statement. + + Sets the polynomial degree for curves and surfaces. + + degu is the degree in the u direction. It is required for both + curves and surfaces. + + degv is the degree in the v direction. It is required only for + surfaces. For Bezier, B-spline, Taylor, and basis matrix, there is + no default; a value must be supplied. For Cardinal, the degree is + always 3. If some other value is given for Cardinal, it will be + ignored. + +bmat u matrix + +bmat v matrix + + Free-form geometry statement. + + Sets the basis matrices used for basis matrix curves and surfaces. + The u and v values must be specified in separate bmat statements. + + NOTE: The deg statement must be given before the bmat statements + and the size of the matrix must be appropriate for the degree. + + u specifies that the basis matrix is applied in the u direction. + + v specifies that the basis matrix is applied in the v direction. + + matrix lists the contents of the basis matrix with column subscript + j varying the fastest. If n is the degree in the given u or v + direction, the matrix (i,j) should be of size (n + 1) x (n + 1). + + There is no default. A value must be supplied. + + NOTE: The arrangement of the matrix is different from that commonly + found in other references. For more information, see the examples + at the end of this section and also the section, "Mathematics for + free-form curves and surfaces." + +step stepu stepv + + Free-form geometry statement. + + Sets the step size for curves and surfaces that use a basis + matrix. + + stepu is the step size in the u direction. It is required for both + curves and surfaces that use a basis matrix. + + stepv is the step size in the v direction. It is required only for + surfaces that use a basis matrix. There is no default. A value must + be supplied. + + When a curve or surface is being evaluated and a transition from + one segment or patch to the next occurs, the set of control points + used is incremented by the step size. The appropriate step size + depends on the representation type, which is expressed through the + basis matrix, and on the degree. + + That is, suppose we are given a curve with k control points: + {v , ... v } + 1 k + + If the curve is of degree n, then n + 1 control points are needed + for each polynomial segment. If the step size is given as s, then + the ith polynomial segment, where i = 0 is the first segment, will + use the control points: + {v ,...,v } + is+1 is+n+1 + + For example, for Bezier curves, s = n . + + For surfaces, the above description applies independently to each + parametric direction. + + When you create a file which uses the basis matrix type, be sure to + specify a step size appropriate for the current curve or surface + representation. + +Examples + +1. Cubic Bezier surface made with a basis matrix + + To create a cubic Bezier surface: + + cstype bmatrix + deg 3 3 + step 3 3 + bmat u 1 -3 3 -1 \ + 0 3 -6 3 \ + 0 0 3 -3 \ + 0 0 0 1 + bmat v 1 -3 3 -1 \ + 0 3 -6 3 \ + 0 0 3 -3 \ + 0 0 0 1 + +2. Hermite curve made with a basis matrix + + To create a Hermite curve: + + cstype bmatrix + deg 3 + step 2 + bmat u 1 0 -3 2 0 0 3 -2 \ + 0 1 -2 1 0 0 -1 1 + +3. Bezier in u direction with B-spline in v direction; + made with a basis matrix + + To create a surface with a cubic Bezier in the u direction and + cubic uniform B-spline in the v direction: + + cstype bmatrix + deg 3 3 + step 3 1 + bmat u 1 -3 3 -1 \ + 0 3 -6 3 \ + 0 0 3 -3 \ + 0 0 0 1 + bmat v 0.16666 -0.50000 0.50000 -0.16666 \ + 0.66666 0.00000 -1.00000 0.50000 \ + 0.16666 0.50000 0.50000 -0.50000 \ + 0.00000 0.00000 0.00000 0.16666 + + + +Elements + +For polygonal geometry, the element types available in the .obj file +are: + +o points + +o lines + +o faces + +For free-form geometry, the element types available in the .obj file +are: + +o curve + +o 2D curve on a surface + +o surface + +All elements can be freely intermixed in the file. + +Referencing vertex data + +For all elements, reference numbers are used to identify geometric +vertices, texture vertices, vertex normals, and parameter space +vertices. + +Each of these types of vertices is numbered separately, starting with +1. This means that the first geometric vertex in the file is 1, the +second is 2, and so on. The first texture vertex in the file is 1, the +second is 2, and so on. The numbering continues sequentially throughout +the entire file. Frequently, files have multiple lists of vertex data. +This numbering sequence continues even when vertex data is separated by +other data. + +In addition to counting vertices down from the top of the first list in +the file, you can also count vertices back up the list from an +element's position in the file. When you count up the list from an +element, the reference numbers are negative. A reference number of -1 +indicates the vertex immediately above the element. A reference number +of -2 indicates two references above and so on. + +Referencing groups of vertices + +Some elements, such as faces and surfaces, may have a triplet of +numbers that reference vertex data.These numbers are the reference +numbers for a geometric vertex, a texture vertex, and a vertex normal. + +Each triplet of numbers specifies a geometric vertex, texture vertex, +and vertex normal. The reference numbers must be in order and must +separated by slashes (/). + +o The first reference number is the geometric vertex. + +o The second reference number is the texture vertex. It follows + the first slash. + +o The third reference number is the vertex normal. It follows the + second slash. + +There is no space between numbers and the slashes. There may be more +than one series of geometric vertex/texture vertex/vertex normal +numbers on a line. + +The following is a portion of a sample file for a four-sided face +element: + + f 1/1/1 2/2/2 3/3/3 4/4/4 + +Using v, vt, and vn to represent geometric vertices, texture vertices, +and vertex normals, the statement would read: + + f v/vt/vn v/vt/vn v/vt/vn v/vt/vn + +If there are only vertices and vertex normals for a face element (no +texture vertices), you would enter two slashes (//). For example, to +specify only the vertex and vertex normal reference numbers, you would +enter: + + f 1//1 2//2 3//3 4//4 + +When you are using a series of triplets, you must be consistent in the +way you reference the vertex data. For example, it is illegal to give +vertex normals for some vertices, but not all. + +The following is an example of an illegal statement. + + f 1/1/1 2/2/2 3//3 4//4 + +Syntax + +The following syntax statements are listed in order of complexity of +geometry. + +p v1 v2 v3 . . . + + Polygonal geometry statement. + + Specifies a point element and its vertex. You can specify multiple + points with this statement. Although points cannot be shaded or + rendered, they are used by other Advanced Visualizer programs. + + v is the vertex reference number for a point element. Each point + element requires one vertex. Positive values indicate absolute + vertex numbers. Negative values indicate relative vertex numbers. + +l v1/vt1 v2/vt2 v3/vt3 . . . + + Polygonal geometry statement. + + Specifies a line and its vertex reference numbers. You can + optionally include the texture vertex reference numbers. Although + lines cannot be shaded or rendered, they are used by other Advanced + Visualizer programs. + + The reference numbers for the vertices and texture vertices must be + separated by a slash (/). There is no space between the number and + the slash. + + v is a reference number for a vertex on the line. A minimum of two + vertex numbers are required. There is no limit on the maximum. + Positive values indicate absolute vertex numbers. Negative values + indicate relative vertex numbers. + + vt is an optional argument. + + vt is the reference number for a texture vertex in the line + element. It must always follow the first slash. + +f v1/vt1/vn1 v2/vt2/vn2 v3/vt3/vn3 . . . + + Polygonal geometry statement. + + Specifies a face element and its vertex reference number. You can + optionally include the texture vertex and vertex normal reference + numbers. + + The reference numbers for the vertices, texture vertices, and + vertex normals must be separated by slashes (/). There is no space + between the number and the slash. + + v is the reference number for a vertex in the face element. A + minimum of three vertices are required. + + vt is an optional argument. + + vt is the reference number for a texture vertex in the face + element. It always follows the first slash. + + vn is an optional argument. + + vn is the reference number for a vertex normal in the face element. + It must always follow the second slash. + + Face elements use surface normals to indicate their orientation. If + vertices are ordered counterclockwise around the face, both the + face and the normal will point toward the viewer. If the vertex + ordering is clockwise, both will point away from the viewer. If + vertex normals are assigned, they should point in the general + direction of the surface normal, otherwise unpredictable results + may occur. + + If a face has a texture map assigned to it and no texture vertices + are assigned in the f statement, the texture map is ignored when + the element is rendered. + + NOTE: Any references to fo (face outline) are no longer valid as of + version 2.11. You can use f (face) to get the same results. + References to fo in existing .obj files will still be read, + however, they will be written out as f when the file is saved. + +curv u0 u1 v1 v2 . . . + + Element statement for free-form geometry. + + Specifies a curve, its parameter range, and its control vertices. + Although curves cannot be shaded or rendered, they are used by + other Advanced Visualizer programs. + + u0 is the starting parameter value for the curve. This is a + floating point number. + + u1 is the ending parameter value for the curve. This is a floating + point number. + + v is the vertex reference number for a control point. You can + specify multiple control points. A minimum of two control points + are required for a curve. + + For a non-rational curve, the control points must be 3D. For a + rational curve, the control points are 3D or 4D. The fourth + coordinate (weight) defaults to 1.0 if omitted. + +curv2 vp1 vp2 vp3. . . + + Free-form geometry statement. + + Specifies a 2D curve on a surface and its control points. A 2D + curve is used as an outer or inner trimming curve, as a special + curve, or for connectivity. + + vp is the parameter vertex reference number for the control point. + You can specify multiple control points. A minimum of two control + points is required for a 2D curve. + + The control points are parameter vertices because the curve must + lie in the parameter space of some surface. For a non-rational + curve, the control vertices can be 2D. For a rational curve, the + control vertices can be 2D or 3D. The third coordinate (weight) + defaults to 1.0 if omitted. + +surf s0 s1 t0 t1 v1/vt1/vn1 v2/vt2/vn2 . . . + + Element statement for free-form geometry. + + Specifies a surface, its parameter range, and its control vertices. + The surface is evaluated within the global parameter range from s0 + to s1 in the u direction and t0 to t1 in the v direction. + + s0 is the starting parameter value for the surface in the u + direction. + + s1 is the ending parameter value for the surface in the u + direction. + + t0 is the starting parameter value for the surface in the v + direction. + + t1 is the ending parameter value for the surface in the v + direction. + + v is the reference number for a control vertex in the surface. + + vt is an optional argument. + + vt is the reference number for a texture vertex in the surface. It + must always follow the first slash. + + vn is an optional argument. + + vn is the reference number for a vertex normal in the surface. It + must always follow the second slash. + + For a non-rational surface, the control vertices are 3D. For a + rational surface the control vertices can be 3D or 4D. The fourth + coordinate (weight) defaults to 1.0 if ommitted. + + NOTE: For more information on the ordering of control points for + survaces, refer to the section on surfaces and control points in + "mathematics of free-form curves/surfaces" at the end of this + appendix. + + + + +Examples + +These are examples for polygonal geometry. + +For examples using free-form geometry, see the examples at the end of +the next section, "Free-form curve/surface body statements." + +1. Square + +This example shows a square that measures two units on each side and +faces in the positive direction (toward the camera). Note that the +ordering of the vertices is counterclockwise. This ordering determines +that the square is facing forward. + + v 0.000000 2.000000 0.000000 + v 0.000000 0.000000 0.000000 + v 2.000000 0.000000 0.000000 + v 2.000000 2.000000 0.000000 + f 1 2 3 4 + +2. Cube + +This is a cube that measures two units on each side. Each vertex is +shared by three different faces. + + v 0.000000 2.000000 2.000000 + v 0.000000 0.000000 2.000000 + v 2.000000 0.000000 2.000000 + v 2.000000 2.000000 2.000000 + v 0.000000 2.000000 0.000000 + v 0.000000 0.000000 0.000000 + v 2.000000 0.000000 0.000000 + v 2.000000 2.000000 0.000000 + f 1 2 3 4 + f 8 7 6 5 + f 4 3 7 8 + f 5 1 4 8 + f 5 6 2 1 + f 2 6 7 3 + +3. Cube with negative reference numbers + +This is a cube with negative vertex reference numbers. Each element +references the vertices stored immediately above it in the file. Note +that vertices are not shared. + +v 0.000000 2.000000 2.000000 +v 0.000000 0.000000 2.000000 +v 2.000000 0.000000 2.000000 +v 2.000000 2.000000 2.000000 +f -4 -3 -2 -1 + +v 2.000000 2.000000 0.000000 +v 2.000000 0.000000 0.000000 +v 0.000000 0.000000 0.000000 +v 0.000000 2.000000 0.000000 +f -4 -3 -2 -1 + +v 2.000000 2.000000 2.000000 +v 2.000000 0.000000 2.000000 +v 2.000000 0.000000 0.000000 +v 2.000000 2.000000 0.000000 +f -4 -3 -2 -1 + +v 0.000000 2.000000 0.000000 +v 0.000000 2.000000 2.000000 +v 2.000000 2.000000 2.000000 +v 2.000000 2.000000 0.000000 +f -4 -3 -2 -1 + +v 0.000000 2.000000 0.000000 +v 0.000000 0.000000 0.000000 +v 0.000000 0.000000 2.000000 +v 0.000000 2.000000 2.000000 +f -4 -3 -2 -1 + +v 0.000000 0.000000 2.000000 +v 0.000000 0.000000 0.000000 +v 2.000000 0.000000 0.000000 +v 2.000000 0.000000 2.000000 +f -4 -3 -2 -1 + + + +Free-form curve/surface body statements + +You can specify additional information for free-form curve and surface +elements using a series of statements called body statements. The +series is concluded by an end statement. + +Body statements are valid only when they appear between the free-form +element statement (curv, curv2, surf) and the end statement. If they +are anywhere else in the .obj file, they do not have any effect. + +You can use body statements to specify the following values: + +o parameter + +o knot vector + +o trimming loop + +o hole + +o special curve + +o special point + +You cannot use any other statements between the free-form curve or +surface statement and the end statement. Using any other of type of +statement may cause unpredictable results. + +This portion of a sample file shows the knot vector values for a +rational B-spline surface with a trimming loop. Notice the end +statement to conclude the body statements. + + cstype rat bspline + deg 2 2 + surf -1.0 2.5 -2.0 2.0 -9 -8 -7 -6 -5 -4 -3 -2 -1 + parm u -1.00 -1.00 -1.00 2.50 2.50 2.50 + parm v -2.00 -2.00 -2.00 -2.00 -2.00 -2.00 + trim 0.0 2.0 1 + end + +Parameter values and knot vectors + +All curve and surface elements require a set of parameter values. + +For polynomial curves and surfaces, this specifies global parameter +values. For B-spline curves and surfaces, this specifies the knot +vectors. + +For surfaces, the parameter values must be specified for both the u and +v directions. For curves, the parameter values must be specified for +only the u direction. + +If multiple parameter value statements for the same parametric +direction are used inside a single curve or surface body, the last +statement is used. + +Trimming loops and holes + +The trimming loop statement builds a single outer trimming loop as a +sequence of curves which lie on a given surface. + +The hole statement builds a single inner trimming loop as a sequence of +curves which lie on a given surface. The inner loop creates a hole. + +The curves are referenced by number in the same way vertices are +referenced by face elements. + +The individual curves must lie end-to-end to form a closed loop which +does not intersect itself and which lies within the parameter range +specified for the surface. The loop as a whole may be oriented in +either direction (clockwise or counterclockwise). + +To cut one or more holes in a region, use a trim statement followed by +one or more hole statements. To introduce another trimmed region in the +same surface, use another trim statement followed by one or more hole +statements. The ordering that associates holes and the regions they cut +is important and must be maintained. + +If the first trim statement in the sequence is omitted, the enclosing +outer trimming loop is taken to be the parameter range of the surface. +If no trim or hole statements are specified, then the surface is +trimmed at its parameter range. + +This portion of a sample file shows a non-rational Bezier surface with +two regions, each with a single hole: + + cstype bezier + deg 1 1 + surf 0.0 2.0 0.0 2.0 1 2 3 4 + parm u 0.00 2.00 + parm v 0.00 2.00 + trim 0.0 4.0 1 + hole 0.0 4.0 2 + trim 0.0 4.0 3 + hole 0.0 4.0 4 + end + +Special curve + +A special curve statement builds a single special curve as a sequence +of curves which lie on a given surface. + +The curves are referenced by number in the same way vertices are +referenced by face elements. + +A special curve is guaranteed to be included in any triangulation of +the surface. This means that the line formed by approximating the +special curve with a sequence of straight line segments will actually +appear as a sequence of triangle edges in the final triangulation. + +Special point + +A special point statement specifies that special geometric points are +to be associated with a curve or surface. For space curves and trimming +curves, the parameter vertices must be 1D. For surfaces, the parameter +vertices must be 2D. + +These special points will be included in any linear approximation of +the curve or surface. + +For space curves, this means that the point corresponding to the given +curve parameter is included as one of the vertices in an approximation +consisting of a sequence of line segments. + +For surfaces, this means that the point corresponding to the given +surface parameters is included as a triangle vertex in the +triangulation. + +For trimming curves, the treatment is slightly different: a special +point on a trimming curve is essentially the same as a special point on +the surface it trims. + +The following portion of a sample files shows special points for a +rational Bezier 2D curve on a surface. + + vp -0.675 1.850 3.000 + vp 0.915 1.930 + vp 2.485 0.470 2.000 + vp 2.485 -1.030 + vp 1.605 -1.890 10.700 + vp -0.745 -0.654 0.500 + cstype rat bezier + curv2 -6 -5 -4 -3 -2 -1 -6 + parm u 0.00 1.00 2.00 + sp 2 3 + end + +Syntax + +The following syntax statement are listed in order of normal use. + +parm u p1 p2 p3. . . + +parm v p1 p2 p3 . . . + + Body statement for free-form geometry. + + Specifies global parameter values. For B-spline curves and + surfaces, this specifies the knot vectors. + + u is the u direction for the parameter values. + + v is the v direction for the parameter values. + + To set u and v values, use separate command lines. + + p is the global parameter or knot value. You can specify multiple + values. A minimum of two parameter values are required. Parameter + values must increase monotonically. The type of surface and the + degree dictate the number of values required. + +trim u0 u1 curv2d u0 u1 curv2d . . . + + Body statement for free-form geometry. + + Specifies a sequence of curves to build a single outer trimming + loop. + + u0 is the starting parameter value for the trimming curve curv2d. + + u1 is the ending parameter value for the trimming curve curv2d. + + curv2d is the index of the trimming curve lying in the parameter + space of the surface. This curve must have been previously defined + with the curv2 statement. + +hole u0 u1 curv2d u0 u1 curv2d . . . + + Body statement for free-form geometry. + + Specifies a sequence of curves to build a single inner trimming + loop (hole). + + u0 is the starting parameter value for the trimming curve curv2d. + + u1 is the ending parameter value for the trimming curve curv2d. + + curv2d is the index of the trimming curve lying in the parameter + space of the surface. This curve must have been previously defined + with the curv2 statement. + +scrv u0 u1 curv2d u0 u1 curv2d . . . + + Body statement for free-form geometry. + + Specifies a sequence of curves which lie on the given surface to + build a single special curve. + + u0 is the starting parameter value for the special curve curv2d. + + u1 is the ending parameter value for the special curve curv2d. + + curv2d is the index of the special curve lying in the parameter + space of the surface. This curve must have been previously defined + with the curv2 statement. + +sp vp1 vp. . . + + Body statement for free-form geometry. + + Specifies special geometric points to be associated with a curve or + surface. For space curves and trimming curves, the parameter + vertices must be 1D. For surfaces, the parameter vertices must be + 2D. + + vp is the reference number for the parameter vertex of a special + point to be associated with the parameter space point of the curve + or surface. + +end + + Body statement for free-form geometry. + + Specifies the end of a curve or surface body begun by a curv, + curv2, or surf statement. + +Examples + +1. Taylor curve + + For creating a single-segment Taylor polynomial curve of the form: + + 2 3 4 + x = 3.00 + 2.30t + 7.98t + 8.30t + 6.34t + + 2 3 4 + y = 1.00 - 10.10t + 5.40t - 4.70t + 2.03t + + 2 3 4 + z = -2.50 + 0.50t - 7.00t + 18.10t + 0.08t + + +and evaluated between the global parameters 0.5 and 1.6: + + v 3.000 1.000 -2.500 + v 2.300 -10.100 0.500 + v 7.980 5.400 -7.000 + v 8.300 -4.700 18.100 + v 6.340 2.030 0.080 + cstype taylor + deg 4 + curv 0.500 1.600 1 2 3 4 5 + parm u 0.000 2.000 + end + +2. Bezier curve + +This example shows a non-rational Bezier curve with 13 control points. + + v -2.300000 1.950000 0.000000 + v -2.200000 0.790000 0.000000 + v -2.340000 -1.510000 0.000000 + v -1.530000 -1.490000 0.000000 + v -0.720000 -1.470000 0.000000 + v -0.780000 0.230000 0.000000 + v 0.070000 0.250000 0.000000 + v 0.920000 0.270000 0.000000 + v 0.800000 -1.610000 0.000000 + v 1.620000 -1.590000 0.000000 + v 2.440000 -1.570000 0.000000 + v 2.690000 0.670000 0.000000 + v 2.900000 1.980000 0.000000 + # 13 vertices + + cstype bezier + ctech cparm 1.000000 + deg 3 + curv 0.000000 4.000000 1 2 3 4 5 6 7 8 9 10 \ + 11 12 13 + parm u 0.000000 1.000000 2.000000 3.000000 \ + 4.000000 + end + # 1 element + + + +3. B-spline surface + +This is an example of a cubic B-spline surface. + + g bspatch + v -5.000000 -5.000000 -7.808327 + v -5.000000 -1.666667 -7.808327 + v -5.000000 1.666667 -7.808327 + v -5.000000 5.000000 -7.808327 + v -1.666667 -5.000000 -7.808327 + v -1.666667 -1.666667 11.977780 + v -1.666667 1.666667 11.977780 + v -1.666667 5.000000 -7.808327 + v 1.666667 -5.000000 -7.808327 + v 1.666667 -1.666667 11.977780 + v 1.666667 1.666667 11.977780 + v 1.666667 5.000000 -7.808327 + v 5.000000 -5.000000 -7.808327 + v 5.000000 -1.666667 -7.808327 + v 5.000000 1.666667 -7.808327 + v 5.000000 5.000000 -7.808327 + # 16 vertices + + cstype bspline + stech curv 0.5 10.000000 + deg 3 3 + 8surf 0.000000 1.000000 0.000000 1.000000 13 14 \ 15 16 9 10 11 12 5 6 + 7 8 1 2 3 4 + parm u -3.000000 -2.000000 -1.000000 0.000000 \ + 1.000000 2.000000 3.000000 4.000000 + parm v -3.000000 -2.000000 -1.000000 0.000000 \ + 1.000000 2.000000 3.000000 4.000000 + end + # 1 element + + +4. Cardinal surface + +This example shows a Cardinal surface. + + v -5.000000 -5.000000 0.000000 + v -5.000000 -1.666667 0.000000 + v -5.000000 1.666667 0.000000 + v -5.000000 5.000000 0.000000 + v -1.666667 -5.000000 0.000000 + v -1.666667 -1.666667 0.000000 + v -1.666667 1.666667 0.000000 + v -1.666667 5.000000 0.000000 + v 1.666667 -5.000000 0.000000 + v 1.666667 -1.666667 0.000000 + v 1.666667 1.666667 0.000000 + v 1.666667 5.000000 0.000000 + v 5.000000 -5.000000 0.000000 + v 5.000000 -1.666667 0.000000 + v 5.000000 1.666667 0.000000 + v 5.000000 5.000000 0.000000 + # 16 vertices + + cstype cardinal + stech cparma 1.000000 1.000000 + deg 3 3 + surf 0.000000 1.000000 0.000000 1.000000 13 14 \ + 15 16 9 10 11 12 5 6 7 8 1 2 3 4 + parm u 0.000000 1.000000 + parm v 0.000000 1.000000 + end + # 1 element + + +5. Rational B-spline surface + +This example creates a second-degree, rational B-spline surface using +open, uniform knot vectors. A texture map is applied to the surface. + + v -1.3 -1.0 0.0 + v 0.1 -1.0 0.4 7.6 + v 1.4 -1.0 0.0 2.3 + v -1.4 0.0 0.2 + v 0.1 0.0 0.9 0.5 + v 1.3 0.0 0.4 1.5 + v -1.4 1.0 0.0 2.3 + v 0.1 1.0 0.3 6.1 + v 1.1 1.0 0.0 3.3 + vt 0.0 0.0 + vt 0.5 0.0 + vt 1.0 0.0 + vt 0.0 0.5 + vt 0.5 0.5 + vt 1.0 0.5 + vt 0.0 1.0 + vt 0.5 1.0 + vt 1.0 1.0 + cstype rat bspline + deg 2 2 + surf 0.0 1.0 0.0 1.0 1/1 2/2 3/3 4/4 5/5 6/6 \ + 7/7 8/8 9/9 + parm u 0.0 0.0 0.0 1.0 1.0 1.0 + parm v 0.0 0.0 0.0 1.0 1.0 1.0 + end + + +6. Trimmed NURB surface + +This is a complete example of a file containing a trimmed NURB surface +with negative reference numbers for vertices. + + # trimming curve + vp -0.675 1.850 3.000 + vp 0.915 1.930 + vp 2.485 0.470 2.000 + vp 2.485 -1.030 + vp 1.605 -1.890 10.700 + vp -0.745 -0.654 0.500 + cstype rat bezier + deg 3 + curv2 -6 -5 -4 -3 -2 -1 -6 + parm u 0.00 1.00 2.00 + end + # surface + v -1.350 -1.030 0.000 + v 0.130 -1.030 0.432 7.600 + v 1.480 -1.030 0.000 2.300 + v -1.460 0.060 0.201 + v 0.120 0.060 0.915 0.500 + v 1.380 0.060 0.454 1.500 + v -1.480 1.030 0.000 2.300 + v 0.120 1.030 0.394 6.100 + v 1.170 1.030 0.000 3.300 + cstype rat bspline + deg 2 2 + surf -1.0 2.5 -2.0 2.0 -9 -8 -7 -6 -5 -4 -3 -2 -1 + parm u -1.00 -1.00 -1.00 2.50 2.50 2.50 + parm v -2.00 -2.00 -2.00 -2.00 -2.00 -2.00 + trim 0.0 2.0 1 + end + + +7. Two trimming regions with a hole + +This example shows a Bezier surface with two trimming regions, each +with a hole in them. + + # outer loop of first region + deg 1 + cstype bezier + vp 0.100 0.100 + vp 0.900 0.100 + vp 0.900 0.900 + vp 0.100 0.900 + curv2 1 2 3 4 1 + parm u 0.00 1.00 2.00 3.00 4.00 + end + # hole in first region + vp 0.300 0.300 + vp 0.700 0.300 + vp 0.700 0.700 + vp 0.300 0.700 + curv2 5 6 7 8 5 + parm u 0.00 1.00 2.00 3.00 4.00 + end + # outer loop of second region + vp 1.100 1.100 + vp 1.900 1.100 + vp 1.900 1.900 + vp 1.100 1.900 + curv2 9 10 11 12 9 + parm u 0.00 1.00 2.00 3.00 4.00 + end + # hole in second region + vp 1.300 1.300 + vp 1.700 1.300 + vp 1.700 1.700 + vp 1.300 1.700 + curv2 13 14 15 16 13 + parm u 0.00 1.00 2.00 3.00 4.00 + end + # surface + v 0.000 0.000 0.000 + v 1.000 0.000 0.000 + v 0.000 1.000 0.000 + v 1.000 1.000 0.000 + deg 1 1 + cstype bezier + surf 0.0 2.0 0.0 2.0 1 2 3 4 + parm u 0.00 2.00 + parm v 0.00 2.00 + trim 0.0 4.0 1 + hole 0.0 4.0 2 + trim 0.0 4.0 3 + hole 0.0 4.0 4 + end + + +8. Trimming with a special curve +This example is similar to the trimmed NURB surface example (6), except +there is a special curve on the surface. This example uses negative +vertex numbers. + + # trimming curve + vp -0.675 1.850 3.000 + vp 0.915 1.930 + vp 2.485 0.470 2.000 + vp 2.485 -1.030 + vp 1.605 -1.890 10.700 + vp -0.745 -0.654 0.500 + cstype rat bezier + deg 3 + curv2 -6 -5 -4 -3 -2 -1 -6 + parm u 0.00 1.00 2.00 + end + # special curve + vp -0.185 0.322 + vp 0.214 0.818 + vp 1.652 0.207 + vp 1.652 -0.455 + curv2 -4 -3 -2 -1 + parm u 2.00 10.00 + end + # surface + v -1.350 -1.030 0.000 + v 0.130 -1.030 0.432 7.600 + v 1.480 -1.030 0.000 2.300 + v -1.460 0.060 0.201 + v 0.120 0.060 0.915 0.500 + v 1.380 0.060 0.454 1.500 + v -1.480 1.030 0.000 2.300 + v 0.120 1.030 0.394 6.100 + v 1.170 1.030 0.000 3.300 + cstype rat bspline + deg 2 2 + surf -1.0 2.5 -2.0 2.0 -9 -8 -7 -6 -5 -4 -3 -2 -1 + parm u -1.00 -1.00 -1.00 2.50 2.50 2.50 + parm v -2.00 -2.00 -2.00 2.00 2.00 2.00 + trim 0.0 2.0 1 + scrv 4.2 9.7 2 + end + + +9. Trimming with special points + +This example extends the trimmed NURB surface example (6) to include +special points on both the trimming curve and surface. A space curve +with a special point is also included. This example uses negative +vertex numbers. + + # special point and space curve data + vp 0.500 + vp 0.700 + vp 1.100 + vp 0.200 0.950 + v 0.300 1.500 0.100 + v 0.000 0.000 0.000 + v 1.000 1.000 0.000 + v 2.000 1.000 0.000 + v 3.000 0.000 0.000 + cstype bezier + deg 3 + curv 0.2 0.9 -4 -3 -2 -1 + sp 1 + parm u 0.00 1.00 + end + # trimming curve + vp -0.675 1.850 3.000 + vp 0.915 1.930 + vp 2.485 0.470 2.000 + vp 2.485 -1.030 + vp 1.605 -1.890 10.700 + vp -0.745 -0.654 0.500 + cstype rat bezier + curv2 -6 -5 -4 -3 -2 -1 -6 + parm u 0.00 1.00 2.00 + sp 2 3 + end + # surface + v -1.350 -1.030 0.000 + v 0.130 -1.030 0.432 7.600 + v 1.480 -1.030 0.000 2.300 + v -1.460 0.060 0.201 + v 0.120 0.060 0.915 0.500 + v 1.380 0.060 0.454 1.500 + v -1.480 1.030 0.000 2.300 + v 0.120 1.030 0.394 6.100 + v 1.170 1.030 0.000 3.300 + cstype rat bspline + deg 2 2 + surf -1.0 2.5 -2.0 2.0 -9 -8 -7 -6 -5 -4 -3 -2 -1 + parm u -1.00 -1.00 -1.00 2.50 2.50 2.50 + parm v -2.00 -2.00 -2.00 2.00 2.00 2.00 + trim 0.0 2.0 1 + sp 4 + end + +Connectivity between free-form surfaces + +Connectivity connects two surfaces along their trimming curves. + +The con statement specifies the first surface with its trimming curve +and the second surface with its trimming curve. This information is +useful for edge merging. Without this surface and curve data, +connectivity must be determined numerically at greater expense and with +reduced accuracy using the mg statement. + +Connectivity between surfaces in different merging groups is ignored. +Also, although connectivity which crosses points of C1discontinuity in +trimming curves is legal, it is not recommended. Instead, use two +connectivity statements which meet at the point of discontinuity. + +The two curves and their starting and ending parameters should all map +to the same curve and starting and ending points in object space. + +Syntax + +con surf_1 q0_1 q1_1 curv2d_1 surf_2 q0_2 q1_2 curv2d_2 + + Free-form geometry statement. + + Specifies connectivity between two surfaces. + + surf_1 is the index of the first surface. + + q0_1 is the starting parameter for the curve referenced by + curv2d_1. + + q1_1 is the ending parameter for the curve referenced by curv2d_1. + + curv2d_1 is the index of a curve on the first surface. This curve + must have been previously defined with the curv2 statement. + + surf_2 is the index of the second surface. + + q0_2 is the starting parameter for the curve referenced by + curv2d_2. + + q1_2 is the ending parameter for the curve referenced by curv2d_2. + + curv2d_2 is the index of a curve on the second surface. This curve + must have been previously defined with the curv2 statement. + +Example + +1. Connectivity between two surfaces + +This example shows the connectivity between two surfaces with trimming +curves. + + cstype bezier + deg 1 1 + + v 0 0 0 + v 1 0 0 + v 0 1 0 + v 1 1 0 + + vp 0 0 + vp 1 0 + vp 1 1 + vp 0 1 + + curv2 1 2 3 4 1 + parm u 0.0 1.0 2.0 3.0 4.0 + end + + surf 0.0 1.0 0.0 1.0 1 2 3 4 + parm u 0.0 1.0 + parm v 0.0 1.0 + trim 0.0 4.0 1 + end + + v 1 0 0 + v 2 0 0 + v 1 1 0 + v 2 1 0 + + surf 0.0 1.0 0.0 1.0 5 6 7 8 + parm u 0.0 1.0 + parm v 0.0 1.0 + trim 0.0 4.0 1 + end + + con 1 2.0 2.0 1 2 4.0 3.0 1 + + +Grouping + +There are four statements in the .obj file to help you manipulate groups +of elements: + +o Gropu name statements are used to organize collections of + elements and simplify data manipulation for operations in + Model. + +o Smoothing group statements let you identify elements over which + normals are to be interpolated to give those elements a smooth, + non-faceted appearance. This is a quick way to specify vertex + normals. + +o Merging group statements are used to ideneify free-form elements + that should be inspected for adjacency detection. You can also + use merging groups to exclude surfaces which are close enough to + be considered adjacent but should not be merged. + +o Object name statements let you assign a name to an entire object + in a single file. + +All grouping statements are state-setting. This means that once a +group statement is set, it alpplies to all elements that follow +until the next group statement. + +This portion of a sample file shows a single element which belongs to +three groups. The smoothing group is turned off. + + g square thing all + s off + f 1 2 3 4 + +This example shows two surfaces in merging group 1 with a merge +resolution of 0.5. + + mg 1 .5 + surf 0.0 1.0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 + surf 0.0 1.0 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 + +Syntax + +g group_name1 group_name2 . . . + + Polygonal and free-form geometry statement. + + Specifies the group name for the elements that follow it. You can + have multiple group names. If there are multiple groups on one + line, the data that follows belong to all groups. Group information + is optional. + + group_name is the name for the group. Letters, numbers, and + combinations of letters and numbers are accepted for group names. + The default group name is default. + +s group_number + + Polygonal and free-form geometry statement. + + Sets the smoothing group for the elements that follow it. If you do + not want to use a smoothing group, specify off or a value of 0. + + To display with smooth shading in Model and PreView, you must + create vertex normals after you have assigned the smoothing groups. + You can create vertex normals with the vn statement or with the + Model program. + + To smooth polygonal geometry for rendering with Image, it is + sufficient to put elements in some smoothing group. However, vertex + normals override smoothing information for Image. + + group_number is the smoothing group number. To turn off smoothing + groups, use a value of 0 or off. Polygonal elements use group + numbers to put elements in different smoothing groups. For + free-form surfaces, smoothing groups are either turned on or off; + there is no difference between values greater than 0. + +mg group_number res + + Free-form geometry statement. + + Sets the merging group and merge resolution for the free-form + surfaces that follow it. If you do not want to use a merging group, + specify off or a value of 0. + + Adjacency detection is performed only within groups, never between + groups. Connectivity between surfaces in different merging groups + is not allowed. Surfaces in the same merging group are merged + together along edges that are within the distance res apart. + + NOTE: Adjacency detection is an expensive numerical comparison + process. It is best to restrict this process to as small a domain + as possible by using small merging groups. + + group_number is the merging group number. To turn off adjacency + detection, use a value of 0 or off. + + res is the maximum distance between two surfaces that will be + merged together. The resolution must be a value greater than 0. + This is a required argument only when using merging groups. + +o object_name + + Polygonal and free-form geometry statement. + + Optional statement; it is not processed by any Wavefront programs. + It specifies a user-defined object name for the elements defined + after this statement. + + object_name is the user-defined object name. There is no default. + +Examples + +1. Cube with group names + +The following example is a cube with each of its faces placed in a +separate group. In addition, all elements belong to the group cube. + + v 0.000000 2.000000 2.000000 + v 0.000000 0.000000 2.000000 + v 2.000000 0.000000 2.000000 + v 2.000000 2.000000 2.000000 + v 0.000000 2.000000 0.000000 + v 0.000000 0.000000 0.000000 + v 2.000000 0.000000 0.000000 + v 2.000000 2.000000 0.000000 + # 8 vertices + + g front cube + f 1 2 3 4 + g back cube + f 8 7 6 5 + g right cube + f 4 3 7 8 + g top cube + f 5 1 4 8 + g left cube + f 5 6 2 1 + g bottom cube + f 2 6 7 3 + # 6 elements + + +2. Two adjoining squares with a smoothing group + +This example shows two adjoining squares that share a common edge. The +squares are placed in a smoothing group to ensure that their common +edge will be smoothed when rendered with Image. + + v 0.000000 2.000000 0.000000 + v 0.000000 0.000000 0.000000 + v 2.000000 0.000000 0.000000 + v 2.000000 2.000000 0.000000 + v 4.000000 0.000000 -1.255298 + v 4.000000 2.000000 -1.255298 + # 6 vertices + + g all + s 1 + f 1 2 3 4 + f 4 3 5 6 + # 2 elements + + +3. Two adjoining squares with vertex normals + +This example also shows two squares that share a common edge. Vertex +normals have been added to the corners of each square to ensure that +their common edge will be smoothed during display in Model and PreView +and when rendered with Image. + + v 0.000000 2.000000 0.000000 + v 0.000000 0.000000 0.000000 + v 2.000000 0.000000 0.000000 + v 2.000000 2.000000 0.000000 + v 4.000000 0.000000 -1.255298 + v 4.000000 2.000000 -1.255298 + vn 0.000000 0.000000 1.000000 + vn 0.000000 0.000000 1.000000 + vn 0.276597 0.000000 0.960986 + vn 0.276597 0.000000 0.960986 + vn 0.531611 0.000000 0.846988 + vn 0.531611 0.000000 0.846988 + # 6 vertices + + # 6 normals + + g all + s 1 + f 1//1 2//2 3//3 4//4 + f 4//4 3//3 5//5 6//6 + # 2 elements + + +4. Merging group + +This example shows two Bezier surfaces that meet at a common edge. They +have both been placed in the same merging group to ensure continuity at +the edge where they meet. This prevents "cracks" from appearing along +the seam between the two surfaces during rendering. Merging groups will +be ignored during flat-shading, smooth-shading, and material shading of +the surface. + + v -4.949854 -5.000000 0.000000 + v -4.949854 -1.666667 0.000000 + v -4.949854 1.666667 0.000000 + v -4.949854 5.000000 0.000000 + v -1.616521 -5.000000 0.000000 + v -1.616521 -1.666667 0.000000 + v -1.616521 1.666667 0.000000 + v -1.616521 5.000000 0.000000 + v 1.716813 -5.000000 0.000000 + v 1.716813 -1.666667 0.000000 + v 1.716813 1.666667 0.000000 + v 1.716813 5.000000 0.000000 + v 5.050146 -5.000000 0.000000 + v 5.050146 -1.666667 0.000000 + v 5.050146 1.666667 0.000000 + v 5.050146 5.000000 0.000000 + v -15.015566 -4.974991 0.000000 + v -15.015566 -1.641658 0.000000 + v -15.015566 1.691675 0.000000 + v -15.015566 5.025009 0.000000 + v -11.682233 -4.974991 0.000000 + v -11.682233 -1.641658 0.000000 + v -11.682233 1.691675 0.000000 + v -11.682233 5.025009 0.000000 + v -8.348900 -4.974991 0.000000 + v -8.348900 -1.641658 0.000000 + v -8.348900 1.691675 0.000000 + v -8.348900 5.025009 0.000000 + v -5.015566 -4.974991 0.000000 + v -5.015566 -1.641658 0.000000 + v -5.015566 1.691675 0.000000 + v -5.015566 5.025009 0.000000 + + mg 1 0.500000 + + cstype bezier + deg 3 3 + surf 0.000000 1.000000 0.000000 1.000000 13 14 \ + 15 16 9 10 11 12 5 6 7 8 1 2 3 4 + parm u 0.000000 1.000000 + parm v 0.000000 1.000000 + end + surf 0.000000 1.000000 0.000000 1.000000 29 30 31 32 25 26 27 28 21 22 \ + 23 24 17 18 19 20 + parm u 0.000000 1.000000 + parm v 0.000000 1.000000 + end + + +Display/render attributes + +Display and render attributes describe how an object looks when +displayed in Model and PreView or when rendered with Image. + +Some attributes apply to both free-form and polygonal geometry, such as +material name and library, ray tracing, and shadow casting. +Interpolation attributes apply only to polygonal geometry. Curve and +surface resolutions are used for only free-form geometry. + +The following chart shows the display and render statements available +for polygonal and free-form geometry. + +Table B1-1. Display and render attributes + +polygonal only polygonal or free-form free-form only +-------------- ---------------------- -------------- +bevel lod ctech +c_interp usemtl stech +d_interp mtllib + shadow_obj + trace_obj + +All display and render attribute statements are state-setting. This +means that once an attribute statement is set, it applies to all +elements that follow until it is reset to a different value. + +The following sample shows rendering and display statements for a face +element.: + + s 1 + usemtl blue + usemap marble + f 1 2 3 4 + +Syntax + +The following syntax statements are listed by the type of geometry. +First are statements for polygonal geometry. Second are statements for +both free-form and polygonal geometry. Third are statements for +free-form geometry only. + +bevel on/off + + Polygonal geometry statement. + + Sets bevel interpolation on or off. It works only with beveled + objects, that is, objects with sides separated by beveled faces. + + Bevel interpolation uses normal vector interpolation to give an + illusion of roundness to a flat bevel. It does not affect the + smoothing of non-bevelled faces. + + Bevel interpolation does not alter the geometry of the original + object. + + on turns on bevel interpolation. + + off turns off bevel interpolation. The default is off. + + NOTE: Image cannot render bevel-interpolated elements that have + vertex normals. + +c_interp on/off + + Polygonal geometry statement. + + Sets color interpolation on or off. + + Color interpolation creates a blend across the surface of a polygon + between the materials assigned to its vertices. This creates a + blending of colors across a face element. + + To support color interpolation, materials must be assigned per + vertex, not per element. The illumination models for all materials + of vertices attached to the polygon must be the same. Color + interpolation applies to the values for ambient (Ka), diffuse (Kd), + specular (Ks), and specular highlight (Ns) material properties. + + on turns on color interpolation. + + off turns off color interpolation. The default is off. + +d_interp on/off + + Polygonal geometry statement. + + Sets dissolve interpolation on or off. + + Dissolve interpolation creates an interpolation or blend across a + polygon between the dissolve (d) values of the materials assigned + to its vertices. This feature is used to create effects exhibiting + varying degrees of apparent transparency, as in glass or clouds. + + To support dissolve interpolation, materials must be assigned per + vertex, not per element. All the materials assigned to the vertices + involved in the dissolve interpolation must contain a dissolve + factor command to specify a dissolve. + + on turns on dissolve interpolation. + + off turns off dissolve interpolation. The default is off. + +lod level + + Polygonal and free-form geometry statement. + + Sets the level of detail to be displayed in a PreView animation. + The level of detail feature lets you control which elements of an + object are displayed while working in PreView. + + level is the level of detail to be displayed. When you set the + level of detail to 0 or omit the lod statement, all elements are + displayed. Specifying an integer between 1 and 100 sets the level + of detail to be displayed when reading the .obj file. + +maplib filename1 filename2 . . . + + This is a rendering identifier that specifies the map library file + for the texture map definitions set with the usemap identifier. You + can specify multiple filenames with maplib. If multiple filenames + are specified, the first file listed is searched first for the map + definition, the second file is searched next, and so on. + + When you assign a map library using the Model program, Model allows + only one map library per .obj file. You can assign multiple + libraries using a text editor. + + filename is the name of the library file where the texture maps are + defined. There is no default. + +usemap map_name/off + + This is a rendering identifier that specifies the texture map name + for the element following it. To turn off texture mapping, specify + off instead of the map name. + + If you specify texture mapping for a face without texture vertices, + the texture map will be ignored. + + map_name is the name of the texture map. + + off turns off texture mapping. The default is off. + +usemtl material_name + + Polygonal and free-form geometry statement. + + Specifies the material name for the element following it. Once a + material is assigned, it cannot be turned off; it can only be + changed. + + material_name is the name of the material. If a material name is + not specified, a white material is used. + +mtllib filename1 filename2 . . . + + Polygonal and free-form geometry statement. + + Specifies the material library file for the material definitions + set with the usemtl statement. You can specify multiple filenames + with mtllib. If multiple filenames are specified, the first file + listed is searched first for the material definition, the second + file is searched next, and so on. + + When you assign a material library using the Model program, only + one map library per .obj file is allowed. You can assign multiple + libraries using a text editor. + + filename is the name of the library file that defines the + materials. There is no default. + +shadow_obj filename + + Polygonal and free-form geometry statement. + + Specifies the shadow object filename. This object is used to cast + shadows for the current object. Shadows are only visible in a + rendered image; they cannot be seen using hardware shading. The + shadow object is invisible except for its shadow. + + An object will cast shadows only if it has a shadow object. You can + use an object as its own shadow object. However, a simplified + version of the original object is usually preferable for shadow + objects, since shadow casting can greatly increase rendering time. + + filename is the filename for the shadow object. You can enter any + valid object filename for the shadow object. The object file can be + an .obj or .mod file. If a filename is given without an extension, + an extension of .obj is assumed. + + Only one shadow object can be stored in a file. If more than one + shadow object is specified, the last one specified will be used. + +trace_obj filename + + Polygonal and free-form geometry statement. + + Specifies the ray tracing object filename. This object will be used + in generating reflections of the current object on reflective + surfaces. Reflections are only visible in a rendered image; they + cannot be seen using hardware shading. + + An object will appear in reflections only if it has a trace object. + You can use an object as its own trace object. However, a + simplified version of the original object is usually preferable for + trace objects, since ray tracing can greatly increase rendering + time. + + filename is the filename for the ray tracing object. You can enter + any valid object filename for the trace object. You can enter any + valid object filename for the shadow object. The object file can be + an .obj or .mod file. If a filename is given without an extension, + an extension of .obj is assumed. + + Only one trace object can be stored in a file. If more than one is + specified, the last one is used. + +ctech technique resolution + + Free-form geometry statement. + + Specifies a curve approximation technique. The arguments specify + the technique and resolution for the curve. + + You must select from one of the following three techniques. + + ctech cparm res + + Specifies a curve with constant parametric subdivision using + one resolution parameter. Each polynomial segment of the curve + is subdivided n times in parameter space, where n is the + resolution parameter multiplied by the degree of the curve. + + res is the resolution parameter. The larger the value, the + finer the resolution. If res has a value of 0, each polynomial + curve segment is represented by a single line segment. + + ctech cspace maxlength + + Specifies a curve with constant spatial subdivision. The curve + is approximated by a series of line segments whose lengths in + real space are less than or equal to the maxlength. + + maxlength is the maximum length of the line segments. The + smaller the value, the finer the resolution. + + ctech curv maxdist maxangle + + Specifies curvature-dependent subdivision using separate + resolution parameters for the maximum distance and the maximum + angle. + + The curve is approximated by a series of line segments in which + 1) the distance in object space between a line segment and the + actual curve must be less than the maxdist parameter and 2) the + angle in degrees between tangent vectors at the ends of a line + segment must be less than the maxangle parameter. + + maxdist is the distance in real space between a line segment + and the actual curve. + + maxangle is the angle (in degrees) between tangent vectors at + the ends of a line segment. + + The smaller the values for maxdist and maxangle, the finer the + resolution. + + NOTE: Approximation information for trimming, hole, and special + curves is stored in the corresponding surface. The ctech statement + for the surface is used, not the ctech statement applied to the + curv2 statement. Although untrimmed surfaces have no explicit + trimming loop, a loop is constructed which bounds the legal + parameter range. This implicit loop follows the same rules as any + other loop and is approximated according to the ctech information + for the surface. + +stech technique resolution + + Free-form geometry statement. + + Specifies a surface approximation technique. The arguments specify + the technique and resolution for the surface. + + You must select from one of the following techniques: + + stech cparma ures vres + + Specifies a surface with constant parametric subdivision using + separate resolution parameters for the u and v directions. Each + patch of the surface is subdivided n times in parameter space, + where n is the resolution parameter multiplied by the degree of + the surface. + + ures is the resolution parameter for the u direction. + + vres is the resolution parameter for the v direction. + + The larger the values for ures and vres, the finer the + resolution. If you enter a value of 0 for both ures and vres, + each patch is approximated by two triangles. + + stech cparmb uvres + + Specifies a surface with constant parametric subdivision, with + refinement using one resolution parameter for both the u and v + directions. + + An initial triangulation is performed using only the points on + the trimming curves. This triangulation is then refined until + all edges are of an appropriate length. The resulting triangles + are not oriented along isoparametric lines as they are in the + cparma technique. + + uvres is the resolution parameter for both the u and v + directions. The larger the value, the finer the resolution. + + stech cspace maxlength + + Specifies a surface with constant spatial subdivision. + + The surface is subdivided in rectangular regions until the + length in real space of any rectangle edge is less than the + maxlength. These rectangular regions are then triangulated. + + maxlength is the length in real space of any rectangle edge. + The smaller the value, the finer the resolution. + + stech curv maxdist maxangle + + Specifies a surface with curvature-dependent subdivision using + separate resolution parameters for the maximum distance and the + maximum angle. + + The surface is subdivided in rectangular regions until 1) the + distance in real space between the approximating rectangle and + the actual surface is less than the maxdist (approximately) and + 2) the angle in degrees between surface normals at the corners + of the rectangle is less than the maxangle. Following + subdivision, the regions are triangulated. + + maxdist is the distance in real space between the approximating + rectangle and the actual surface. + + maxangle is the angle in degrees between surface normals at the + corners of the rectangle. + + The smaller the values for maxdist and maxangle, the finer the + resolution. + +Examples + +1. Cube with materials + +This cube has a different material applied to each of its faces. + + mtllib master.mtl + + v 0.000000 2.000000 2.000000 + v 0.000000 0.000000 2.000000 + v 2.000000 0.000000 2.000000 + v 2.000000 2.000000 2.000000 + v 0.000000 2.000000 0.000000 + v 0.000000 0.000000 0.000000 + v 2.000000 0.000000 0.000000 + v 2.000000 2.000000 0.000000 + # 8 vertices + + g front + usemtl red + f 1 2 3 4 + g back + usemtl blue + f 8 7 6 5 + g right + usemtl green + f 4 3 7 8 + g top + usemtl gold + f 5 1 4 8 + g left + usemtl orange + f 5 6 2 1 + g bottom + usemtl purple + f 2 6 7 3 + # 6 elements + + +2. Cube casting a shadow + +In this example, the cube casts a shadow on the other objects when it +is rendered with Image. The cube, which is stored in the file cube.obj, +references itself as the shadow object. + + mtllib master.mtl + shadow_obj cube.obj + + v 0.000000 2.000000 2.000000 + v 0.000000 0.000000 2.000000 + v 2.000000 0.000000 2.000000 + v 2.000000 2.000000 2.000000 + v 0.000000 2.000000 0.000000 + v 0.000000 0.000000 0.000000 + v 2.000000 0.000000 0.000000 + v 2.000000 2.000000 0.000000 + # 8 vertices + + g front + usemtl red + f 1 2 3 4 + g back + usemtl blue + f 8 7 6 5 + g right + usemtl green + f 4 3 7 8 + g top + usemtl gold + f 5 1 4 8 + g left + usemtl orange + f 5 6 2 1 + g bottom + usemtl purple + f 2 6 7 3 + # 6 elements + + +3. Cube casting a reflection + +This cube casts its reflection on any reflective objects when it is +rendered with Image. The cube, which is stored in the file cube.obj, +references itself as the trace object. + + mtllib master.mtl + trace_obj cube.obj + + v 0.000000 2.000000 2.000000 + v 0.000000 0.000000 2.000000 + v 2.000000 0.000000 2.000000 + v 2.000000 2.000000 2.000000 + v 0.000000 2.000000 0.000000 + v 0.000000 0.000000 0.000000 + v 2.000000 0.000000 0.000000 + v 2.000000 2.000000 0.000000 + # 8 vertices + + g front + usemtl red + f 1 2 3 4 + g back + usemtl blue + f 8 7 6 5 + g right + usemtl green + f 4 3 7 8 + g top + usemtl gold + f 5 1 4 8 + g left + usemtl orange + f 5 6 2 1 + g bottom + usemtl purple + f 2 6 7 3 + # 6 elements + + + +4. Texture-mapped square + +This example describes a 2 x 2 square. It is mapped with a 1 x 1 square +texture. The texture is stretched to fit the square exactly. + +mtllib master.mtl + +v 0.000000 2.000000 0.000000 +v 0.000000 0.000000 0.000000 +v 2.000000 0.000000 0.000000 +v 2.000000 2.000000 0.000000 +vt 0.000000 1.000000 0.000000 +vt 0.000000 0.000000 0.000000 +vt 1.000000 0.000000 0.000000 +vt 1.000000 1.000000 0.000000 +# 4 vertices + +usemtl wood +f 1/1 2/2 3/3 4/4 +# 1 element + +5. Approximation technique for a surface + +This example shows a B-spline surface which will be approximated using +curvature-dependent subdivision specified by the stech command. + + g bspatch + v -5.000000 -5.000000 -7.808327 + v -5.000000 -1.666667 -7.808327 + v -5.000000 1.666667 -7.808327 + v -5.000000 5.000000 -7.808327 + v -1.666667 -5.000000 -7.808327 + v -1.666667 -1.666667 11.977780 + v -1.666667 1.666667 11.977780 + v -1.666667 5.000000 -7.808327 + v 1.666667 -5.000000 -7.808327 + v 1.666667 -1.666667 11.977780 + v 1.666667 1.666667 11.977780 + v 1.666667 5.000000 -7.808327 + v 5.000000 -5.000000 -7.808327 + v 5.000000 -1.666667 -7.808327 + v 5.000000 1.666667 -7.808327 + v 5.000000 5.000000 -7.808327 + # 16 vertices + + g bspatch + cstype bspline + stech curv 0.5 10.000000 + deg 3 3 + surf 0.000000 1.000000 0.000000 1.000000 13 14 \ 15 16 9 10 11 12 5 6 7 + 8 1 2 3 4 + parm u -3.000000 -2.000000 -1.000000 0.000000 \ + 1.000000 2.000000 3.000000 4.000000 + parm v -3.000000 -2.000000 -1.000000 0.000000 \ + 1.000000 2.000000 3.000000 4.000000 + end + # 1 element + + + +6. Approximation technique for a curve + +This example shows a Bezier curve which will be approximated using +constant parametric subdivision specified by the ctech command. + + v -2.300000 1.950000 0.000000 + v -2.200000 0.790000 0.000000 + v -2.340000 -1.510000 0.000000 + v -1.530000 -1.490000 0.000000 + v -0.720000 -1.470000 0.000000 + v -0.780000 0.230000 0.000000 + v 0.070000 0.250000 0.000000 + v 0.920000 0.270000 0.000000 + v 0.800000 -1.610000 0.000000 + v 1.620000 -1.590000 0.000000 + v 2.440000 -1.570000 0.000000 + v 2.690000 0.670000 0.000000 + v 2.900000 1.980000 0.000000 + # 13 vertices + + g default + cstype bezier + ctech cparm 1.000000 + deg 3 + curv 0.000000 4.000000 1 2 3 4 5 6 7 8 9 10 \ + 11 12 13 + parm u 0.000000 1.000000 2.000000 3.000000 \ + 4.000000 + end + # 1 element + + + +Comments + +Comments can appear anywhere in an .obj file. They are used to annotate +the file; they are not processed. + +Here is an example: + + # this is a comment + +The Model program automatically inserts comments when it creates .obj +files. For example, it reports the number of geometric vertices, +texture vertices, and vertex normals in a file. + + # 4 vertices + # 4 texture vertices + # 4 normals + +Mathematics for free-form curves/surfaces + +[I apologize but this section will make absolutely no sense whatsoever + without the equations and diagrams and there was just no easy way to + include them in a pure ASCII document. You should probably just skip + ahead to the section "Superseded statements." -Jim] + +General forms + +Rational and non-rational curves and surfaces + +In general, any non-rational curve segment may be written as: + +where + +K + 1 is the number of control points + +di are the control points + +n is the degree of the curve + +Ni,n(t) are the degree n basis functions + +Extending this to the bivariate case, any non-rational surface patch +may be written as: + +where: + +K1 + 1 is the number of control points in the u direction + +K2 + 1 is the number of control points in the v direction + +di,j are the control points + +m is the degree of the surface in the u direction + +n is the degree of the surface in the v direction + +Ni,m(u) are the degree m basis functions in the u direction + +Nj,n(v) are the degree n basis functions in the v direction + +NOTE: The front of the surface is defined as the side where the u +parameter increases to the right and the v parameter increases upward. + +We may extend this curve to the rational case as: + + + +where wi are the weights associated with the control points di. +Similarly, a rational surface may be expressed as: + +where wi,j are the weights associated with the control points di,j. + +NOTE: If a curve or surface in an .obj file is rational, it must use +the rat option with the cstype statement and it requires some weight +values for each control point. + + + +The weights for the rational form are given as a third control point +coordinate (for trimming curves) or fourth coordinate (for space curves +and surfaces). These weights are optional and default to 1.0 if not +given. + + + +This default weight is only reasonable for curves and surfaces whose +basis functions sum to 1.0, such as Bezier, Cardinal, and NURB. It does +not make sense for Taylor and may or may not make sense for a +representation given in basis-matrix form. + +For all forms other than B-spline, the final curve or surface is +constructed by piecing together the individual curve segments or +surface patches. A global parameter space is then defined over the +entire composite curve or surface using the parameter vector given with +the parm statement. + +The parameter vector for a curve is a list of p global parameter values +{t1, . . . , tp}. If t1 t < ti+1 is a point in global parameter space, +then: + +is the corresponding point in local parameter space for the ith +polynomial segment. It is this t which is used when evaluating a given +segment of the piecewise curve. For surfaces, this mapping from global +to local parameter space is applied independently in both the u and v +parametric directions. + +B-splines require a knot vector rather than a parameter vector, +although this is also given with the parm statement. Refer to the +description of B-splines below. + +The following discussion of each type is expressed in terms of the +above definitions. + +NOTE: The maximum degree for all curve and surface types is currently +set at 20, which is high enough for most purposes. + + + +Free-form curve and surface types + +B-spline + +Type bspline specifies arbitrary degree non-uniform B-splines which are +commonly referred to as NURBs in their rational form. The basis +functions are defined by the Cox-deBoor recursion formulas as: + +and: + +where, by convention, 0/0 = 0. + +The xi {x0, . . . ,xq} form a set known as the knot vector which is +given by the parm statement. It is required that + +1. xi xi + 1, + +2. x0 < xn + 1, + +3. xq -n -1 < xq, + +4. xi < xi + n for 0 < i < q - n - 1, + +5. xn t min < tmax xK+ 1, where [tmin, tmax] is the parameter +over which the B-spline is to be evaluated, and + +6. K = q - n - 1. + +A knot is said to be of multiplicity r if its value is repeated r times +in the knot vector. The second through fourth conditions above restrict +knots to be of at most multiplicity n + 1 at the ends of the vector and +at most n everywhere else. + +The last condition requires that the number of control points is equal +to one less than the number of knots minus the degree. For surfaces, +all of the above conditions apply independently for the u and v +parametric directions. + +Bezier + +Type bezier specifies arbitrary degree Bezier curves and surfaces. This +basis function is defined as: + +where: + +When using type bezier, the number of global parameter values given +with the parm statement must be K/n + 1, where K is the number of +control points. For surfaces, this requirement applies independently +for the u and v parametric directions. + +Cardinal + +Type cardinal specifies a cubic, first derivative, continuous curve or +surface. For curves, this interpolates all but the first and last +control points. For surfaces, all but the first and last row and column +of control points are interpolated. + +Cardinal splines, also known as Catmull-Rom splines, are best +understood by considering the conversion from Cardinal to Bezier +control points for a single curve segment: + +Here, the ci variables are the Cardinal control points and the bi +variables are the Bezier control points. We see that the second and +third Cardinal points are the beginning and ending points for the +segment, respectively. Also, the beginning tangent lies along the +vector from the first to the third point, and the ending tangent along +the vector from the second to the last point. + +If we let Bi(t) be the cubic Bezier basis functions (i.e. what was +given above for Bezier as Ni,n(t) with n = 3), then we may write the +Cardinal basis functions as: + +Note that Cardinal splines are only defined for the cubic case. + +When using type cardinal, the number of global parameter values given +with the parm statement must be K - n + 2, where K is the number of +control points. For surfaces, this requirement applies independently +for the u and v parametric directions. + +Taylor + +Type taylor specifies arbitrary degree Taylor polynomial curves and +surfaces. The basis function is simply: + +NOTE: The control points in this case are the polynomial coefficients +and have no obvious geometric significance. + +When using type taylor, the number of global parameter values given +with the parm statement must be (K + 1)/(n + 1) + 1, where K is the +number of control points. For surfaces, this requirement applies +independently for the u and v parametric directions. + +Basis matrix + +Type bmatrix specifies general, arbitrary-degree curves defined through +the use of a basis matrix rather than an explicit type such as Bezier. +The basis functions are defined as: + +where the basis matrix is the bi,j. In order to make the matrix nature +of this more obvious, we may also write: + +When constructing basis matrices, you should keep this definition in +mind, as different authors write this in different ways. A more common +matrix representation is: + +To use such matrices in the .obj file, simply transpose the matrix and +reverse the column ordering. + +When using type basis, the number of global parameter values given with +the parm statement must be (K - n)/s + 2, where K is the number of +control points and s is the step size given with the step statement. +For surfaces, this requirement applies independently for the u and v +parametric directions. + +Surface vertex data + +Control points + +The control points for a surface consisting of a single patch are +listed in the order i = 0 to K1 for j = 0, followed by i = 0 to K1 for +j = 1, and so on until j = K2. + +For surfaces made up of many patches, which is the usual case, the +control points are ordered as if the surface were a single large patch. +For example, the control points for a bicubic Bezier surface consisting +of four patches would be arranged as follows: + +where (m, n) is the global parameter space of the surface and the +numbers indicate the ordering of the vertex indices in the surf +statement. + +Texture vertices and texture mapping + +When texture vertices are not supplied, the original surface +parameterization is used for texture mapping. However, if texture +vertices are supplied, they are interpreted as additional information +to be interpolated or approximated separately from, but using the same +interpolation functions as the control vertices. + +That is, whereas the surface itself, in the non-rational case, was +given in the section "Rational and non-rational curves and surfaces" +as: + + + +the texture vertices are interpolated or approximated by: + +where ti,j are the texture vertices and the basis functions are the +same as for S(u,v). It is T(u,v), rather than the surface +parameterization (u,v), which is used when a texture map is applied. + +Vertex normals and normal mapping + +Vertex normals are treated exactly like texture vertices. When vertex +normals are not supplied, the true surface normals are used. If vertex +normals are supplied, they are calculated as: + +where qi,j are the vertex normals and the basis functions are the same +as for S(u,v) and T(u,v). + +NOTE: Vertex normals do not affect the shape of the surface; they are +simply associated with the triangle vertices in the final +triangulation. As with faces, supplying vertex normals only affects +lighting calculations for the surface. + +The treatment of both texture vertices and vertex normals in the case +of rational surfaces is identical. It is important to notice that even +when the surface S(u,v) is rational, the texture and normal surfaces, +T(u,v) and Q(u,v), are not rational. This is because the control points +(the texture vertices and vertex normals) are never rational. + +Curve and surface operations + +Special points + +The following equations give a more precise description of special +points for space curves and discuss the extension to trimming curves +and surfaces. + +Let C(t) be a space curve with the global parameter t. We can +approximate this curve by a set of k-1 line segments which connect the +points: + +for some set of k global parameter values {t1,...,tk} + +Given a special point ts in the parameter space of the curve +(referenced by vp), we guarantee that ts {t1, . . . ,tk}. More +specifically, we approximate the curve by: + +where, at the point i where ts is inserted, we have ti ts < ti+1. + +Special curves + +The following equations give a more precise description of a special +curve. + +Let T(t) be a special curve with the global parameter t. We have: + +where (m,n) is a point in the global parameter space of a surface. We +can approximate this curve by a set of k-1 line segments which connect +the points: + +for some set of k global parameter values. + +Let S(m,n) be a surface with the global parameters m and n. We can +approximate this surface by a triangulation of a set of p points. + +which lie on the surface. We further define E as the set of all edges +such that ei,j E implies that S(mi,ni) and S(mj,nj) are connected in +the triangulation. Finally, we guarantee that there exists some subset +of E: + +such that the points: + +are connected in the triangulation. + +Connectivity + +Recall that the syntax of the con statement is: + +con surf_1 q0_1 q1_1 curv2d_1 surf_2 q0_2 q1_2 curv2d_2 + +If we let: + +T1(t1) be the curve referenced by curv2d_1 + +S1(m1, n1) be the surface referenced by surf1 on which T1(t1) lies + +T2(t2) be the curve referenced by curv2d_2 + +S2(m2, n2) be the surface referenced by surf2 on which T2(t2) lies + +then S1(T1(t1)), S2(T2(t2)) must be identical up to reparameterization. +Moreover, it must be the case that: + +S1(T1(q0_1)) = S2(T2(q0_2)) + +and: + +S1(T1(q1_1)) = S2(T2(q1_2)) + +It is along the curve S1(T1(t1)) between t1 = q0_1 and t1 = q1_1, and +the curve S2(T2(t2)) between t2 = q0_2 and t2 = q1_2 that the surface +S1(m1, n1) is connected to the surface S2(m2, n2). + + + +Superseded statements + +The new .obj file format has eliminated the need for several patch and +curve statements. These statements have been replaced by free-form +geometry statements. + +In the 3.0 release, the following keywords have been superseded: + +o bsp + +o bzp + +o cdc + +o cdp + +o res + +You can still read these statements in this version 3.0, however, the +system will no longer write files in this format. + +This release is the last release that will read these statements. If +you want to save any data from this format, read in the file and write +it out. The system will convert the data to the new .obj format. + +For more information on the new syntax statements, see "Specifying +free-form curves and surfaces." + +Syntax + +The following syntax statements are for the superseded keywords. + +bsp v1 v2 . . . v16 + + Specifies a B-spline patch. B-spline patches have sixteen control + points, defined as vertices. Only four of the control points are + distributed over the surface of the patch; the remainder are + distributed around the perimeter of the patch. + + Patches must be tessellated in Model before they can be correctly + shaded or rendered. + + v is the vertex number for a control point. Sixteen vertex numbers + are required. Positive values indicate absolute vertex numbers. + Negative values indicate relative vertex numbers. + +bzp v1 v2 . . . v16 + + Specifies a Bezier patch. Bezier patches have sixteen control + points, defined as vertices. The control points are distributed + uniformly over its surface. + + Patches must be tessellated in Model before they can be correctly + shaded or rendered. + + v is the vertex number for a control point. Sixteen vertex numbers + are required. Positive values indicate absolute vertex numbers. + Negative values indicate relative vertex numbers. + +cdc v1 v2 v3 v4 v5 . . . + + Specifies a Cardinal curve. Cardinal curves have a minimum of four + control points, defined as vertices. + + Cardinal curves cannot be correctly shaded or rendered. They can be + tessellated and then extruded in Model to create 3D shapes. + + v is the vertex number for a control point. A minimum of four + vertex numbers are required. There is no limit on the maximum. + Positive values indicate absolute vertex numbers. Negative values + indicate relative vertex numbers. + +cdp v1 v2 v3 . . . v16 + + Specifies a Cardinal patch. Cardinal patches have sixteen control + points, defined as vertices. Four of the control points are + attached to the corners of the patch. + + Patches must be tessellated in Model before they can be correctly + shaded or rendered. + + v is the vertex number for a control point. Sixteen vertex numbers + are required. Positive values indicate absolute vertex numbers. + Negative values indicate relative vertex numbers. + +res useg vseg + + Reference and display statement. + + Sets the number of segments for Bezier, B-spline and Cardinal + patches that follow it. + + useg is the number of segments in the u direction (horizontal or x + direction). The minimum setting is 3 and the maximum setting is + 120. The default is 4. + + vseg is the number of segments in the v direction (vertical or y + direction). The minimum setting is 3 and the maximum setting is + 120. The default is 4. + +Comparison of 2.11 and 3.0 syntax + +Cardinal curve + +The following example shows the 2.11 syntax and the 3.0 syntax for the +same Cardinal curve. + +2.11 Cardinal curve + + # 2.11 Cardinal Curve + + v 2.570000 1.280000 0.000000 + v 0.940000 1.340000 0.000000 + v -0.670000 0.820000 0.000000 + v -0.770000 -0.940000 0.000000 + v 1.030000 -1.350000 0.000000 + v 3.070000 -1.310000 0.000000 + # 6 vertices + + cdc 1 2 3 4 5 6 + + +3.0 Cardinal curve + + # 3.0 Cardinal curve + + v 2.570000 1.280000 0.000000 + v 0.940000 1.340000 0.000000 + v -0.670000 0.820000 0.000000 + v -0.770000 -0.940000 0.000000 + v 1.030000 -1.350000 0.000000 + v 3.070000 -1.310000 0.000000 + # 6 vertices + + cstype cardinal + deg 3 + curv 0.000000 3.000000 1 2 3 4 5 6 + parm u 0.000000 1.000000 2.000000 3.000000 + end + # 1 element + +Bezier patch + + The following example shows the 2.11 syntax and the 3.0 syntax for the + same Bezier patch. + +2.11 Bezier patch + + # 2.11 Bezier Patch + v -5.000000 -5.000000 0.000000 + v -5.000000 -1.666667 0.000000 + v -5.000000 1.666667 0.000000 + v -5.000000 5.000000 0.000000 + v -1.666667 -5.000000 0.000000 + v -1.666667 -1.666667 0.000000 + v -1.666667 1.666667 0.000000 + v -1.666667 5.000000 0.000000 + v 1.666667 -5.000000 0.000000 + v 1.666667 -1.666667 0.000000 + v 1.666667 1.666667 0.000000 + v 1.666667 5.000000 0.000000 + v 5.000000 -5.000000 0.000000 + v 5.000000 -1.666667 0.000000 + v 5.000000 1.666667 0.000000 + v 5.000000 5.000000 0.000000 + # 16 vertices + + bzp 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 + # 1 element + +3.0 Bezier patch + + # 3.0 Bezier patch + + v -5.000000 -5.000000 0.000000 + v -5.000000 -1.666667 0.000000 + v -5.000000 1.666667 0.000000 + v -5.000000 5.000000 0.000000 + v -1.666667 -5.000000 0.000000 + v -1.666667 -1.666667 0.000000 + v -1.666667 1.666667 0.000000 + v -1.666667 5.000000 0.000000 + v 1.666667 -5.000000 0.000000 + v 1.666667 -1.666667 0.000000 + v 1.666667 1.666667 0.000000 + v 1.666667 5.000000 0.000000 + v 5.000000 -5.000000 0.000000 + v 5.000000 -1.666667 0.000000 + v 5.000000 1.666667 0.000000 + v 5.000000 5.000000 0.000000 + # 16 vertices + + cstype bezier + deg 3 3 + surf 0.000000 1.000000 0.000000 1.000000 13 14 \ + 15 16 9 10 11 12 5 6 7 8 1 2 3 4 + parm u 0.000000 1.000000 + parm v 0.000000 1.000000 + end + # 1 element + diff --git a/src/osgPlugins/osg/AlphaFunc.cpp b/src/osgPlugins/osg/AlphaFunc.cpp new file mode 100644 index 000000000..2d25aca07 --- /dev/null +++ b/src/osgPlugins/osg/AlphaFunc.cpp @@ -0,0 +1,92 @@ +#include "osg/AlphaFunc" + +#include "osgDB/Registry" +#include "osgDB/Input" +#include "osgDB/Output" + +using namespace osg; +using namespace osgDB; + +// forward declare functions to use later. +bool AlphaFunc_readLocalData(Object& obj, Input& fr); +bool AlphaFunc_writeLocalData(const Object& obj, Output& fw); +bool AlphaFunc_matchFuncStr(const char* str,AlphaFunc::ComparisonFunction& func); +const char* AlphaFunc_getFuncStr(AlphaFunc::ComparisonFunction func); + +// register the read and write functions with the osgDB::Registry. +RegisterDotOsgWrapperProxy g_AlphaFuncProxy +( + new osg::AlphaFunc, + "AlphaFunc", + "Object StateAttribute AlphaFunc", + &AlphaFunc_readLocalData, + &AlphaFunc_writeLocalData +); + + +bool AlphaFunc_readLocalData(Object& obj, Input& fr) +{ + bool iteratorAdvanced = false; + + AlphaFunc& alphaFunc = static_cast(obj); + + AlphaFunc::ComparisonFunction func = alphaFunc.getFunction(); + if (fr[0].matchWord("comparisonFunc") && AlphaFunc_matchFuncStr(fr[1].getStr(),func)) + { + fr+=2; + iteratorAdvanced = true; + } + + float ref = alphaFunc.getReferenceValue(); + if (fr[0].matchWord("referenceValue") && fr[1].getFloat(ref)) + { + fr+=2; + iteratorAdvanced = true; + } + + if (iteratorAdvanced) alphaFunc.setFunction(func,ref); + + return iteratorAdvanced; +} + + +bool AlphaFunc_writeLocalData(const Object& obj,Output& fw) +{ + const AlphaFunc& alphaFunc = static_cast(obj); + + fw.indent() << "comparisonFunc " << AlphaFunc_getFuncStr(alphaFunc.getFunction()) << endl; + fw.indent() << "referenceValue " << alphaFunc.getReferenceValue() << endl; + return true; +} + + +bool AlphaFunc_matchFuncStr(const char* str,AlphaFunc::ComparisonFunction& func) +{ + if (strcmp(str,"NEVER")==0) func = AlphaFunc::NEVER; + else if (strcmp(str,"LESS")==0) func = AlphaFunc::LESS; + else if (strcmp(str,"EQUAL")==0) func = AlphaFunc::EQUAL; + else if (strcmp(str,"LEQUAL")==0) func = AlphaFunc::LEQUAL; + else if (strcmp(str,"GREATER")==0) func = AlphaFunc::GREATER; + else if (strcmp(str,"NOTEQUAL")==0) func = AlphaFunc::NOTEQUAL; + else if (strcmp(str,"GEQUAL")==0) func = AlphaFunc::GEQUAL; + else if (strcmp(str,"ALWAYS")==0) func = AlphaFunc::ALWAYS; + else return false; + return true; +} + + +const char* AlphaFunc_getFuncStr(AlphaFunc::ComparisonFunction func) +{ + switch(func) + { + case(AlphaFunc::NEVER): return "NEVER"; + case(AlphaFunc::LESS): return "LESS"; + case(AlphaFunc::EQUAL): return "EQUAL"; + case(AlphaFunc::LEQUAL): return "LEQUAL"; + case(AlphaFunc::GREATER): return "GREATER"; + case(AlphaFunc::NOTEQUAL): return "NOTEQUAL"; + case(AlphaFunc::GEQUAL): return "GEQUAL"; + case(AlphaFunc::ALWAYS): return "ALWAYS"; + } + return ""; +} diff --git a/src/osgPlugins/osg/Billboard.cpp b/src/osgPlugins/osg/Billboard.cpp new file mode 100644 index 000000000..024f968e3 --- /dev/null +++ b/src/osgPlugins/osg/Billboard.cpp @@ -0,0 +1,136 @@ +#include "osg/Billboard" + +#include "osgDB/Registry" +#include "osgDB/Input" +#include "osgDB/Output" + +using namespace osg; +using namespace osgDB; + +// forward declare functions to use later. +bool Billboard_readLocalData(Object& obj, Input& fr); +bool Billboard_writeLocalData(const Object& obj, Output& fw); + +// register the read and write functions with the osgDB::Registry. +RegisterDotOsgWrapperProxy g_BillboardProxy +( + new osg::Billboard, + "Billboard", + "Object Node Geode Billboard", + &Billboard_readLocalData, + &Billboard_writeLocalData +); + +bool Billboard_readLocalData(Object& obj, Input& fr) +{ + bool iteratorAdvanced = false; + + Billboard& billboard = static_cast(obj); + + if (fr[0].matchWord("Mode")) + { + if (fr[1].matchWord("AXIAL_ROT")) + { + billboard.setMode(Billboard::AXIAL_ROT); + fr+=2; + iteratorAdvanced = true; + } + else if (fr[1].matchWord("POINT_ROT_EYE")) + { + billboard.setMode(Billboard::POINT_ROT_EYE); + fr+=2; + iteratorAdvanced = true; + } + else if (fr[1].matchWord("POINT_ROT_WORLD")) + { + billboard.setMode(Billboard::POINT_ROT_WORLD); + fr+=2; + iteratorAdvanced = true; + } + } + + if (fr[0].matchWord("Axis")) + { + float x,y,z; + if (fr[1].getFloat(x) && fr[2].getFloat(y) && fr[3].getFloat(z)) + { + billboard.setAxis(Vec3(x,y,z)); + fr+=4; + iteratorAdvanced = true; + } + } + + // read the position data. + bool matchFirst = false; + if ((matchFirst=fr.matchSequence("Positions {")) || fr.matchSequence("Positions %i {")) + { + + // set up coordinates. + int entry = fr[0].getNoNestedBrackets(); + + Billboard::PositionList& positionList = billboard.getPositionList(); + positionList.clear(); + + if (matchFirst) + { + fr += 2; + } + else + { + //positionList.(capacity); + fr += 3; + } + + Vec3 pos; + while (!fr.eof() && fr[0].getNoNestedBrackets()>entry) + { + if (fr[0].getFloat(pos[0]) && fr[1].getFloat(pos[1]) && fr[2].getFloat(pos[2])) + { + fr += 3; + positionList.push_back(pos); + } + else + { + ++fr; + } + } + + iteratorAdvanced = true; + ++fr; + + } + + return iteratorAdvanced; +} + + +bool Billboard_writeLocalData(const Object& obj, Output& fw) +{ + + const Billboard& billboard = static_cast(obj); + + switch(billboard.getMode()) + { + case(Billboard::AXIAL_ROT): fw.indent() << "Mode AXIAL_ROT"<(obj); + + if (fr.matchSequence("clipPlaneNum %i")) + { + unsigned int num; + fr[1].getUInt(num); + clipplane.setClipPlaneNum(num); + + fr+=2; + iteratorAdvanced = true; + } + + + if (fr.matchSequence("plane %f %f %f %f")) + { + double plane[4]; + fr[1].getDouble(plane[0]); + fr[2].getDouble(plane[1]); + fr[3].getDouble(plane[2]); + fr[4].getDouble(plane[3]); + clipplane.setClipPlane(plane); + + fr+=5; + iteratorAdvanced = true; + } + + return iteratorAdvanced; +} + + +bool ClipPlane_writeLocalData(const Object& obj,Output& fw) +{ + const ClipPlane& clipplane = static_cast(obj); + + fw.indent() << "clipPlaneNum " << clipplane.getClipPlaneNum() <(obj); + + bool redMask=colormask.getRedMask(); + if (fr[0].matchWord("redMask") && ColorMask_matchModeStr(fr[1].getStr(),redMask)) + { + fr+=2; + iteratorAdvanced = true; + } + + bool greenMask=colormask.getGreenMask(); + if (fr[0].matchWord("greenMask") && ColorMask_matchModeStr(fr[1].getStr(),greenMask)) + { + fr+=2; + iteratorAdvanced = true; + } + + bool blueMask=colormask.getBlueMask(); + if (fr[0].matchWord("blueMask") && ColorMask_matchModeStr(fr[1].getStr(),blueMask)) + { + fr+=2; + iteratorAdvanced = true; + } + + bool alphaMask=colormask.getAlphaMask(); + if (fr[0].matchWord("alphaMask") && ColorMask_matchModeStr(fr[1].getStr(),alphaMask)) + { + fr+=2; + iteratorAdvanced = true; + } + + if (iteratorAdvanced) + { + colormask.setMask(redMask,greenMask,blueMask,alphaMask); + } + + return iteratorAdvanced; +} + + +bool ColorMask_writeLocalData(const Object& obj,Output& fw) +{ + const ColorMask& colormask = static_cast(obj); + + fw.indent() << "redMask " << ColorMask_getModeStr(colormask.getRedMask()) << endl; + fw.indent() << "greenMask " << ColorMask_getModeStr(colormask.getGreenMask()) << endl; + fw.indent() << "blueMask " << ColorMask_getModeStr(colormask.getBlueMask()) << endl; + fw.indent() << "alphaMask " << ColorMask_getModeStr(colormask.getAlphaMask()) << endl; + return true; +} + + +bool ColorMask_matchModeStr(const char* str,bool& mode) +{ + if (strcmp(str,"TRUE")==0) mode = true; + else if (strcmp(str,"FALSE")==0) mode = false; + else if (strcmp(str,"ON")==0) mode = true; + else if (strcmp(str,"OFF")==0) mode = false; + else return false; + return true; +} + + +const char* ColorMask_getModeStr(bool mode) +{ + if (mode) return "ON"; + else return "OFF"; +} diff --git a/src/osgPlugins/osg/CullFace.cpp b/src/osgPlugins/osg/CullFace.cpp new file mode 100644 index 000000000..50dad0d72 --- /dev/null +++ b/src/osgPlugins/osg/CullFace.cpp @@ -0,0 +1,69 @@ +#include "osg/CullFace" + +#include "osgDB/Registry" +#include "osgDB/Input" +#include "osgDB/Output" + +using namespace osg; +using namespace osgDB; + +// forward declare functions to use later. +bool CullFace_readLocalData(Object& obj, Input& fr); +bool CullFace_writeLocalData(const Object& obj, Output& fw); + +// register the read and write functions with the osgDB::Registry. +RegisterDotOsgWrapperProxy g_CullFaceFuncProxy +( + new osg::CullFace, + "CullFace", + "Object StateAttribute CullFace", + &CullFace_readLocalData, + &CullFace_writeLocalData +); + + +bool CullFace_readLocalData(Object& obj,Input& fr) +{ + bool iteratorAdvanced = false; + + CullFace& cullface = static_cast(obj); + + if (fr[0].matchWord("mode")) + { + if (fr[1].matchWord("FRONT")) + { + cullface.setMode(CullFace::FRONT); + fr+=2; + iteratorAdvanced = true; + } + else if (fr[1].matchWord("BACK")) + { + cullface.setMode(CullFace::BACK); + fr+=2; + iteratorAdvanced = true; + } + else if (fr[1].matchWord("FRONT_AND_BACK")) + { + cullface.setMode(CullFace::FRONT_AND_BACK); + fr+=2; + iteratorAdvanced = true; + } + } + + return iteratorAdvanced; +} + + +bool CullFace_writeLocalData(const Object& obj, Output& fw) +{ + + const CullFace& cullface = static_cast(obj); + + switch(cullface.getMode()) + { + case(CullFace::FRONT): fw.indent() << "mode FRONT" << endl; break; + case(CullFace::BACK): fw.indent() << "mode BACK" << endl; break; + case(CullFace::FRONT_AND_BACK): fw.indent() << "mode FRONT_AND_BACK" << endl; break; + } + return true; +} diff --git a/src/osgPlugins/osg/Depth.cpp b/src/osgPlugins/osg/Depth.cpp new file mode 100644 index 000000000..27c301e74 --- /dev/null +++ b/src/osgPlugins/osg/Depth.cpp @@ -0,0 +1,116 @@ +#include "osg/Depth" + +#include "osgDB/Registry" +#include "osgDB/Input" +#include "osgDB/Output" + +using namespace osg; +using namespace osgDB; + +// forward declare functions to use later. +bool Depth_readLocalData(Object& obj, Input& fr); +bool Depth_writeLocalData(const Object& obj, Output& fw); + +bool Depth_matchFuncStr(const char* str,Depth::Function& func); +const char* Depth_getFuncStr(Depth::Function func); + + +// register the read and write functions with the osgDB::Registry. +RegisterDotOsgWrapperProxy g_DepthProxy +( + new osg::Depth, + "Depth", + "Object StateAttribute Depth", + &Depth_readLocalData, + &Depth_writeLocalData +); + + +bool Depth_readLocalData(Object& obj, Input& fr) +{ + bool iteratorAdvanced = false; + + Depth& depth = static_cast(obj); + + Depth::Function func; + if (fr[0].matchWord("function") && Depth_matchFuncStr(fr[1].getStr(),func)) + { + depth.setFunction(func); + fr+=2; + iteratorAdvanced = true; + } + + if (fr[0].matchWord("writeMask")) + { + if (fr[1].matchWord("TRUE") || fr[1].matchWord("ON")) + { + depth.setWriteMask(true); + fr+=2; + iteratorAdvanced = true; + } + else if (fr[1].matchWord("FALSE") || fr[1].matchWord("OFF")) + { + depth.setWriteMask(false); + fr+=2; + iteratorAdvanced = true; + } + } + + double znear,zfar; + if (fr[0].matchWord("range") && fr[1].getDouble(znear) && fr[2].getDouble(zfar)) + { + depth.setRange(znear,zfar); + fr+=2; + iteratorAdvanced = true; + } + + return iteratorAdvanced; +} + + +bool Depth_writeLocalData(const Object& obj,Output& fw) +{ + const Depth& depth = static_cast(obj); + + fw.indent() << "function " << Depth_getFuncStr(depth.getFunction()) << endl; + + fw.indent() << "writeMask "; + if (depth.getWriteMask()) fw << "TRUE" << endl; + else fw << "TRUE" << endl; + + fw.indent() << "range " << depth.getZNear() << " " << depth.getZFar() << endl; + + return true; +} + + +bool Depth_matchFuncStr(const char* str,Depth::Function& func) +{ + if (strcmp(str,"NEVER")==0) func = Depth::NEVER; + else if (strcmp(str,"LESS")==0) func = Depth::LESS; + else if (strcmp(str,"EQUAL")==0) func = Depth::EQUAL; + else if (strcmp(str,"LEQUAL")==0) func = Depth::LEQUAL; + else if (strcmp(str,"GREATER")==0) func = Depth::GREATER; + else if (strcmp(str,"NOTEQUAL")==0) func = Depth::NOTEQUAL; + else if (strcmp(str,"GEQUAL")==0) func = Depth::GEQUAL; + else if (strcmp(str,"ALWAYS")==0) func = Depth::ALWAYS; + else return false; + return true; +} + + +const char* Depth_getFuncStr(Depth::Function func) +{ + switch(func) + { + case(Depth::NEVER): return "NEVER"; + case(Depth::LESS): return "LESS"; + case(Depth::EQUAL): return "EQUAL"; + case(Depth::LEQUAL): return "LEQUAL"; + case(Depth::GREATER): return "GREATER"; + case(Depth::NOTEQUAL): return "NOTEQUAL"; + case(Depth::GEQUAL): return "GEQUAL"; + case(Depth::ALWAYS): return "ALWAYS"; + } + return ""; +} diff --git a/src/osgPlugins/osg/Drawable.cpp b/src/osgPlugins/osg/Drawable.cpp new file mode 100644 index 000000000..ed685dcea --- /dev/null +++ b/src/osgPlugins/osg/Drawable.cpp @@ -0,0 +1,94 @@ +#include "osg/Drawable" + +#include "osgDB/Registry" +#include "osgDB/Input" +#include "osgDB/Output" + +using namespace osg; +using namespace osgDB; + +// forward declare functions to use later. +bool Drawable_readLocalData(Object& obj, Input& fr); +bool Drawable_writeLocalData(const Object& obj, Output& fw); + +// register the read and write functions with the osgDB::Registry. +RegisterDotOsgWrapperProxy g_DrawableFuncProxy +( + /*new osg::Drawable*/NULL, + "Drawable", + "Object Drawable", + &Drawable_readLocalData, + &Drawable_writeLocalData +); + +bool Drawable_readLocalData(Object& obj, Input& fr) +{ + bool iteratorAdvanced = false; + + Drawable& drawable = static_cast(obj); + + static ref_ptr s_drawstate = new osg::StateSet; + if (StateSet* readState = static_cast(fr.readObjectOfType(*s_drawstate))) + { + drawable.setStateSet(readState); + iteratorAdvanced = true; + } + + if (fr[0].matchWord("supportsDisplayList")) + { + if (fr[1].matchWord("TRUE")) + { + drawable.setSupportsDisplayList(true); + fr+=2; + iteratorAdvanced = true; + } + else if (fr[1].matchWord("FALSE")) + { + drawable.setSupportsDisplayList(false); + fr+=2; + iteratorAdvanced = true; + } + } + + if (fr[0].matchWord("useDisplayList")) + { + if (fr[1].matchWord("TRUE")) + { + drawable.setUseDisplayList(true); + fr+=2; + iteratorAdvanced = true; + } + else if (fr[1].matchWord("FALSE")) + { + drawable.setUseDisplayList(false); + fr+=2; + iteratorAdvanced = true; + } + } + + return iteratorAdvanced; +} + + +bool Drawable_writeLocalData(const Object& obj, Output& fw) +{ + const Drawable& drawable = static_cast(obj); + + if (drawable.getStateSet()) + { + fw.writeObject(*drawable.getStateSet()); + } + + if (!drawable.getSupportsDisplayList()) + { + fw.indent()<<"supportsDisplayList "; + if (drawable.getSupportsDisplayList()) fw << "TRUE" <(obj); + + Fog::Mode mode; + if (fr[0].matchWord("mode") && Fog_matchModeStr(fr[1].getStr(),mode)) + { + fog.setMode(mode); + fr+=2; + iteratorAdvanced = true; + } + + float value; + if (fr[0].matchWord("density") && fr[1].getFloat(value)) + { + fog.setDensity(value); + fr+=2; + iteratorAdvanced = true; + } + + if (fr[0].matchWord("start") && fr[1].getFloat(value)) + { + fog.setStart(value); + fr+=2; + iteratorAdvanced = true; + } + + if (fr[0].matchWord("end") && fr[1].getFloat(value)) + { + fog.setEnd(value); + fr+=2; + iteratorAdvanced = true; + } + + if (fr.matchSequence("color %f %f %f %f")) + { + osg::Vec4 color; + fr[1].getFloat(color[0]); + fr[2].getFloat(color[1]); + fr[3].getFloat(color[2]); + fr[4].getFloat(color[3]); + fog.setColor(color); + fr+=5; + iteratorAdvanced = true; + } + + return iteratorAdvanced; +} + + +bool Fog_writeLocalData(const Object& obj,Output& fw) +{ + const Fog& fog = static_cast(obj); + + fw.indent() << "mode " << Fog_getModeStr(fog.getMode()) << endl; + fw.indent() << "density " << fog.getDensity() << endl; + fw.indent() << "start " << fog.getStart() << endl; + fw.indent() << "end " << fog.getEnd() << endl; + fw.indent() << "color " << fog.getColor() << endl; + return true; +} + + +bool Fog_matchModeStr(const char* str,Fog::Mode& mode) +{ + if (strcmp(str,"LINEAR")==0) mode = Fog::LINEAR; + else if (strcmp(str,"EXP")==0) mode = Fog::EXP; + else if (strcmp(str,"EXP2")==0) mode = Fog::EXP2; + else return false; + return true; +} + + +const char* Fog_getModeStr(Fog::Mode mode) +{ + switch(mode) + { + case(Fog::LINEAR): return "NEVER"; + case(Fog::EXP): return "EXP"; + case(Fog::EXP2): return "EXP2"; + } + return ""; +} diff --git a/src/osgPlugins/osg/FrontFace.cpp b/src/osgPlugins/osg/FrontFace.cpp new file mode 100644 index 000000000..05ca03b3a --- /dev/null +++ b/src/osgPlugins/osg/FrontFace.cpp @@ -0,0 +1,60 @@ +#include "osg/FrontFace" + +#include "osgDB/Registry" +#include "osgDB/Input" +#include "osgDB/Output" + +using namespace osg; +using namespace osgDB; + +// forward declare functions to use later. +bool FrontFace_readLocalData(Object& obj, Input& fr); +bool FrontFace_writeLocalData(const Object& obj, Output& fw); + +// register the read and write functions with the osgDB::Registry. +RegisterDotOsgWrapperProxy g_FrontFaceProxy +( + new osg::FrontFace, + "FrontFace", + "Object StateAttribute FrontFace", + &FrontFace_readLocalData, + &FrontFace_writeLocalData +); + +bool FrontFace_readLocalData(Object& obj, Input& fr) +{ + bool iteratorAdvanced = false; + + FrontFace& frontface = static_cast(obj); + + if (fr[0].matchWord("mode")) + { + if (fr[1].matchWord("CLOCKWISE")) + { + frontface.setMode(FrontFace::CLOCKWISE); + fr+=2; + iteratorAdvanced = true; + } + else if (fr[1].matchWord("COUNTER_CLOCKWISE")) + { + frontface.setMode(FrontFace::COUNTER_CLOCKWISE); + fr+=2; + iteratorAdvanced = true; + } + } + + return iteratorAdvanced; +} + + +bool FrontFace_writeLocalData(const Object& obj, Output& fw) +{ + const FrontFace& frontface = static_cast(obj); + + switch(frontface.getMode()) + { + case(FrontFace::CLOCKWISE): fw.indent() << "mode CLOCKWISE" << endl; break; + case(FrontFace::COUNTER_CLOCKWISE): fw.indent() << "mode COUNTER_CLOCKWISE" << endl; break; + } + return true; +} diff --git a/src/osgPlugins/osg/GeoSet.cpp b/src/osgPlugins/osg/GeoSet.cpp new file mode 100644 index 000000000..ad481a017 --- /dev/null +++ b/src/osgPlugins/osg/GeoSet.cpp @@ -0,0 +1,1093 @@ +#if defined(_MSC_VER) + #pragma warning( disable : 4786 ) +#endif + +#include "osg/GeoSet" +#include "osg/Types" +#include "osg/Notify" + +#include "osgDB/Registry" +#include "osgDB/Input" +#include "osgDB/Output" + +using namespace osg; +using namespace osgDB; + +// forward declare functions to use later. +bool GeoSet_readLocalData(Object& obj, Input& fr); +bool GeoSet_writeLocalData(const Object& obj, Output& fw); + +bool GeoSet_readIndexData(Input& fr, const char* IndexName, GeoSet::IndexPointer& ip, bool& useCIndex); +bool GeoSet_writeIndexData(Output& fw, const char* IndexName,const GeoSet::IndexPointer& ip); +bool GeoSet_matchBindingTypeStr(const char* str,GeoSet::BindingType& mode); +const char* GeoSet_getBindingTypeStr(GeoSet::BindingType mode); +const char* GeoSet_getInterleavedRowComposition(GeoSet::InterleaveArrayType at); +int GeoSet_getInterleavedRowLength(GeoSet::InterleaveArrayType at); + +// register the read and write functions with the osgDB::Registry. +RegisterDotOsgWrapperProxy g_GeoSetFuncProxy +( + new osg::GeoSet, + "GeoSet", + "Object Drawable GeoSet", + &GeoSet_readLocalData, + &GeoSet_writeLocalData, + DotOsgWrapper::READ_AND_WRITE +); + +// register the old style 'Geoset' keyword read and write functions with the osgDB::Registry. +RegisterDotOsgWrapperProxy g_GeosetFuncProxy +( + new osg::GeoSet, + "Geoset", + "Object Drawable Geoset", + &GeoSet_readLocalData, + NULL, + DotOsgWrapper::READ_ONLY +); + +bool GeoSet_readLocalData(Object& obj, Input& fr) +{ + bool iteratorAdvanced = false; + + GeoSet& geoset = static_cast(obj); + + Vec3* coordList = NULL; + bool coordIndexUseCIndex = false; + GeoSet::IndexPointer coordIndex; + Vec3* normalList = NULL; + bool normIndexUseCIndex = false; + GeoSet::IndexPointer normIndex; + Vec4* colorList = NULL; + bool colIndexUseCIndex = false; + GeoSet::IndexPointer colIndex; + Vec2* textureList = NULL; + bool tIndexUseCIndex = false; + GeoSet::IndexPointer tIndex; + float* interleavedArray = NULL; + bool iaIndexUseCIndex = false; + GeoSet::IndexPointer iaIndex; + + GeoSet::BindingType bind=GeoSet::BIND_OFF; + GeoSet::BindingType normal_bind=GeoSet::BIND_OFF; + GeoSet::BindingType color_bind=GeoSet::BIND_OFF; + GeoSet::BindingType texture_bind=GeoSet::BIND_OFF; + GeoSet::InterleaveArrayType iaType = GeoSet::IA_OFF; + + int start_indent = fr[0].getNoNestedBrackets(); + while (!fr.eof() && fr[0].getNoNestedBrackets()>=start_indent) + { + + bool fieldAdvanced = false; + + bool readPrimitiveLengths = false; + if (fr.matchSequence("tstrips %i {")) + { + readPrimitiveLengths = true; + geoset.setPrimType(GeoSet::TRIANGLE_STRIP); + } + else if (fr.matchSequence("flat_tstrips %i {")) + { + readPrimitiveLengths = true; + geoset.setPrimType(GeoSet::FLAT_TRIANGLE_STRIP); + } + else if (fr.matchSequence("polys %i {")) + { + readPrimitiveLengths = true; + geoset.setPrimType(GeoSet::POLYGON); + } + else if (fr.matchSequence("quadstrip %i {")) + { + readPrimitiveLengths = true; + geoset.setPrimType(GeoSet::QUAD_STRIP); + } + else if (fr.matchSequence("lineloops %i {")) + { + readPrimitiveLengths = true; + geoset.setPrimType(GeoSet::LINE_LOOP); + } + else if (fr.matchSequence("linestrip %i {")) + { + readPrimitiveLengths = true; + geoset.setPrimType(GeoSet::LINE_STRIP); + } + else if (fr.matchSequence("flat_linestrip %i {")) + { + readPrimitiveLengths = true; + geoset.setPrimType(GeoSet::LINE_STRIP); + } + else if (fr.matchSequence("tfans %i {")) + { + readPrimitiveLengths = true; + geoset.setPrimType(GeoSet::TRIANGLE_FAN); + } + else if (fr.matchSequence("flat_tfans %i {")) + { + readPrimitiveLengths = true; + geoset.setPrimType(GeoSet::FLAT_TRIANGLE_FAN); + } + + if (readPrimitiveLengths) + { + + int entry = fr[1].getNoNestedBrackets(); + fr += 3; + + int capacity; + if (!fr[1].getInt(capacity)) capacity=100; + int size = 0; + int* list = new int [capacity]; + + while (!fr.eof() && fr[0].getNoNestedBrackets()>entry) + { + int primLength; + if (fr[0].getInt(primLength)) + { + + if (size>=capacity) + { + int oldCapacity = capacity; + while(capacity<=size) capacity *= 2; + int* oldList = list; + list = new int[capacity]; + for(int i=0;ientry) + { + float x,y,z; + if (fr[0].getFloat(x) && fr[1].getFloat(y) && fr[2].getFloat(z)) + { + fr += 3; + + if (size>=capacity) + { + int oldCapacity = capacity; + while(capacity<=size) capacity *= 2; + Vec3* oldList = coordList; + coordList = new Vec3[capacity]; + for(int i=0;ientry) + { + float x,y,z; + if (fr[0].getFloat(x) && fr[1].getFloat(y) && fr[2].getFloat(z)) + { + fr += 3; + + if (size>=capacity) + { + int oldCapacity = capacity; + while(capacity<=size) capacity *= 2; + Vec3* oldList = normalList; + normalList = new Vec3[capacity]; + for(int i=0;ientry) + { + float r,g,b,a; + if (fr[0].getFloat(r) && fr[1].getFloat(g) && fr[2].getFloat(b) && fr[3].getFloat(a)) + { + + fr += 4; + + if (size>=capacity) + { + int oldCapacity = capacity; + while(capacity<=size) capacity *= 2; + Vec4* oldList = colorList; + colorList = new Vec4[capacity]; + for(int i=0;ientry) + { + float r,s; + if (fr[0].getFloat(r) && fr[1].getFloat(s)) + { + fr += 2; + if (size>=capacity) + { + int oldCapacity = capacity; + while(capacity<=size) capacity *= 2; + Vec2* oldList = textureList; + textureList = new Vec2[capacity]; + for(int i=0;ientry) ++fr; + } + else + { + // now read the data rows between the {}. + const char* rowComp = GeoSet_getInterleavedRowComposition(iaType); + int rowLength = GeoSet_getInterleavedRowLength(iaType); + + int size = 0; + unsigned char* dataList = new unsigned char[capacity*rowLength]; + + unsigned char* rowData = new unsigned char [rowLength]; + + float floatData; + int intData; + while (!fr.eof() && fr[0].getNoNestedBrackets()>entry) + { + + unsigned char* itrRowData = rowData; + const char* itrRowComp = rowComp; + int rn = 0; + while (*itrRowComp!=0) + { + if (*itrRowComp=='f') + { + + if (!fr[rn].getFloat(floatData)) break; + *(float*)itrRowData = floatData; + itrRowData += 4; + } + else + { + if (!fr[rn].getInt(intData)) break; + *itrRowData = (unsigned char)intData; + itrRowData += 1; + } + ++rn; + } + if (*itrRowComp==0) + { + fr += rn; + if (size>=capacity) + { + int oldCapacity = capacity; + while(capacity<=size) capacity *= 2; + unsigned char* oldList = dataList; + dataList = new unsigned char[capacity*rowLength]; + memcpy(dataList,oldList,oldCapacity*rowLength); + delete [] oldList; + } + memcpy(dataList+size*rowLength,rowData,rowLength); + ++size; + + } + else + { + ++fr; + } + } + + interleavedArray = (float*)dataList; + } + + fieldAdvanced = true; + ++fr; + + } + + if (GeoSet_readIndexData(fr, "InterleavedArrayIndex" ,iaIndex, iaIndexUseCIndex)) + { + fieldAdvanced = true; + } + + if (!fieldAdvanced) + { + if (fr[0].getNoNestedBrackets()>start_indent) fr.advanceToEndOfBlock(start_indent+1); + else ++fr; + } + iteratorAdvanced = true; + + } + + // set up the coord lists. + if (coordList) + { + geoset.setCoords(coordList,coordIndex); + } + + // set up the normal lists. + if (normalList) + { + geoset.setNormalBinding(normal_bind); + if (normIndexUseCIndex) geoset.setNormals(normalList,coordIndex); + else geoset.setNormals(normalList,normIndex); + + } else geoset.setNormalBinding(GeoSet::BIND_OFF); + + // set up the color lists. + if (colorList) + { + geoset.setColorBinding(color_bind); + if (colIndexUseCIndex) geoset.setColors(colorList,coordIndex); + else geoset.setColors(colorList,colIndex); + + } else geoset.setColorBinding(GeoSet::BIND_OFF); + + if (textureList) + { + geoset.setTextureBinding(texture_bind); + if (tIndexUseCIndex) geoset.setTextureCoords(textureList,coordIndex); + else geoset.setTextureCoords(textureList,tIndex); + + } else geoset.setTextureBinding(GeoSet::BIND_OFF); + + if (interleavedArray) + { + if (iaIndexUseCIndex) geoset.setInterleavedArray(iaType,interleavedArray,coordIndex); + else geoset.setInterleavedArray(iaType,interleavedArray,iaIndex); + + }; + + return iteratorAdvanced; +} + + +bool GeoSet_writeLocalData(const Object& obj, Output& fw) +{ + int i; + + const GeoSet& geoset = static_cast(obj); + + // write out primitives. + bool writeOutPrimitiveLengths = false; + switch(geoset.getPrimType()) + { + case (GeoSet::TRIANGLE_STRIP): + fw.indent()<<"tstrips "<< geoset.getNumPrims() << endl; + writeOutPrimitiveLengths = true; + break; + case (GeoSet::FLAT_TRIANGLE_STRIP): + fw.indent()<<"flat_tstrips "<< geoset.getNumPrims() << endl; + writeOutPrimitiveLengths = true; + break; + case (GeoSet::POLYGON): + fw.indent()<<"polys "<< geoset.getNumPrims() << endl; + writeOutPrimitiveLengths = true; + break; + case (GeoSet::QUAD_STRIP): + fw.indent()<<"quadstrip "<< geoset.getNumPrims() << endl; + writeOutPrimitiveLengths = true; + break; + case (GeoSet::LINE_LOOP): + fw.indent()<<"lineloops "<< geoset.getNumPrims() << endl; + writeOutPrimitiveLengths = true; + break; + case (GeoSet::LINE_STRIP): + fw.indent()<<"linestrip "<< geoset.getNumPrims() << endl; + writeOutPrimitiveLengths = false; + break; + case (GeoSet::FLAT_LINE_STRIP): + fw.indent()<<"flat_linestrip "<< geoset.getNumPrims() << endl; + writeOutPrimitiveLengths = false; + break; + case (GeoSet::TRIANGLE_FAN): + fw.indent()<<"tfans "<< geoset.getNumPrims() << endl; + writeOutPrimitiveLengths = true; + case (GeoSet::FLAT_TRIANGLE_FAN): + fw.indent()<<"flat_tfans "<< geoset.getNumPrims() << endl; + writeOutPrimitiveLengths = true; + break; + case (GeoSet::LINES): + fw.indent()<<"lines "<< geoset.getNumPrims() << endl; + writeOutPrimitiveLengths = false; + break; + case (GeoSet::TRIANGLES): + fw.indent()<<"triangles "<< geoset.getNumPrims() << endl; + writeOutPrimitiveLengths = false; + break; + case (GeoSet::QUADS): + fw.indent()<<"quads "<< geoset.getNumPrims() << endl; + writeOutPrimitiveLengths = false; + break; + case (GeoSet::POINTS) : + fw.indent()<<"points "<< geoset.getNumPrims() << endl; + break; + default: + notify(WARN) << "GeoSet::writeLocalData() - unhandled primitive type = "<<(int)geoset.getPrimType()<(geoset); + non_const_geoset.computeNumVerts(); + + if (geoset.getCoords()) + { + // write out _coords. + fw.indent() << "Coords " << geoset.getNumCoords()<entry) + { + int index; + if (fr[0].getInt(index)) + { + + if (size>=capacity) + { + int oldCapacity = capacity; + while(capacity<=size) capacity *= 2; + osg::ushort* oldList = coordIndexList; + coordIndexList = new osg::ushort[capacity]; + for(int i=0;ientry) + { + int index; + if (fr[0].getInt(index)) + { + + if (size>=capacity) + { + int oldCapacity = capacity; + while(capacity<=size) capacity *= 2; + osg::uint* oldList = coordIndexList; + coordIndexList = new osg::uint[capacity]; + for(int i=0;i(obj); + + int num_drawables; + if ((fr[0].matchWord("num_drawables") || fr[0].matchWord("num_geosets")) && + fr[1].getInt(num_drawables)) + { + // could allocate space for children here... + fr+=2; + iteratorAdvanced = true; + } + + Drawable* drawable = NULL; + while((drawable=fr.readDrawable())!=NULL) + { + geode.addDrawable(drawable); + iteratorAdvanced = true; + } + + return iteratorAdvanced; +} + + +bool Geode_writeLocalData(const osg::Object& obj, Output& fw) +{ + const Geode& geode = static_cast(obj); + + fw.indent() << "num_drawables " << geode.getNumDrawables() << endl; + + for(int i=0;i(obj); + + int num_children; + if (fr[0].matchWord("num_children") && + fr[1].getInt(num_children)) + { + // could allocate space for children here... + fr+=2; + iteratorAdvanced = true; + } + + Node* node = NULL; + while((node=fr.readNode())!=NULL) + { + group.addChild(node); + iteratorAdvanced = true; + } + + return iteratorAdvanced; +} + + +bool Group_writeLocalData(const Object& obj, Output& fw) +{ + const Group& group = static_cast(obj); + + fw.indent() << "num_children " << group.getNumChildren() << endl; + for(int i=0;i(obj); + + // no current image reading code + // as it is all handled by osg::Registry::readImage() via plugins. + + return iteratorAdvanced; +} + + +bool Image_writeLocalData(const Object& /*obj*/, Output& /*fw*/) +{ + // const Image& image = static_cast(obj); + + // no current image writing code here + // as it is all handled by osg::Registry::writeImage() via plugins. + + return true; +} diff --git a/src/osgPlugins/osg/Impostor.cpp b/src/osgPlugins/osg/Impostor.cpp new file mode 100644 index 000000000..883b597be --- /dev/null +++ b/src/osgPlugins/osg/Impostor.cpp @@ -0,0 +1,51 @@ +#include "osg/Impostor" + +#include "osgDB/Registry" +#include "osgDB/Input" +#include "osgDB/Output" + +using namespace osg; +using namespace osgDB; + +// forward declare functions to use later. +bool Impostor_readLocalData(Object& obj, Input& fr); +bool Impostor_writeLocalData(const Object& obj, Output& fw); + +// register the read and write functions with the osgDB::Registry. +RegisterDotOsgWrapperProxy g_ImpostorProxy +( + new osg::Impostor, + "Impostor", + "Object Node Impostor LOD Group", + &Impostor_readLocalData, + &Impostor_writeLocalData +); + +bool Impostor_readLocalData(Object& obj, Input& fr) +{ + bool iteratorAdvanced = false; + + Impostor& impostor = static_cast(obj); + + if (fr.matchSequence("ImpostorThreshold %f")) + { + float threshold; + fr[1].getFloat(threshold); + impostor.setImpostorThreshold(threshold); + + iteratorAdvanced = true; + fr+=2; + } + + return iteratorAdvanced; +} + + +bool Impostor_writeLocalData(const Object& obj, Output& fw) +{ + const Impostor& impostor = static_cast(obj); + + fw.indent() << "ImpostorThreshold "<< impostor.getImpostorThreshold() <(obj); + + if (fr.matchSequence("Center %f %f %f")) + { + Vec3 center; + fr[1].getFloat(center[0]); + fr[2].getFloat(center[1]); + fr[3].getFloat(center[2]); + lod.setCenter(center); + + iteratorAdvanced = true; + fr+=4; + } + + bool matchFirst = false; + if ((matchFirst=fr.matchSequence("Ranges {")) || fr.matchSequence("Ranges %i {")) + { + + // set up coordinates. + int entry = fr[0].getNoNestedBrackets(); + + if (matchFirst) + { + fr += 2; + } + else + { + //_rangeList.(capacity); + fr += 3; + } + + float range; + int i=0; + while (!fr.eof() && fr[0].getNoNestedBrackets()>entry) + { + if (fr[0].getFloat(range)) + { + lod.setRange(i,range); + ++fr; + ++i; + } + else + { + ++fr; + } + } + + iteratorAdvanced = true; + ++fr; + + } + + return iteratorAdvanced; +} + + +bool LOD_writeLocalData(const Object& obj, Output& fw) +{ + const LOD& lod = static_cast(obj); + + fw.indent() << "Center "<< lod.getCenter() <(obj); + + +#define ReadVec4(A,B) { \ + if (fr[0].matchWord(B) && \ + fr[1].getFloat(vec4[0]) && \ + fr[2].getFloat(vec4[1]) && \ + fr[3].getFloat(vec4[2]) && \ + fr[4].getFloat(vec4[3])) \ + { \ + light.A(vec4); \ + fr+=5; \ + iteratorAdvanced = true; \ + } \ +} + +#define ReadVec3(A,B) { \ + if (fr[0].matchWord(B) && \ + fr[1].getFloat(vec3[0]) && \ + fr[2].getFloat(vec3[1]) && \ + fr[3].getFloat(vec4[2])) \ + { \ + light.A(vec3); \ + fr+=4; \ + iteratorAdvanced = true; \ + } \ +} + +#define ReadFloat(A,B) { \ + if (fr[0].matchWord(B) && \ + fr[1].getFloat(value)) \ + { \ + light.A(value); \ + fr+=4; \ + iteratorAdvanced = true; \ + } \ +} + + Vec4 vec4; + ReadVec4(setAmbient,"ambient") + ReadVec4(setDiffuse,"diffuse") + ReadVec4(setSpecular,"specular") + ReadVec4(setPosition,"position") + + Vec3 vec3; + ReadVec3(setDirection,"direction") + + float value; + ReadFloat(setConstantAttenuation,"constant_attenuation") + ReadFloat(setLinearAttenuation,"linear_attenuation") + ReadFloat(setQuadraticAttenuation,"quadratic_attenuation") + ReadFloat(setSpotExponent,"spot_exponent") + ReadFloat(setSpotCutoff,"spot_cutoff") + +#undef ReadVec4 +#undef ReadVec3 +#undef ReadFloat + + return iteratorAdvanced; +} + + +bool Light_writeLocalData(const Object& obj,Output& fw) +{ + const Light& light = static_cast(obj); + + // Vec4's + fw.indent() << "ambient " << light.getAmbient() << endl; + fw.indent() << "diffuse " << light.getDiffuse() << endl; + fw.indent() << "specular " << light.getSpecular() << endl; + fw.indent() << "position " << light.getPosition() << endl; + + // Vec3's + fw.indent() << "direction " << light.getDirection() << endl; + + // float's + fw.indent() << "constant_attenuation " << light.getConstantAttenuation() << endl; + fw.indent() << "linear_attenuation " << light.getLinearAttenuation () << endl; + fw.indent() << "quadratic_attenuation " << light.getQuadraticAttenuation() << endl; + fw.indent() << "spot_exponent " << light.getSpotExponent() << endl; + fw.indent() << "spot_cutoff " << light.getSpotCutoff() << endl; + + return true; +} diff --git a/src/osgPlugins/osg/LightSource.cpp b/src/osgPlugins/osg/LightSource.cpp new file mode 100644 index 000000000..3011796bb --- /dev/null +++ b/src/osgPlugins/osg/LightSource.cpp @@ -0,0 +1,50 @@ +#include "osg/LightSource" + +#include "osgDB/Registry" +#include "osgDB/Input" +#include "osgDB/Output" + +using namespace osg; +using namespace osgDB; + +// forward declare functions to use later. +bool LightSource_readLocalData(Object& obj, Input& fr); +bool LightSource_writeLocalData(const Object& obj, Output& fw); + +// register the read and write functions with the osgDB::Registry. +RegisterDotOsgWrapperProxy g_LightSourceProxy +( + new osg::LightSource, + "LightSource", + "Object Node LightSource", + &LightSource_readLocalData, + &LightSource_writeLocalData +); + +bool LightSource_readLocalData(Object& obj, Input& fr) +{ + bool iteratorAdvanced = false; + + LightSource& lightsource = static_cast(obj); + + static ref_ptr s_light = new osg::Light; + + Light* light = static_cast(fr.readObjectOfType(*s_light)); + if (light) + { + lightsource.setLight(light); + iteratorAdvanced = true; + } + + return iteratorAdvanced; +} + + +bool LightSource_writeLocalData(const Object& obj, Output& fw) +{ + const LightSource& lightsource = static_cast(obj); + + if (lightsource.getLight()) fw.writeObject(*lightsource.getLight()); + + return true; +} diff --git a/src/osgPlugins/osg/Makedepend b/src/osgPlugins/osg/Makedepend new file mode 100644 index 000000000..e69de29bb diff --git a/src/osgPlugins/osg/Makefile b/src/osgPlugins/osg/Makefile new file mode 100644 index 000000000..625c38349 --- /dev/null +++ b/src/osgPlugins/osg/Makefile @@ -0,0 +1,51 @@ +#!smake +include ../../../Make/makedefs + +C++FILES = \ + AlphaFunc.cpp\ + Billboard.cpp\ + ClipPlane.cpp\ + ColorMask.cpp\ + CullFace.cpp\ + Depth.cpp\ + Drawable.cpp\ + Fog.cpp\ + FrontFace.cpp\ + Geode.cpp\ + GeoSet.cpp\ + Group.cpp\ + Image.cpp\ + Impostor.cpp\ + Light.cpp\ + LightSource.cpp\ + LOD.cpp\ + Material.cpp\ + Matrix.cpp\ + Node.cpp\ + Object.cpp\ + Point.cpp\ + PolygonMode.cpp\ + PolygonOffset.cpp\ + ReaderWriterOSG.cpp\ + StateSet.cpp\ + Stencil.cpp\ + Switch.cpp\ + TexEnv.cpp\ + TexGen.cpp\ + TexMat.cpp\ + Texture.cpp\ + Transform.cpp\ + Transparency.cpp\ + +LIB = ../../../lib/osgPlugins/osgdb_osg.so + +TARGET_LOADER_FILES = osgPlugins/osgdb_osg.so + +LIBS = +C++FLAGS += -I. -I../../../include +LDFLAGS += -L../../../lib + +include ../../../Make/makerules + + + diff --git a/src/osgPlugins/osg/Material.cpp b/src/osgPlugins/osg/Material.cpp new file mode 100644 index 000000000..c5515207e --- /dev/null +++ b/src/osgPlugins/osg/Material.cpp @@ -0,0 +1,253 @@ +#if defined(_MSC_VER) + #pragma warning( disable : 4786 ) +#endif + +#include "osg/Material" + +#include "osgDB/Registry" +#include "osgDB/Input" +#include "osgDB/Output" + +using namespace osg; +using namespace osgDB; + +// forward declare functions to use later. +bool Material_readLocalData(Object& obj, Input& fr); +bool Material_writeLocalData(const Object& obj, Output& fw); +bool Material_matchFaceAndColor(Input& fr,const char* name,Material::Face& mf,Vec4& color); + +// register the read and write functions with the osgDB::Registry. +RegisterDotOsgWrapperProxy g_MaterialProxy +( + new osg::Material, + "Material", + "Object StateAttribute Material", + &Material_readLocalData, + &Material_writeLocalData +); + + +bool Material_readLocalData(Object& obj, Input& fr) +{ + bool iteratorAdvanced = false; + + Material& material = static_cast(obj); + + Vec4 data(0.0f, 0.0f, 0.0f, 1.0f); + Material::Face mf = Material::FRONT_AND_BACK; + + if (fr[0].matchWord("ColorMode")) + { + if (fr[1].matchWord("AMBIENT")) + { + material.setColorMode(Material::AMBIENT); + fr+=2; + iteratorAdvanced = true; + } + else if (fr[1].matchWord("DIFFUSE")) + { + material.setColorMode(Material::DIFFUSE); + fr+=2; + iteratorAdvanced = true; + } + else if (fr[1].matchWord("SPECULAR")) + { + material.setColorMode(Material::SPECULAR); + fr+=2; + iteratorAdvanced = true; + } + else if (fr[1].matchWord("EMISSION")) + { + material.setColorMode(Material::EMISSION); + fr+=2; + iteratorAdvanced = true; + } + else if (fr[1].matchWord("AMBIENT_AND_DIFFUSE")) + { + material.setColorMode(Material::AMBIENT_AND_DIFFUSE); + fr+=2; + iteratorAdvanced = true; + } + else if (fr[1].matchWord("OFF")) + { + material.setColorMode(Material::OFF); + fr+=2; + iteratorAdvanced = true; + } + + } + + if (Material_matchFaceAndColor(fr,"ambientColor",mf,data)) + { + material.setAmbient(mf,data); + iteratorAdvanced = true; + } + + if (Material_matchFaceAndColor(fr,"diffuseColor",mf,data)) + { + material.setDiffuse(mf,data); + iteratorAdvanced = true; + } + + if (Material_matchFaceAndColor(fr,"specularColor",mf,data)) + { + material.setSpecular(mf,data); + iteratorAdvanced = true; + } + + if (Material_matchFaceAndColor(fr,"emissionColor",mf,data) || + Material_matchFaceAndColor(fr,"emissiveColor",mf,data)) + { + material.setEmission(mf,data); + iteratorAdvanced = true; + } + + if (Material_matchFaceAndColor(fr,"ambientColor",mf,data)) + { + material.setAmbient(mf,data); + iteratorAdvanced = true; + } + + float shininess = 0.0f; + if (fr[0].matchWord("shininess")) + { + + mf = Material::FRONT_AND_BACK; + int fr_inc = 1; + + if (fr[1].matchWord("FRONT")) + { + mf = Material::FRONT; + ++fr_inc; + } + else if (fr[1].matchWord("BACK")) + { + mf = Material::BACK; + ++fr_inc; + } + + if (fr[fr_inc].getFloat(shininess)) + { + fr+=(fr_inc+1); + material.setShininess(mf,shininess); + iteratorAdvanced = true; + } + + } + + float transparency = 0.0f; + if (fr[0].matchWord("transparency") && fr[1].getFloat(transparency)) + { + + material.setTransparency(Material::FRONT_AND_BACK,transparency); + + fr+=2; + iteratorAdvanced = true; + } + + return iteratorAdvanced; + +} + +bool Material_matchFaceAndColor(Input& fr,const char* name,Material::Face& mf,Vec4& color) +{ + bool iteratorAdvanced = false; + + if (fr[0].matchWord(name)) + { + int fr_inc = 1; + if (fr[1].matchWord("FRONT")) + { + mf = Material::FRONT; + ++fr_inc; + } + else if (fr[1].matchWord("BACK")) + { + mf = Material::BACK; + ++fr_inc; + } + + if (fr[fr_inc].getFloat(color[0]) && fr[fr_inc+1].getFloat(color[1]) && fr[fr_inc+2].getFloat(color[2])) + { + fr_inc += 3; + + if (fr[fr_inc].getFloat(color[3])) ++fr_inc; + else color[3] = 1.0f; + + fr+=fr_inc; + + iteratorAdvanced = true; + } + } + + return iteratorAdvanced; +} + + +bool Material_writeLocalData(const Object& obj, Output& fw) +{ + + const Material& material = static_cast(obj); + + switch(material.getColorMode()) + { + case(Material::AMBIENT): fw.indent() << "ColorMode AMBIENT" << endl; break; + case(Material::DIFFUSE): fw.indent() << "ColorMode DIFFUSE" << endl; break; + case(Material::SPECULAR): fw.indent() << "ColorMode SPECULAR" << endl; break; + case(Material::EMISSION): fw.indent() << "ColorMode EMISSION" << endl; break; + case(Material::AMBIENT_AND_DIFFUSE): fw.indent() << "ColorMode AMBIENT_AND_DIFFUSE" << endl; break; + case(Material::OFF): fw.indent() << "ColorMode OFF" << endl; break; + } + + if (material.getAmbientFrontAndBack()) + { + fw.indent() << "ambientColor " << material.getAmbient(Material::FRONT) << endl; + } + else + { + fw.indent() << "ambientColor FRONT " << material.getAmbient(Material::FRONT) << endl; + fw.indent() << "ambientColor BACK " << material.getAmbient(Material::BACK) << endl; + } + + if (material.getDiffuseFrontAndBack()) + { + fw.indent() << "diffuseColor " << material.getDiffuse(Material::FRONT) << endl; + } + else + { + fw.indent() << "diffuseColor FRONT " << material.getDiffuse(Material::FRONT) << endl; + fw.indent() << "diffuseColor BACK " << material.getDiffuse(Material::BACK) << endl; + } + + if (material.getSpecularFrontAndBack()) + { + fw.indent() << "specularColor " << material.getSpecular(Material::FRONT) << endl; + } + else + { + fw.indent() << "specularColor FRONT " << material.getSpecular(Material::FRONT) << endl; + fw.indent() << "specularColor BACK " << material.getSpecular(Material::BACK) << endl; + } + + if (material.getEmissionFrontAndBack()) + { + fw.indent() << "emissionColor " << material.getEmission(Material::FRONT) << endl; + } + else + { + fw.indent() << "emissionColor FRONT " << material.getEmission(Material::FRONT) << endl; + fw.indent() << "emissionColor BACK " << material.getEmission(Material::BACK) << endl; + } + + if (material.getShininessFrontAndBack()) + { + fw.indent() << "shininess " << material.getShininess(Material::FRONT) << endl; + } + else + { + fw.indent() << "shininess FRONT " << material.getShininess(Material::FRONT) << endl; + fw.indent() << "shininess BACK " << material.getShininess(Material::BACK) << endl; + } + + return true; +} diff --git a/src/osgPlugins/osg/Matrix.cpp b/src/osgPlugins/osg/Matrix.cpp new file mode 100644 index 000000000..56b1dddf7 --- /dev/null +++ b/src/osgPlugins/osg/Matrix.cpp @@ -0,0 +1,64 @@ +#include "osg/Matrix" + +#include "osgDB/Registry" +#include "osgDB/Input" +#include "osgDB/Output" + +using namespace osg; +using namespace osgDB; + +// forward declare functions to use later. +bool Matrix_readLocalData(Object& obj, Input& fr); +bool Matrix_writeLocalData(const Object& obj, Output& fw); + +// register the read and write functions with the osgDB::Registry. +RegisterDotOsgWrapperProxy g_MatrixFuncProxy +( + new osg::Matrix, + "Matrix", + "Object Matrix", + &Matrix_readLocalData, + &Matrix_writeLocalData +); + +bool Matrix_readLocalData(Object& obj, Input& fr) +{ + bool iteratorAdvanced = false; + + Matrix& matrix = static_cast(obj); + + bool matched = true; + for(int k=0;k<16 && matched;++k) + { + matched = fr[k].isFloat(); + } + if (matched) + { + int k=0; + for(int i=0;i<4;++i) + { + for(int j=0;j<4;++j) + { + fr[k].getFloat(matrix._mat[i][j]); + k++; + } + } + fr += 16; + iteratorAdvanced = true; + } + + return iteratorAdvanced; +} + + +bool Matrix_writeLocalData(const Object& obj, Output& fw) +{ + const Matrix& matrix = static_cast(obj); + + fw.indent() << matrix._mat[0][0] << " " << matrix._mat[0][1] << " " << matrix._mat[0][2] << " " << matrix._mat[0][3] << endl; + fw.indent() << matrix._mat[1][0] << " " << matrix._mat[1][1] << " " << matrix._mat[1][2] << " " << matrix._mat[1][3] << endl; + fw.indent() << matrix._mat[2][0] << " " << matrix._mat[2][1] << " " << matrix._mat[2][2] << " " << matrix._mat[2][3] << endl; + fw.indent() << matrix._mat[3][0] << " " << matrix._mat[3][1] << " " << matrix._mat[3][2] << " " << matrix._mat[3][3] << endl; + return true; +} + diff --git a/src/osgPlugins/osg/Node.cpp b/src/osgPlugins/osg/Node.cpp new file mode 100644 index 000000000..e8e832e8c --- /dev/null +++ b/src/osgPlugins/osg/Node.cpp @@ -0,0 +1,132 @@ +#include "osg/Node" + +#include "osgDB/Registry" +#include "osgDB/Input" +#include "osgDB/Output" + +using namespace osg; +using namespace osgDB; + +// forward declare functions to use later. +bool Node_readLocalData(Object& obj, Input& fr); +bool Node_writeLocalData(const Object& obj, Output& fw); + +// register the read and write functions with the osgDB::Registry. +RegisterDotOsgWrapperProxy g_NodeProxy +( + new osg::Node, + "Node", + "Object Node", + &Node_readLocalData, + &Node_writeLocalData +); + +bool Node_readLocalData(Object& obj, Input& fr) +{ + bool iteratorAdvanced = false; + + Node& node = static_cast(obj); + + if (fr.matchSequence("name %s")) + { + node.setName(fr[1].getStr()); + fr+=2; + iteratorAdvanced = true; + } + + // if (fr.matchSequence("user_data {")) + // { + // notify(DEBUG) << "Matched user_data {"<entry) + // { + // Object* object = fr.readObject(); + // if (object) setUserData(object); + // notify(DEBUG) << "read "<entry) + { + node.addDescription(fr[0].getStr()); + ++fr; + } + iteratorAdvanced = true; + + } + + while (fr.matchSequence("description %s")) + { + node.addDescription(fr[1].getStr()); + fr+=2; + iteratorAdvanced = true; + } + + static ref_ptr s_drawstate = new osg::StateSet; + if (StateSet* readState = static_cast(fr.readObjectOfType(*s_drawstate))) + { + node.setStateSet(readState); + iteratorAdvanced = true; + } + + + return iteratorAdvanced; +} + + +bool Node_writeLocalData(const Object& obj, Output& fw) +{ + const Node& node = static_cast(obj); + + if (!node.getName().empty()) fw.indent() << "name "<<'"'<(_userData); + // if (object) + // { + // fw.indent() << "user_data {"<write(fw); + // fw.moveOut(); + // fw.indent() << "}"<(obj); + + float data; + if (fr[0].matchWord("size") && fr[1].getFloat(data)) + { + + point.setSize(data); + fr+=2; + iteratorAdvanced = true; + } + + if (fr[0].matchWord("fade_threshold_size") && fr[1].getFloat(data)) + { + + point.setFadeThresholdSize(data); + fr+=2; + iteratorAdvanced = true; + } + + Vec3 distAtten; + if (fr[0].matchWord("distance_attenuation") && + fr[1].getFloat(distAtten[0]) && fr[2].getFloat(distAtten[1]) && fr[3].getFloat(distAtten[2])) + { + + point.setDistanceAttenuation(distAtten); + fr+=4; + iteratorAdvanced = true; + } + + return iteratorAdvanced; +} + + +bool Point_writeLocalData(const Object& obj, Output& fw) +{ + const Point& point = static_cast(obj); + + fw.indent() << "size " << point.getSize() << endl; + fw.indent() << "fade_threshold_size " << point.getFadeThresholdSize() << endl; + fw.indent() << "distance_attenuation " << point.getDistanceAttenuation() << endl; + return true; +} diff --git a/src/osgPlugins/osg/PolygonMode.cpp b/src/osgPlugins/osg/PolygonMode.cpp new file mode 100644 index 000000000..68dc8601f --- /dev/null +++ b/src/osgPlugins/osg/PolygonMode.cpp @@ -0,0 +1,90 @@ +#include "osg/PolygonMode" + +#include "osgDB/Registry" +#include "osgDB/Input" +#include "osgDB/Output" + +using namespace osg; +using namespace osgDB; + +// forward declare functions to use later. +bool PolygonMode_readLocalData(Object& obj, Input& fr); +bool PolygonMode_writeLocalData(const Object& obj, Output& fw); + +// register the read and write functions with the osgDB::Registry. +RegisterDotOsgWrapperProxy g_PolygonModeProxy +( + new osg::PolygonMode, + "PolygonMode", + "Object StateAttribute PolygonMode", + &PolygonMode_readLocalData, + &PolygonMode_writeLocalData +); + + +bool PolygonMode_readLocalData(Object& obj, Input& fr) +{ + bool iteratorAdvanced = false; + + PolygonMode& polygonmode = static_cast(obj); + + if (fr[0].matchWord("mode")) + { + PolygonMode::Face face = PolygonMode::FRONT_AND_BACK; + bool readFace = true; + if (fr[1].matchWord("FRONT")) face = PolygonMode::FRONT; + else if (fr[1].matchWord("BACK")) face = PolygonMode::BACK; + else if (fr[1].matchWord("FRONT_AND_BACK")) face = PolygonMode::FRONT_AND_BACK; + else readFace = false; + if (readFace) + { + PolygonMode::Mode mode = PolygonMode::FILL; + bool readMode = true; + if (fr[2].matchWord("POINT")) mode = PolygonMode::POINT; + else if (fr[2].matchWord("LINE")) mode = PolygonMode::LINE; + else if (fr[2].matchWord("FILL")) mode = PolygonMode::FILL; + else readMode = false; + if (readMode) + { + polygonmode.setMode(face,mode); + fr+=3; + iteratorAdvanced = true; + } + } + } + + return iteratorAdvanced; +} + + +bool PolygonMode_writeLocalData(const Object& obj, Output& fw) +{ + const PolygonMode& polygonmode = static_cast(obj); + + if (polygonmode.getFrontAndBack()) + { + switch(polygonmode.getMode(PolygonMode::FRONT)) + { + case(PolygonMode::POINT): fw.indent() << "mode FRONT_AND_BACK POINT" << endl; break; + case(PolygonMode::LINE): fw.indent() << "mode FRONT_AND_BACK LINE" << endl; break; + case(PolygonMode::FILL): fw.indent() << "mode FRONT_AND_BACK FILL" << endl; break; + } + } + else + { + switch(polygonmode.getMode(PolygonMode::FRONT)) + { + case(PolygonMode::POINT): fw.indent() << "mode FRONT POINT" << endl; break; + case(PolygonMode::LINE): fw.indent() << "mode FRONT LINE" << endl; break; + case(PolygonMode::FILL): fw.indent() << "mode FRONT FILL" << endl; break; + } + switch(polygonmode.getMode(PolygonMode::BACK)) + { + case(PolygonMode::POINT): fw.indent() << "mode BACK POINT" << endl; break; + case(PolygonMode::LINE): fw.indent() << "mode BACK LINE" << endl; break; + case(PolygonMode::FILL): fw.indent() << "mode BACK FILL" << endl; break; + } + } + + return true; +} diff --git a/src/osgPlugins/osg/PolygonOffset.cpp b/src/osgPlugins/osg/PolygonOffset.cpp new file mode 100644 index 000000000..2db163c96 --- /dev/null +++ b/src/osgPlugins/osg/PolygonOffset.cpp @@ -0,0 +1,59 @@ +#include "osg/PolygonOffset" + +#include "osgDB/Registry" +#include "osgDB/Input" +#include "osgDB/Output" + +using namespace osg; +using namespace osgDB; + +// forward declare functions to use later. +bool PolygonOffset_readLocalData(Object& obj, Input& fr); +bool PolygonOffset_writeLocalData(const Object& obj, Output& fw); + +// register the read and write functions with the osgDB::Registry. +RegisterDotOsgWrapperProxy g_PolygonOffsetProxy +( + new osg::PolygonOffset, + "PolygonOffset", + "Object StateAttribute PolygonOffset", + &PolygonOffset_readLocalData, + &PolygonOffset_writeLocalData +); + + +bool PolygonOffset_readLocalData(Object& obj, Input& fr) +{ + bool iteratorAdvanced = false; + + PolygonOffset& polygonoffset = static_cast(obj); + + float data; + if (fr[0].matchWord("factor") && fr[1].getFloat(data)) + { + + polygonoffset.setFactor(data); + fr+=2; + iteratorAdvanced = true; + } + + if (fr[0].matchWord("units") && fr[1].getFloat(data)) + { + + polygonoffset.setUnits(data); + fr+=2; + iteratorAdvanced = true; + } + + return iteratorAdvanced; +} + + +bool PolygonOffset_writeLocalData(const Object& obj, Output& fw) +{ + const PolygonOffset& polygonoffset = static_cast(obj); + + fw.indent() << "factor " << polygonoffset.getFactor() << endl; + fw.indent() << "units " << polygonoffset.getUnits() << endl; + return true; +} diff --git a/src/osgPlugins/osg/README b/src/osgPlugins/osg/README new file mode 100644 index 000000000..3e6f8649c --- /dev/null +++ b/src/osgPlugins/osg/README @@ -0,0 +1,10 @@ +Notes +===== +Currently there is no read/write .osg support for osg::Lighting. + +The support in Image.cpp is also not full functional and should be rewritten +in the future to support inline images. Currently osg::Images are supported +via the osgDB::Registry::read/writeImage methods and plugins. + +Robert Osfield, +March 20001. diff --git a/src/osgPlugins/osg/ReaderWriterOSG.cpp b/src/osgPlugins/osg/ReaderWriterOSG.cpp new file mode 100644 index 000000000..843a36fb4 --- /dev/null +++ b/src/osgPlugins/osg/ReaderWriterOSG.cpp @@ -0,0 +1,103 @@ +#include "osg/Image" +#include "osg/Group" + +#include "osgDB/FileNameUtils" +#include "osgDB/Registry" +#include "osgDB/Input" +#include "osgDB/Output" + +using namespace osg; +using namespace osgDB; + +class OSGReaderWriter : public ReaderWriter +{ + public: + virtual const char* className() { return "OSG Reader/Writer"; } + + virtual bool acceptsExtension(const std::string& extension) + { + return equalCaseInsensitive(extension,"osg"); + } + + virtual Object* readObject(const std::string& fileName) { return readNode(fileName); } + + virtual Node* readNode(const std::string& fileName) + { + std::string ext = getFileExtension(fileName); + if (!acceptsExtension(ext)) return NULL; + + ifstream fin(fileName.c_str()); + if (fin) + { + Input fr; + fr.attach(&fin); + + Group* group = new Group; + group->setName("import group"); + + // load all nodes in file, placing them in a group. + while(!fr.eof()) + { + Node *node = fr.readNode(); + if (node) group->addChild(node); + else fr.advanceOverCurrentFieldOrBlock(); + } + + if (group->getNumChildren()>1) + { + return group; + } + else if (group->getNumChildren()==1) + { + // only one node loaded so just return that one node, + // and delete the redundent group. Note, the + // child must be referenced before defrencing + // the group so to avoid delete its children. + Node* node = group->getChild(0); + node->ref(); + group->unref(); + return node; + } // group->getNumChildren()==0 + else + { + return 0L; + } + + } + else + { + return 0L; + } + } + + virtual bool writeObject(const Object& obj,const std::string& fileName) + { + Output fout; + fout.open(fileName.c_str()); + if (fout) + { + fout.writeObject(obj); + fout.close(); + return true; + } + return false; + } + + virtual bool writeNode(const Node& node,const std::string& fileName) + { + Output fout; + fout.open(fileName.c_str()); + if (fout) + { + fout.writeObject(node); + fout.close(); + return true; + } + return false; + } + +}; + +// now register with Registry to instantiate the above +// reader/writer. +RegisterReaderWriterProxy g_OSGReaderWriterProxy; diff --git a/src/osgPlugins/osg/StateSet.cpp b/src/osgPlugins/osg/StateSet.cpp new file mode 100644 index 000000000..86660d41a --- /dev/null +++ b/src/osgPlugins/osg/StateSet.cpp @@ -0,0 +1,493 @@ +#include "osg/StateSet" + +#include "osgDB/Registry" +#include "osgDB/Input" +#include "osgDB/Output" + +using namespace osg; +using namespace osgDB; + +// forward declare functions to use later. +bool GeoState_readLocalData(Object& obj, Input& fr); + +bool StateSet_readLocalData(Object& obj, Input& fr); +bool StateSet_writeLocalData(const Object& obj, Output& fw); + +bool StateSet_matchModeStr(const char* str,StateAttribute::GLModeValue& mode); +const char* StateSet_getModeStr(StateAttribute::GLModeValue mode); + +bool StateSet_matchRenderBinModeStr(const char* str,StateSet::RenderBinMode& mode); +const char* StateSet_getRenderBinModeStr(StateSet::RenderBinMode mode); + +// register the read and write functions with the osgDB::Registry. +RegisterDotOsgWrapperProxy g_StateSetFuncProxy +( + new osg::StateSet, + "StateSet", + "Object StateSet", + &StateSet_readLocalData, + &StateSet_writeLocalData, + DotOsgWrapper::READ_AND_WRITE +); + +// register the read and write functions with the osgDB::Registry. +RegisterDotOsgWrapperProxy g_GeoStateFuncProxy +( + new osg::StateSet, + "GeoState", + "Object GeoState", + &GeoState_readLocalData, + NULL, + DotOsgWrapper::READ_ONLY +); + +// +// Set up the maps from name to GLMode and visa versa. +// +typedef std::map GLNameToGLModeMap; +typedef std::map GLModeToGLNameMap; + +GLNameToGLModeMap s_GLNameToGLModeMap; +GLModeToGLNameMap s_GLModeToGLNameMap; + +#define ADD_NAME(name,mode) s_GLNameToGLModeMap[name]=mode; s_GLModeToGLNameMap[mode]=name; + +void initGLNames() +{ + static bool first_time = true; + if (!first_time) return; + + ADD_NAME("GL_ALPHA_TEST",GL_ALPHA_TEST) + ADD_NAME("GL_BLEND",GL_BLEND) + ADD_NAME("GL_COLOR_MATERIAL",GL_COLOR_MATERIAL) + ADD_NAME("GL_CULL_FACE",GL_CULL_FACE) + ADD_NAME("GL_DEPTH_TEST",GL_DEPTH_TEST) + ADD_NAME("GL_FOG",GL_FOG) + ADD_NAME("GL_LIGHTING",GL_LIGHTING) + ADD_NAME("GL_POINT_SMOOTH",GL_POINT_SMOOTH) + ADD_NAME("GL_POLYGON_OFFSET_FILL",GL_POLYGON_OFFSET_FILL) + ADD_NAME("GL_POLYGON_OFFSET_LINE",GL_POLYGON_OFFSET_LINE) + ADD_NAME("GL_POLYGON_OFFSET_POINT",GL_POLYGON_OFFSET_POINT) + + ADD_NAME("GL_TEXTURE_2D",GL_TEXTURE_2D) + ADD_NAME("GL_TEXTURE_GEN_Q",GL_TEXTURE_GEN_Q) + ADD_NAME("GL_TEXTURE_GEN_R",GL_TEXTURE_GEN_R) + ADD_NAME("GL_TEXTURE_GEN_S",GL_TEXTURE_GEN_S) + ADD_NAME("GL_TEXTURE_GEN_T",GL_TEXTURE_GEN_T) + + ADD_NAME("GL_STENCIL_TEST",GL_STENCIL_TEST) + + ADD_NAME("GL_CLIP_PLANE0",GL_CLIP_PLANE0); + ADD_NAME("GL_CLIP_PLANE1",GL_CLIP_PLANE1); + ADD_NAME("GL_CLIP_PLANE2",GL_CLIP_PLANE2); + ADD_NAME("GL_CLIP_PLANE3",GL_CLIP_PLANE3); + ADD_NAME("GL_CLIP_PLANE4",GL_CLIP_PLANE4); + ADD_NAME("GL_CLIP_PLANE5",GL_CLIP_PLANE5); + + ADD_NAME("GL_LIGHT0",GL_LIGHT0); + ADD_NAME("GL_LIGHT1",GL_LIGHT1); + ADD_NAME("GL_LIGHT2",GL_LIGHT2); + ADD_NAME("GL_LIGHT3",GL_LIGHT3); + ADD_NAME("GL_LIGHT4",GL_LIGHT4); + ADD_NAME("GL_LIGHT5",GL_LIGHT5); + ADD_NAME("GL_LIGHT6",GL_LIGHT6); + ADD_NAME("GL_LIGHT7",GL_LIGHT7); + +// for(GLNameToGLModeMap::iterator itr=s_GLNameToGLModeMap.begin(); +// itr!=s_GLNameToGLModeMap.end(); +// ++itr) +// { +// cout << "Name ["<first<<","<second<<"]"<(obj); + + statset.setRenderingHint(StateSet::OPAQUE_BIN); + + StateAttribute::GLModeValue mode; + if (fr[0].matchWord("transparency") && StateSet_matchModeStr(fr[1].getStr(),mode)) + { + if (mode==StateAttribute::ON || mode==StateAttribute::OVERRIDE_ON) + { + statset.setRenderingHint(StateSet::TRANSPARENT_BIN); + } + statset.setMode(GL_BLEND,mode); + fr+=2; + iteratorAdvanced = true; + } + + if (fr[0].matchWord("antialiasing") && StateSet_matchModeStr(fr[1].getStr(),mode)) + { + // what is the OpenGL modes for antialissing, need to look up. + // statset.setMode(GeoState::ANTIALIAS,mode); + fr+=2; + iteratorAdvanced = true; + } + + if (fr[0].matchWord("face_culling") && StateSet_matchModeStr(fr[1].getStr(),mode)) + { + statset.setMode(GL_CULL_FACE,mode); + fr+=2; + iteratorAdvanced = true; + } + + if (fr[0].matchWord("lighting") && StateSet_matchModeStr(fr[1].getStr(),mode)) + { + statset.setMode(GL_LIGHTING,mode); + fr+=2; + iteratorAdvanced = true; + } + + if (fr[0].matchWord("texturing") && StateSet_matchModeStr(fr[1].getStr(),mode)) + { + statset.setMode(GL_TEXTURE_2D,mode); + fr+=2; + iteratorAdvanced = true; + } + + if (fr[0].matchWord("fogging") && StateSet_matchModeStr(fr[1].getStr(),mode)) + { + statset.setMode(GL_FOG,mode); + fr+=2; + iteratorAdvanced = true; + } + + if (fr[0].matchWord("colortable") && StateSet_matchModeStr(fr[1].getStr(),mode)) + { + // what is the OpenGL modes for colortable, need to look up... + // statset.setMode(GeoState::COLORTABLE,mode); + fr+=2; + iteratorAdvanced = true; + } + + StateAttribute::GLModeValue texgening = StateAttribute::OFF; + if (fr[0].matchWord("texgening") && StateSet_matchModeStr(fr[1].getStr(),mode)) + { + // leave up to a tex gen object to set modes associated with TexGen + // as there are mutiple modes associated with TexGen. See below + // attribute reading code. + texgening = mode; + fr+=2; + iteratorAdvanced = true; + } + + if (fr[0].matchWord("point_smoothing") && StateSet_matchModeStr(fr[1].getStr(),mode)) + { + statset.setMode(GL_POINT_SMOOTH,mode); + fr+=2; + iteratorAdvanced = true; + } + + + if (fr[0].matchWord("polygon_offset") && StateSet_matchModeStr(fr[1].getStr(),mode)) + { + // no GL mode associated with polygon offset so commenting out. + // statset.setMode(GeoState::POLYGON_OFFSET,mode); + fr+=2; + iteratorAdvanced = true; + } + + if (fr[0].matchWord("alpha_test") && StateSet_matchModeStr(fr[1].getStr(),mode)) + { + statset.setMode(GL_ALPHA_TEST,mode); + fr+=2; + iteratorAdvanced = true; + } + + + // new code using osg::Registry's list of prototypes to loaded attributes. + StateAttribute* attribute = NULL; + while((attribute=fr.readStateAttribute())!=NULL) + { + statset.setAttribute(attribute); + + if (attribute->getType()==StateAttribute::TEXGEN) + attribute->setStateSetModes(statset,texgening); + + iteratorAdvanced = true; + } + + return iteratorAdvanced; +} + +bool StateSet_readLocalData(Object& obj, Input& fr) +{ + bool iteratorAdvanced = false; + + // note, StateSet replaced GeoState April 2001. + StateSet& stateset = static_cast(obj); + + initGLNames(); + + // read the rendering hint value. + if (fr[0].matchWord("rendering_hint")) + { + if (fr[1].matchWord("DEFAULT_BIN")) + { + stateset.setRenderingHint(StateSet::DEFAULT_BIN); + fr+=2; + iteratorAdvanced = true; + } + else if (fr[1].matchWord("OPAQUE_BIN")) + { + stateset.setRenderingHint(StateSet::OPAQUE_BIN); + fr+=2; + iteratorAdvanced = true; + } + else if (fr[1].matchWord("TRANSPARENT_BIN")) + { + stateset.setRenderingHint(StateSet::TRANSPARENT_BIN); + fr+=2; + iteratorAdvanced = true; + } + else if (fr[1].isInt()) + { + int value; + fr[1].getInt(value); + stateset.setRenderingHint(value); + fr+=2; + iteratorAdvanced = true; + } + } + + bool setRenderBinDetails=false; + StateSet::RenderBinMode rbmode = stateset.getRenderBinMode(); + if (fr[0].matchWord("renderBinMode") && StateSet_matchRenderBinModeStr(fr[1].getStr(),rbmode)) + { + setRenderBinDetails=true; + fr+=2; + iteratorAdvanced = true; + } + + int binNumber = stateset.getBinNumber(); + if (fr[0].matchWord("binNumber") && fr[1].getInt(binNumber)) + { + setRenderBinDetails=true; + fr+=2; + iteratorAdvanced = true; + } + + std::string binName = stateset.getBinName(); + if (fr[0].matchWord("binName")) + { + setRenderBinDetails=true; + binName = fr[1].getStr(); + + fr+=2; + iteratorAdvanced = true; + } + + if (setRenderBinDetails) + { + stateset.setRenderBinDetails(binNumber,binName,rbmode); + } + + + bool readingMode = true; + StateAttribute::GLModeValue value; + while (readingMode) + { + + readingMode=false; + if (fr[0].isInt()) + { + if (StateSet_matchModeStr(fr[1].getStr(),value)) + { + + int mode; + fr[0].getInt(mode); + stateset.setMode((StateAttribute::GLMode)mode,value); + fr+=2; + iteratorAdvanced = true; + readingMode=true; + } + } + else + if (fr[0].getStr()) + { + if (StateSet_matchModeStr(fr[1].getStr(),value)) + { + GLNameToGLModeMap::iterator nitr = s_GLNameToGLModeMap.find(fr[0].getStr()); + if (nitr!=s_GLNameToGLModeMap.end()) + { + StateAttribute::GLMode mode = nitr->second; + stateset.setMode(mode,value); + fr+=2; + iteratorAdvanced = true; + readingMode=true; + } + } + } + } + + + + // new code using osg::Registry's list of prototypes to loaded attributes. + StateAttribute* attribute = NULL; + while((attribute=fr.readStateAttribute())!=NULL) + { + stateset.setAttribute(attribute); + iteratorAdvanced = true; + } + + return iteratorAdvanced; +} + +bool StateSet_writeLocalData(const Object& obj, Output& fw) +{ + + const StateSet& stateset = static_cast(obj); + + initGLNames(); + + // write the rendering hint value. + fw.indent()<<"rendering_hint "; + switch(stateset.getRenderingHint()) + { + case(StateSet::DEFAULT_BIN): + fw<<"DEFAULT_BIN"<first); + if (nitr!=s_GLModeToGLNameMap.end()) + { + fw.indent() << nitr->second << " " << StateSet_getModeStr(mitr->second) << endl; + } + else + { + // no name defined for GLMode so just pass its value to fw. + fw.indent() << "0x" << hex << (osg::uint)mitr->first << dec <<" " << StateSet_getModeStr(mitr->second) << endl; + } + + } + + StateSet::AttributeVector attributes = stateset.getAttributeVector(); + + for(StateSet::AttributeVector::iterator sitr=attributes.begin(); + sitr!=attributes.end(); + ++sitr) + { + fw.writeObject(*(*sitr)); + } + +#else + + const StateSet::ModeList& ml = stateset.getModeList(); + const StateSet::AttributeList& sl = stateset.getAttributeList(); + + for(StateSet::ModeList::const_iterator mitr=ml.begin(); + mitr!=ml.end(); + ++mitr) + { + GLModeToGLNameMap::iterator nitr = s_GLModeToGLNameMap.find(mitr->first); + if (nitr!=s_GLModeToGLNameMap.end()) + { + fw.indent() << nitr->second << " " << StateSet_getModeStr(mitr->second) << endl; + } + else + { + // no name defined for GLMode so just pass its value to fw. + fw.indent() << "0x" << hex << (osg::uint)mitr->first << dec <<" " << StateSet_getModeStr(mitr->second) << endl; + } + } + + for(StateSet::AttributeList::const_iterator sitr=sl.begin(); + sitr!=sl.end(); + ++sitr) + { + fw.writeObject(*(sitr->second.first)); + } + +#endif + + return true; +} + + +bool StateSet_matchModeStr(const char* str,StateAttribute::GLModeValue& mode) +{ + if (strcmp(str,"INHERIT")==0) mode = StateAttribute::INHERIT; + else if (strcmp(str,"ON")==0) mode = StateAttribute::ON; + else if (strcmp(str,"OFF")==0) mode = StateAttribute::OFF; + else if (strcmp(str,"OVERRIDE_ON")==0) mode = StateAttribute::OVERRIDE_ON; + else if (strcmp(str,"OVERRIDE_OFF")==0) mode = StateAttribute::OVERRIDE_OFF; + else return false; + return true; +} + + +const char* StateSet_getModeStr(StateAttribute::GLModeValue value) +{ + switch(value) + { + case(StateAttribute::INHERIT): return "INHERIT"; + case(StateAttribute::ON): return "ON"; + case(StateAttribute::OFF): return "OFF"; + case(StateAttribute::OVERRIDE_ON): return "OVERRIDE_ON"; + case(StateAttribute::OVERRIDE_OFF): return "OVERRIDE_OFF"; + } + return ""; +} + +bool StateSet_matchRenderBinModeStr(const char* str,StateSet::RenderBinMode& mode) +{ + if (strcmp(str,"INHERIT")==0) mode = StateSet::INHERIT_RENDERBIN_DETAILS; + else if (strcmp(str,"USE")==0) mode = StateSet::USE_RENDERBIN_DETAILS; + else if (strcmp(str,"OVERRID")==0) mode = StateSet::OVERRIDE_RENDERBIN_DETAILS; + else if (strcmp(str,"ENCLOSE")==0) mode = StateSet::ENCLOSE_RENDERBIN_DETAILS; + else return false; + return true; +} + +const char* StateSet_getRenderBinModeStr(StateSet::RenderBinMode mode) +{ + switch(mode) + { + case(StateSet::INHERIT_RENDERBIN_DETAILS): return "INHERIT"; + case(StateSet::USE_RENDERBIN_DETAILS): return "USE"; + case(StateSet::OVERRIDE_RENDERBIN_DETAILS): return "OVERRIDE"; + case(StateSet::ENCLOSE_RENDERBIN_DETAILS): return "ENCLOSE"; + } + return ""; +} diff --git a/src/osgPlugins/osg/Stencil.cpp b/src/osgPlugins/osg/Stencil.cpp new file mode 100644 index 000000000..7754a4a1a --- /dev/null +++ b/src/osgPlugins/osg/Stencil.cpp @@ -0,0 +1,177 @@ +#include "osg/Stencil" + +#include "osgDB/Registry" +#include "osgDB/Input" +#include "osgDB/Output" + +using namespace osg; +using namespace osgDB; + +// forward declare functions to use later. +bool Stencil_readLocalData(Object& obj, Input& fr); +bool Stencil_writeLocalData(const Object& obj, Output& fw); + +bool Stencil_matchFuncStr(const char* str,Stencil::Function& func); +const char* Stencil_getFuncStr(Stencil::Function func); +bool Stencil_matchOperationStr(const char* str,Stencil::Operation& op); +const char* Stencil_getOperationStr(Stencil::Operation op); + + +// register the read and write functions with the osgDB::Registry. +RegisterDotOsgWrapperProxy g_StencilProxy +( + new osg::Stencil, + "Stencil", + "Object StateAttribute Stencil", + &Stencil_readLocalData, + &Stencil_writeLocalData +); + + +bool Stencil_readLocalData(Object& obj, Input& fr) +{ + bool iteratorAdvanced = false; + + Stencil& stencil = static_cast(obj); + + bool setFunction = false; + Stencil::Function func = stencil.getFunction(); + if (fr[0].matchWord("function") && Stencil_matchFuncStr(fr[1].getStr(),func)) + { + setFunction = true; + fr+=2; + iteratorAdvanced = true; + } + + int ref = stencil.getFunctionRef(); + if (fr[0].matchWord("functionRef") && fr[1].getInt(ref)) + { + setFunction = true; + fr+=2; + iteratorAdvanced = true; + } + + osg::uint mask = stencil.getFunctionMask(); + if (fr[0].matchWord("functionMask") && fr[1].getUInt(mask)) + { + setFunction = true; + fr+=2; + iteratorAdvanced = true; + } + + if (setFunction) stencil.setFunction(func,ref,mask); + + bool setOperation = false; + osg::Stencil::Operation sfail = stencil.getStencilFailOperation(); + if (fr[0].matchWord("stencilFailOperation") && Stencil_matchOperationStr(fr[1].getStr(),sfail)) + { + setOperation = true; + fr+=2; + iteratorAdvanced = true; + } + + osg::Stencil::Operation zfail = stencil.getStencilPassAndDepthFailOperation(); + if (fr[0].matchWord("stencilPassAndDepthFailOperation") && Stencil_matchOperationStr(fr[1].getStr(),zfail)) + { + setOperation = true; + fr+=2; + iteratorAdvanced = true; + } + + osg::Stencil::Operation zpass = stencil.getStencilPassAndDepthPassOperation(); + if (fr[0].matchWord("stencilPassAndDepthPassOperation") && Stencil_matchOperationStr(fr[1].getStr(),zpass)) + { + setOperation = true; + fr+=2; + iteratorAdvanced = true; + } + + if (setOperation) stencil.setOperation(sfail, zfail, zpass); + + + if (fr[0].matchWord("writeMask") && fr[1].getUInt(mask)) + { + stencil.setWriteMask(mask); + fr+=2; + iteratorAdvanced = true; + } + + return iteratorAdvanced; +} + + +bool Stencil_writeLocalData(const Object& obj,Output& fw) +{ + const Stencil& stencil = static_cast(obj); + + fw.indent() << "function " << Stencil_getFuncStr(stencil.getFunction()) << endl; + fw.indent() << "functionRef " << stencil.getFunctionRef() << endl; + fw.indent() << "functionMask 0x" << hex << stencil.getFunctionMask() << dec << endl; + + fw.indent() << "stencilFailOperation " << Stencil_getOperationStr(stencil.getStencilFailOperation()) << endl; + fw.indent() << "stencilPassAndDepthFailOperation " << Stencil_getOperationStr(stencil.getStencilPassAndDepthFailOperation()) << endl; + fw.indent() << "stencilPassAndDepthPassOperation " << Stencil_getOperationStr(stencil.getStencilPassAndDepthPassOperation()) << endl; + + fw.indent() << "writeMask 0x" << hex << stencil.getWriteMask() << dec << endl; + + return true; +} + + +bool Stencil_matchFuncStr(const char* str,Stencil::Function& func) +{ + if (strcmp(str,"NEVER")==0) func = Stencil::NEVER; + else if (strcmp(str,"LESS")==0) func = Stencil::LESS; + else if (strcmp(str,"EQUAL")==0) func = Stencil::EQUAL; + else if (strcmp(str,"LEQUAL")==0) func = Stencil::LEQUAL; + else if (strcmp(str,"GREATER")==0) func = Stencil::GREATER; + else if (strcmp(str,"NOTEQUAL")==0) func = Stencil::NOTEQUAL; + else if (strcmp(str,"GEQUAL")==0) func = Stencil::GEQUAL; + else if (strcmp(str,"ALWAYS")==0) func = Stencil::ALWAYS; + else return false; + return true; +} + + +const char* Stencil_getFuncStr(Stencil::Function func) +{ + switch(func) + { + case(Stencil::NEVER): return "NEVER"; + case(Stencil::LESS): return "LESS"; + case(Stencil::EQUAL): return "EQUAL"; + case(Stencil::LEQUAL): return "LEQUAL"; + case(Stencil::GREATER): return "GREATER"; + case(Stencil::NOTEQUAL): return "NOTEQUAL"; + case(Stencil::GEQUAL): return "GEQUAL"; + case(Stencil::ALWAYS): return "ALWAYS"; + } + return ""; +} + +bool Stencil_matchOperationStr(const char* str,Stencil::Operation& op) +{ + if (strcmp(str,"KEEP")==0) op = Stencil::KEEP; + else if (strcmp(str,"ZERO")==0) op = Stencil::ZERO; + else if (strcmp(str,"REPLACE")==0) op = Stencil::REPLACE; + else if (strcmp(str,"INCR")==0) op = Stencil::INCR; + else if (strcmp(str,"DECR")==0) op = Stencil::DECR; + else if (strcmp(str,"INVERT")==0) op = Stencil::INVERT; + else return false; + return true; +} + +const char* Stencil_getOperationStr(Stencil::Operation op) +{ + switch(op) + { + case(Stencil::KEEP): return "KEEP"; + case(Stencil::ZERO): return "ZERO"; + case(Stencil::REPLACE): return "REPLACE"; + case(Stencil::INCR): return "INCR"; + case(Stencil::DECR): return "DECR"; + case(Stencil::INVERT): return "INVERT"; + } + return ""; +} + diff --git a/src/osgPlugins/osg/Switch.cpp b/src/osgPlugins/osg/Switch.cpp new file mode 100644 index 000000000..1f41351f1 --- /dev/null +++ b/src/osgPlugins/osg/Switch.cpp @@ -0,0 +1,71 @@ +#include "osg/Switch" + +#include "osgDB/Registry" +#include "osgDB/Input" +#include "osgDB/Output" + +using namespace osg; +using namespace osgDB; + +// forward declare functions to use later. +bool Switch_readLocalData(Object& obj, Input& fr); +bool Switch_writeLocalData(const Object& obj, Output& fw); + +// register the read and write functions with the osgDB::Registry. +RegisterDotOsgWrapperProxy g_SwitchProxy +( + new osg::Switch, + "Switch", + "Object Node Group Switch", + &Switch_readLocalData, + &Switch_writeLocalData +); + +bool Switch_readLocalData(Object& obj, Input& fr) +{ + bool iteratorAdvanced = false; + + Switch& sw = static_cast(obj); + + if (fr.matchSequence("value")) + { + if (fr[1].matchWord("ALL_CHILDREN_ON")) + { + sw.setValue(Switch::ALL_CHILDREN_ON); + iteratorAdvanced = true; + fr+=2; + } + else if (fr[1].matchWord("ALL_CHILDREN_OFF")) + { + sw.setValue(Switch::ALL_CHILDREN_OFF); + iteratorAdvanced = true; + fr+=2; + } + else if (fr[1].isInt()) + { + int value; + fr[1].getInt(value); + sw.setValue(value); + iteratorAdvanced = true; + fr+=2; + } + } + + return iteratorAdvanced; +} + + +bool Switch_writeLocalData(const Object& obj, Output& fw) +{ + const Switch& sw = static_cast(obj); + + fw.indent() << "value "; + switch(sw.getValue()) + { + case(Switch::ALL_CHILDREN_ON): fw<<"ALL_CHILDREN_ON"<(obj); + + TexEnv::Mode mode; + if (fr[0].matchWord("mode") && TexEnv_matchModeStr(fr[1].getStr(),mode)) + { + texenv.setMode(mode); + fr+=2; + iteratorAdvanced = true; + } + + return iteratorAdvanced; +} + +bool TexEnv_writeLocalData(const Object& obj, Output& fw) +{ + const TexEnv& texenv = static_cast(obj); + + fw.indent() << "mode " << TexEnv_getModeStr(texenv.getMode()) << endl; + + return true; +} + +bool TexEnv_matchModeStr(const char* str,TexEnv::Mode& mode) +{ + if (strcmp(str,"DECAL")==0) mode = TexEnv::DECAL; + else if (strcmp(str,"MODULATE")==0) mode = TexEnv::MODULATE; + else if (strcmp(str,"BLEND")==0) mode = TexEnv::BLEND; + else if (strcmp(str,"REPLACE")==0) mode = TexEnv::REPLACE; + else return false; + return true; +} + + +const char* TexEnv_getModeStr(TexEnv::Mode mode) +{ + switch(mode) + { + case(TexEnv::DECAL): return "DECAL"; + case(TexEnv::MODULATE): return "MODULATE"; + case(TexEnv::BLEND): return "BLEND"; + case(TexEnv::REPLACE): return "REPLACE"; + } + return ""; +} + diff --git a/src/osgPlugins/osg/TexGen.cpp b/src/osgPlugins/osg/TexGen.cpp new file mode 100644 index 000000000..704ff22fa --- /dev/null +++ b/src/osgPlugins/osg/TexGen.cpp @@ -0,0 +1,128 @@ +#if defined(_MSC_VER) + #pragma warning( disable : 4786 ) +#endif + +#include "osg/TexGen" + +#include "osgDB/Registry" +#include "osgDB/Input" +#include "osgDB/Output" + +using namespace osg; +using namespace osgDB; + +// forward declare functions to use later. +bool TexGen_readLocalData(Object& obj, Input& fr); +bool TexGen_writeLocalData(const Object& obj, Output& fw); +bool TexGen_matchModeStr(const char* str,TexGen::Mode& mode); +const char* TexGen_getModeStr(TexGen::Mode mode); + +// register the read and write functions with the osgDB::Registry. +RegisterDotOsgWrapperProxy g_TexGenProxy +( + new osg::TexGen, + "TexGen", + "Object StateAttribute TexGen", + &TexGen_readLocalData, + &TexGen_writeLocalData +); + + +bool TexGen_readLocalData(Object& obj, Input& fr) +{ + bool iteratorAdvanced = false; + + TexGen& texgen = static_cast(obj); + + TexGen::Mode mode; + + if (fr[0].matchWord("mode") && TexGen_matchModeStr(fr[1].getStr(),mode)) + { + texgen.setMode(mode); + fr+=2; + iteratorAdvanced = true; + } + + Vec4 plane; + if (fr[0].matchWord("plane_s")) + { + if (fr[1].getFloat(plane[0]) && fr[2].getFloat(plane[1]) && + fr[3].getFloat(plane[2]) && fr[4].getFloat(plane[3])) + { + texgen.setPlane(TexGen::S,plane); + fr+=5; + iteratorAdvanced = true; + } + } + if (fr[0].matchWord("plane_t")) + { + if (fr[1].getFloat(plane[0]) && fr[2].getFloat(plane[1]) && + fr[3].getFloat(plane[2]) && fr[4].getFloat(plane[3])) + { + texgen.setPlane(TexGen::T,plane); + fr+=5; + iteratorAdvanced = true; + } + } + if (fr[0].matchWord("plane_r")) + { + if (fr[1].getFloat(plane[0]) && fr[2].getFloat(plane[1]) && + fr[3].getFloat(plane[2]) && fr[4].getFloat(plane[3])) + { + texgen.setPlane(TexGen::R,plane); + fr+=5; + iteratorAdvanced = true; + } + } + if (fr[0].matchWord("plane_q")) + { + if (fr[1].getFloat(plane[0]) && fr[2].getFloat(plane[1]) && + fr[3].getFloat(plane[2]) && fr[4].getFloat(plane[3])) + { + texgen.setPlane(TexGen::Q,plane); + fr+=5; + iteratorAdvanced = true; + } + } + + return iteratorAdvanced; +} + + +bool TexGen_matchModeStr(const char* str,TexGen::Mode& mode) +{ + if (strcmp(str,"EYE_LINEAR")==0) mode = TexGen::EYE_LINEAR; + else if (strcmp(str,"OBJECT_LINEAR")==0) mode = TexGen::OBJECT_LINEAR; + else if (strcmp(str,"SPHERE_MAP")==0) mode = TexGen::SPHERE_MAP; + else return false; + return true; +} + + +const char* TexGen_getModeStr(TexGen::Mode mode) +{ + switch(mode) + { + case(TexGen::EYE_LINEAR): return "EYE_LINEAR"; + case(TexGen::OBJECT_LINEAR): return "OBJECT_LINEAR"; + case(TexGen::SPHERE_MAP): return "SPHERE_MAP"; + } + return ""; +} + + +bool TexGen_writeLocalData(const Object& obj, Output& fw) +{ + const TexGen& texgen = static_cast(obj); + + fw.indent() << "mode " << TexGen_getModeStr(texgen.getMode()) << endl; + if (texgen.getMode() == TexGen::OBJECT_LINEAR || texgen.getMode() == TexGen::EYE_LINEAR) + { + fw.indent() << "plane_s " << texgen.getPlane(TexGen::S) << endl; + fw.indent() << "plane_t " << texgen.getPlane(TexGen::T) << endl; + fw.indent() << "plane_r " << texgen.getPlane(TexGen::R) << endl; + fw.indent() << "plane_q " << texgen.getPlane(TexGen::Q) << endl; + } + + return true; +} diff --git a/src/osgPlugins/osg/TexMat.cpp b/src/osgPlugins/osg/TexMat.cpp new file mode 100644 index 000000000..b67fab057 --- /dev/null +++ b/src/osgPlugins/osg/TexMat.cpp @@ -0,0 +1,67 @@ +#include "osg/TexMat" + +#include "osgDB/Registry" +#include "osgDB/Input" +#include "osgDB/Output" + +using namespace osg; +using namespace osgDB; + +// forward declare functions to use later. +bool TexMat_readLocalData(Object& obj, Input& fr); +bool TexMat_writeLocalData(const Object& obj, Output& fw); + +// register the read and write functions with the osgDB::Registry. +RegisterDotOsgWrapperProxy g_TexMatProxy +( + new osg::TexMat, + "TexMat", + "Object StateAttribute TexMat", + &TexMat_readLocalData, + &TexMat_writeLocalData +); + + +bool TexMat_readLocalData(Object& obj, Input& fr) +{ + bool iteratorAdvanced = false; + + TexMat& texmat = static_cast(obj); + + bool matched = true; + for(int k=0;k<16 && matched;++k) + { + matched = fr[k].isFloat(); + } + if (matched) + { + + Matrix& matrix = texmat.getMatrix(); + + int k=0; + for(int i=0;i<4;++i) + { + for(int j=0;j<4;++j) + { + fr[k].getFloat(matrix._mat[i][j]); + k++; + } + } + fr += 16; + iteratorAdvanced = true; + } + + return iteratorAdvanced; +} + + +bool TexMat_writeLocalData(const Object& obj, Output& fw) +{ + const TexMat& texmat = static_cast(obj); + const Matrix& matrix = texmat.getMatrix(); + fw.indent() << matrix._mat[0][0] << " " << matrix._mat[0][1] << " " << matrix._mat[0][2] << " " << matrix._mat[0][3] << endl; + fw.indent() << matrix._mat[1][0] << " " << matrix._mat[1][1] << " " << matrix._mat[1][2] << " " << matrix._mat[1][3] << endl; + fw.indent() << matrix._mat[2][0] << " " << matrix._mat[2][1] << " " << matrix._mat[2][2] << " " << matrix._mat[2][3] << endl; + fw.indent() << matrix._mat[3][0] << " " << matrix._mat[3][1] << " " << matrix._mat[3][2] << " " << matrix._mat[3][3] << endl; + return true; +} diff --git a/src/osgPlugins/osg/Texture.cpp b/src/osgPlugins/osg/Texture.cpp new file mode 100644 index 000000000..bd7c73bcf --- /dev/null +++ b/src/osgPlugins/osg/Texture.cpp @@ -0,0 +1,324 @@ +#include "osg/Texture" + +#include "osgDB/Registry" +#include "osgDB/Input" +#include "osgDB/Output" + +using namespace osg; +using namespace osgDB; + +// forward declare functions to use later. +bool Texture_readLocalData(Object& obj, Input& fr); +bool Texture_writeLocalData(const Object& obj, Output& fw); + +bool Texture_matchWrapStr(const char* str,Texture::WrapMode& wrap); +const char* Texture_getWrapStr(Texture::WrapMode wrap); +bool Texture_matchFilterStr(const char* str,Texture::FilterMode& filter); +const char* Texture_getFilterStr(Texture::FilterMode filter); +bool Texture_matchInternalFormatModeStr(const char* str,Texture::InternalFormatMode& mode); +const char* Texture_getInternalFormatModeStr(Texture::InternalFormatMode mode); +bool Texture_matchInternalFormatValueStr(const char* str,int& value); +const char* Texture_getInternalFormatValueStr(int value); +bool Texture_matchSubloadModeStr(const char* str, Texture::SubloadMode& value); +const char* Texture_getSubloadModeStr(Texture::SubloadMode value); + +// register the read and write functions with the osgDB::Registry. +RegisterDotOsgWrapperProxy g_TextureProxy +( + new osg::Texture, + "Texture", + "Object StateAttribute Texture", + &Texture_readLocalData, + &Texture_writeLocalData +); + + +bool Texture_readLocalData(Object& obj, Input& fr) +{ + bool iteratorAdvanced = false; + + Texture& texture = static_cast(obj); + + if (fr[0].matchWord("file") && fr[1].isString()) + { + std::string filename = fr[1].getStr(); + Image* image = fr.readImage(filename.c_str()); + if (image) + { + // name will have already been set by the image plugin, + // but it will have absolute path, so will override it + // here to keep the original name intact. + //image->setFileName(filename); + texture.setImage(image); + } + + fr += 2; + iteratorAdvanced = true; + } + Texture::WrapMode wrap; + if (fr[0].matchWord("wrap_s") && Texture_matchWrapStr(fr[1].getStr(),wrap)) + { + texture.setWrap(Texture::WRAP_S,wrap); + fr+=2; + iteratorAdvanced = true; + } + + if (fr[0].matchWord("wrap_t") && Texture_matchWrapStr(fr[1].getStr(),wrap)) + { + texture.setWrap(Texture::WRAP_T,wrap); + fr+=2; + iteratorAdvanced = true; + } + + if (fr[0].matchWord("wrap_r") && Texture_matchWrapStr(fr[1].getStr(),wrap)) + { + texture.setWrap(Texture::WRAP_R,wrap); + fr+=2; + iteratorAdvanced = true; + } + + Texture::FilterMode filter; + if (fr[0].matchWord("min_filter") && Texture_matchFilterStr(fr[1].getStr(),filter)) + { + texture.setFilter(Texture::MIN_FILTER,filter); + fr+=2; + iteratorAdvanced = true; + } + + if (fr[0].matchWord("mag_filter") && Texture_matchFilterStr(fr[1].getStr(),filter)) + { + texture.setFilter(Texture::MAG_FILTER,filter); + fr+=2; + iteratorAdvanced = true; + } + + Texture::InternalFormatMode mode; + if (fr[0].matchWord("internalFormatMode") && Texture_matchInternalFormatModeStr(fr[1].getStr(),mode)) + { + texture.setInternalFormatMode(mode); + fr+=2; + iteratorAdvanced = true; + } + + if (fr[0].matchWord("internalFormatValue")) + { + int value; + if (Texture_matchInternalFormatValueStr(fr[1].getStr(),value) || fr[1].getInt(value)) + { + texture.setInternalFormatValue(value); + fr+=2; + iteratorAdvanced = true; + } + } + + Texture::SubloadMode submode; + if (fr[0].matchWord("subloadMode") && Texture_matchSubloadModeStr(fr[1].getStr(),submode)) + { + texture.setSubloadMode(submode); + fr += 2; + iteratorAdvanced = true; + } + if (fr[0].matchWord("subloadOffset")) + { + int x, y; + if (fr[1].getInt(x) && fr[2].getInt(y)) + { + texture.setSubloadOffset(x, y); + fr += 3; + iteratorAdvanced = true; + } + } + + return iteratorAdvanced; +} + + +bool Texture_writeLocalData(const Object& obj, Output& fw) +{ + const Texture& texture = static_cast(obj); + + if (texture.getImage() && !(texture.getImage()->getFileName().empty())) + { + fw.indent() << "file \""<getFileName())<<"\""<(obj); + + static Matrix s_matrix; + + if (Matrix* tmpMatrix = static_cast(fr.readObjectOfType(s_matrix))) + { + + transform.setMatrix(*tmpMatrix); + + delete tmpMatrix; + + iteratorAdvanced = true; + } + + return iteratorAdvanced; +} + + +bool Transform_writeLocalData(const Object& obj, Output& fw) +{ + const Transform& transform = static_cast(obj); + + fw.writeObject(transform.getMatrix()); + + return true; +} diff --git a/src/osgPlugins/osg/Transparency.cpp b/src/osgPlugins/osg/Transparency.cpp new file mode 100644 index 000000000..6715d0c47 --- /dev/null +++ b/src/osgPlugins/osg/Transparency.cpp @@ -0,0 +1,99 @@ +#include "osg/Transparency" + +#include "osgDB/Registry" +#include "osgDB/Input" +#include "osgDB/Output" + +using namespace osg; +using namespace osgDB; + +// forward declare functions to use later. +bool Transparency_readLocalData(Object& obj, Input& fr); +bool Transparency_writeLocalData(const Object& obj, Output& fw); + +bool Transparency_matchModeStr(const char* str,int& mode); +const char* Transparency_getModeStr(int value); + +// register the read and write functions with the osgDB::Registry. +RegisterDotOsgWrapperProxy g_TransparencyProxy +( + new osg::Transparency, + "Transparency", + "Object StateAttribute Transparency", + &Transparency_readLocalData, + &Transparency_writeLocalData +); + + +bool Transparency_readLocalData(Object& obj, Input& fr) +{ + bool iteratorAdvanced = false; + + Transparency& transparency = static_cast(obj); + + int mode; + if (fr[0].matchWord("source") && Transparency_matchModeStr(fr[1].getStr(),mode)) + { + transparency.setSource(mode); + fr+=2; + iteratorAdvanced = true; + } + + if (fr[0].matchWord("destination") && Transparency_matchModeStr(fr[1].getStr(),mode)) + { + transparency.setDestination(mode); + fr+=2; + iteratorAdvanced = true; + } + + return iteratorAdvanced; +} + +bool Transparency_writeLocalData(const Object& obj, Output& fw) +{ + const Transparency& transparency = static_cast(obj); + + fw.indent() << "source " << Transparency_getModeStr(transparency.getSource()) << endl; + fw.indent() << "destination " << Transparency_getModeStr(transparency.getDestination()) << endl; + + return true; +} + + + +bool Transparency_matchModeStr(const char* str,int& mode) +{ + if (strcmp(str,"DST_ALPHA")==0) mode = Transparency::DST_ALPHA; + else if (strcmp(str,"DST_COLOR")==0) mode = Transparency::DST_COLOR; + else if (strcmp(str,"ONE")==0) mode = Transparency::ONE; + else if (strcmp(str,"ONE_MINUS_DST_ALPHA")==0) mode = Transparency::ONE_MINUS_DST_ALPHA; + else if (strcmp(str,"ONE_MINUS_DST_COLOR")==0) mode = Transparency::ONE_MINUS_DST_COLOR; + else if (strcmp(str,"ONE_MINUS_SRC_ALPHA")==0) mode = Transparency::ONE_MINUS_SRC_ALPHA; + else if (strcmp(str,"ONE_MINUS_SRC_COLOR")==0) mode = Transparency::ONE_MINUS_SRC_COLOR; + else if (strcmp(str,"SRC_ALPHA")==0) mode = Transparency::SRC_ALPHA; + else if (strcmp(str,"SRC_ALPHA_SATURATE")==0) mode = Transparency::SRC_ALPHA_SATURATE; + else if (strcmp(str,"SRC_COLOR")==0) mode = Transparency::SRC_COLOR; + else return false; + return true; + +} + +const char* Transparency_getModeStr(int value) +{ + switch(value) + { + case(Transparency::DST_ALPHA) : return "DST_ALPHA"; + case(Transparency::DST_COLOR) : return "DST_COLOR"; + case(Transparency::ONE) : return "ONE"; + case(Transparency::ONE_MINUS_DST_ALPHA) : return "ONE_MINUS_DST_ALPHA"; + case(Transparency::ONE_MINUS_DST_COLOR) : return "ONE_MINUS_DST_COLOR"; + case(Transparency::ONE_MINUS_SRC_ALPHA) : return "ONE_MINUS_SRC_ALPHA"; + case(Transparency::ONE_MINUS_SRC_COLOR) : return "ONE_MINUS_SRC_COLOR"; + case(Transparency::SRC_ALPHA) : return "SRC_ALPHA"; + case(Transparency::SRC_ALPHA_SATURATE) : return "SRC_ALPHA_SATURATE"; + case(Transparency::SRC_COLOR) : return "SRC_COLOR"; + case(Transparency::ZERO) : return "ZERO"; + } + + return NULL; +} diff --git a/src/osgPlugins/osgtgz/Makefile b/src/osgPlugins/osgtgz/Makefile index 7b1a99a74..b801c51eb 100644 --- a/src/osgPlugins/osgtgz/Makefile +++ b/src/osgPlugins/osgtgz/Makefile @@ -2,7 +2,7 @@ include ../../../Make/makedefs C++FILES = \ - osgtgz.cpp\ + ReaderWriterOSGTGZ.cpp\ LIB = ../../../lib/osgPlugins/osgdb_osgtgz.so diff --git a/src/osgPlugins/pfb/ConvertFromPerformer.cpp b/src/osgPlugins/pfb/ConvertFromPerformer.cpp index f78da0fcf..7672399d7 100644 --- a/src/osgPlugins/pfb/ConvertFromPerformer.cpp +++ b/src/osgPlugins/pfb/ConvertFromPerformer.cpp @@ -1,20 +1,23 @@ #include "ConvertFromPerformer.h" -#include #include -#include +#include #include #include -#include #include #include #include #include #include -#include -#include +#include +#include +#include #include +#include +#include +#include + #include #include #include @@ -39,18 +42,20 @@ using namespace std; extern "C" { -extern int -pfdStoreFile_osg (pfNode* root, char *fileName) -{ - ConvertFromPerformer converter; - osg::Node* node = converter.convert(root); - - if (node==NULL) return 0; - if (osg::saveNodeFile(*node,fileName)) return 1; - else return 0; -} + extern int + pfdStoreFile_osg (pfNode* root, char *fileName) + { + ConvertFromPerformer converter; + osg::Node* node = converter.convert(root); + + if (node==NULL) return 0; + if (osgDB::writeNodeFile(*node,fileName)) return 1; + else return 0; + } }; + + ConvertFromPerformer::ConvertFromPerformer() { _osgRoot = NULL; @@ -73,30 +78,12 @@ ConvertFromPerformer::ConvertFromPerformer() _gsetBindMap[PFGS_PER_PRIM] = osg::GeoSet::BIND_PERPRIM; _gsetBindMap[PFGS_PER_VERTEX] = osg::GeoSet::BIND_PERVERTEX; - - _gstateTypeMap[PFSTATE_TRANSPARENCY] = osg::GeoState::TRANSPARENCY; - _gstateTypeMap[PFSTATE_ANTIALIAS] = osg::GeoState::ANTIALIAS; - _gstateTypeMap[PFSTATE_ENLIGHTING] = osg::GeoState::LIGHTING; - _gstateTypeMap[PFSTATE_ENTEXTURE] = osg::GeoState::TEXTURE; - _gstateTypeMap[PFSTATE_ENFOG] = osg::GeoState::FOG; - _gstateTypeMap[PFSTATE_CULLFACE] = osg::GeoState::FACE_CULL; - _gstateTypeMap[PFSTATE_ENWIREFRAME] = osg::GeoState::WIREFRAME; - _gstateTypeMap[PFSTATE_ENTEXGEN] = osg::GeoState::TEXGEN; - _gstateTypeMap[PFSTATE_ENTEXMAT] = osg::GeoState::TEXMAT; - -// not currently supported under the OSG. -// _gstateTypeMap[PFSTATE_DECAL] = ; -// _gstateTypeMap[PFSTATE_ENTEXLOD] = ; -// _gstateTypeMap[PFSTATE_ALPHAFUNC] = ; -// _gstateTypeMap[PFSTATE_ENCOLORTABLE] = ; -// _gstateTypeMap[PFSTATE_ENHIGHLIGHTING] = ; -// _gstateTypeMap[PFSTATE_ENLPOINTSTATE] = ; - _saveImagesAsRGB = false; _saveAbsoluteImagePath = false; } + ConvertFromPerformer::~ConvertFromPerformer() { } @@ -114,17 +101,19 @@ osg::Object* ConvertFromPerformer::getOsgObject(pfObject* pfObj) PfObjectToOsgObjectMap::iterator fitr = _pfToOsgMap.find(pfObj); if (fitr != _pfToOsgMap.end()) { -// osg::notify(DEBUG) << "Found shared object"<(getOsgObject(scene)); + osg::Group* osgScene = dynamic_cast(getOsgObject(scene)); if (osgScene) { if (osgParent) osgParent->addChild(osgScene); return osgScene; } - osgScene = new osg::Scene; + osgScene = new osg::Group; if (osgParent) osgParent->addChild(osgScene); regisiterPfObjectForOsgObject(scene,osgScene); @@ -166,6 +156,7 @@ osg::Node* ConvertFromPerformer::visitScene(osg::Group* osgParent,pfScene* scene return (osg::Node*)osgScene; } + osg::Node* ConvertFromPerformer::visitGroup(osg::Group* osgParent,pfGroup* group) { osg::Group* osgGroup = dynamic_cast(getOsgObject(group)); @@ -190,6 +181,7 @@ osg::Node* ConvertFromPerformer::visitGroup(osg::Group* osgParent,pfGroup* group return (osg::Node*)osgGroup; } + osg::Node* ConvertFromPerformer::visitLOD(osg::Group* osgParent,pfLOD* lod) { osg::LOD* osgLOD = dynamic_cast(getOsgObject(lod)); @@ -226,6 +218,7 @@ osg::Node* ConvertFromPerformer::visitLOD(osg::Group* osgParent,pfLOD* lod) } + osg::Node* ConvertFromPerformer::visitSwitch(osg::Group* osgParent,pfSwitch* switchNode) { osg::Switch* osgSwitch = dynamic_cast(getOsgObject(switchNode)); @@ -246,15 +239,15 @@ osg::Node* ConvertFromPerformer::visitSwitch(osg::Group* osgParent,pfSwitch* swi float val = switchNode->getVal(); if (val==PFSWITCH_ON) { - osgSwitch->setVal(osg::Switch::ALL_CHILDREN_ON); + osgSwitch->setValue(osg::Switch::ALL_CHILDREN_ON); } else if (val==PFSWITCH_OFF) { - osgSwitch->setVal(osg::Switch::ALL_CHILDREN_OFF); + osgSwitch->setValue(osg::Switch::ALL_CHILDREN_OFF); } else { - osgSwitch->setVal((int)val); + osgSwitch->setValue((int)val); } for(int i=0;igetNumChildren();++i) @@ -264,20 +257,33 @@ osg::Node* ConvertFromPerformer::visitSwitch(osg::Group* osgParent,pfSwitch* swi return (osg::Node*)osgSwitch; } + osg::Node* ConvertFromPerformer::visitSequence(osg::Group* osgParent,pfSequence* sequence) { - osg::Sequence* osgSequence = dynamic_cast(getOsgObject(sequence)); + + osg::notify(osg::WARN)<<"Warning : cannot convert pfSequence as no osg::Sequence exists, using osg::Switch instead."<(getOsgObject(sequence)); if (osgSequence) { if (osgParent) osgParent->addChild(osgSequence); return osgSequence; } - osgSequence = new osg::Sequence; + osgSequence = new osg::Switch; if (osgParent) osgParent->addChild(osgSequence); regisiterPfObjectForOsgObject(sequence,osgSequence); + if (sequence->getNumChildren()>0) + { + // set switch to first child as a 'hack' to prevent all + // children being traversed during rendering. Note, + // once osg::Sequence has been implemented this can all + // be removed. + osgSequence->setValue(0); + } + for(int i=0;igetNumChildren();++i) { visitNode(osgSequence,sequence->getChild(i)); @@ -285,75 +291,78 @@ osg::Node* ConvertFromPerformer::visitSequence(osg::Group* osgParent,pfSequence* return (osg::Node*)osgSequence; } + osg::Node* ConvertFromPerformer::visitDCS(osg::Group* osgParent,pfDCS* dcs) { - osg::DCS* osgDCS = dynamic_cast(getOsgObject(dcs)); - if (osgDCS) + osg::Transform* osgTransform = dynamic_cast(getOsgObject(dcs)); + if (osgTransform) { - if (osgParent) osgParent->addChild(osgDCS); - return osgDCS; + if (osgParent) osgParent->addChild(osgTransform); + return osgTransform; } - osgDCS = new osg::DCS; - if (osgParent) osgParent->addChild(osgDCS); + osgTransform = new osg::Transform; + if (osgParent) osgParent->addChild(osgTransform); - regisiterPfObjectForOsgObject(dcs,osgDCS); + regisiterPfObjectForOsgObject(dcs,osgTransform); const char* name = dcs->getName(); - if (name) osgDCS->setName(name); + if (name) osgTransform->setName(name); pfMatrix matrix; dcs->getMat(matrix); osg::Matrix osgMatrix(matrix[0][0],matrix[0][1],matrix[0][2],matrix[0][3], - matrix[1][0],matrix[1][1],matrix[1][2],matrix[1][3], - matrix[2][0],matrix[2][1],matrix[2][2],matrix[2][3], - matrix[3][0],matrix[3][1],matrix[3][2],matrix[3][3]); + matrix[1][0],matrix[1][1],matrix[1][2],matrix[1][3], + matrix[2][0],matrix[2][1],matrix[2][2],matrix[2][3], + matrix[3][0],matrix[3][1],matrix[3][2],matrix[3][3]); - osgDCS->setMatrix(osgMatrix); + osgTransform->setMatrix(osgMatrix); for(int i=0;igetNumChildren();++i) { - visitNode(osgDCS,dcs->getChild(i)); + visitNode(osgTransform,dcs->getChild(i)); } - return (osg::Node*)osgDCS; + return (osg::Node*)osgTransform; } + osg::Node* ConvertFromPerformer::visitSCS(osg::Group* osgParent,pfSCS* scs) { // note the OSG does not currently have a SCS, so use DCS instead. - osg::DCS* osgDCS = dynamic_cast(getOsgObject(scs)); - if (osgDCS) + osg::Transform* osgTransform = dynamic_cast(getOsgObject(scs)); + if (osgTransform) { - if (osgParent) osgParent->addChild(osgDCS); - return osgDCS; + if (osgParent) osgParent->addChild(osgTransform); + return osgTransform; } - osgDCS = new osg::DCS; - if (osgParent) osgParent->addChild(osgDCS); + osgTransform = new osg::Transform; + if (osgParent) osgParent->addChild(osgTransform); - regisiterPfObjectForOsgObject(scs,osgDCS); + regisiterPfObjectForOsgObject(scs,osgTransform); const char* name = scs->getName(); - if (name) osgDCS->setName(name); + if (name) osgTransform->setName(name); pfMatrix matrix; scs->getMat(matrix); osg::Matrix osgMatrix(matrix[0][0],matrix[0][1],matrix[0][2],matrix[0][3], - matrix[1][0],matrix[1][1],matrix[1][2],matrix[1][3], - matrix[2][0],matrix[2][1],matrix[2][2],matrix[2][3], - matrix[3][0],matrix[3][1],matrix[3][2],matrix[3][3]); + matrix[1][0],matrix[1][1],matrix[1][2],matrix[1][3], + matrix[2][0],matrix[2][1],matrix[2][2],matrix[2][3], + matrix[3][0],matrix[3][1],matrix[3][2],matrix[3][3]); - osgDCS->setMatrix(osgMatrix); + osgTransform->setMatrix(osgMatrix); for(int i=0;igetNumChildren();++i) { - visitNode(osgDCS,scs->getChild(i)); + visitNode(osgTransform,scs->getChild(i)); } - return (osg::Node*)osgDCS; + return (osg::Node*)osgTransform; } + osg::Node* ConvertFromPerformer::visitGeode(osg::Group* osgParent,pfGeode* geode) { osg::Geode* osgGeode = dynamic_cast(getOsgObject(geode)); @@ -379,9 +388,10 @@ osg::Node* ConvertFromPerformer::visitGeode(osg::Group* osgParent,pfGeode* geode return (osg::Node*)osgGeode; } + osg::Node* ConvertFromPerformer::visitBillboard(osg::Group* osgParent,pfBillboard* billboard) { -// return NULL; + // return NULL; osg::Billboard* osgBillboard = dynamic_cast(getOsgObject(billboard)); if (osgBillboard) @@ -404,7 +414,8 @@ osg::Node* ConvertFromPerformer::visitBillboard(osg::Group* osgParent,pfBillboar for(int i=0;igetNumGSets();++i) { - /* osg::GeoSet* osggset = */visitGeoSet(osgBillboard,billboard->getGSet(i)); + /* osg::GeoSet* osggset = */ + visitGeoSet(osgBillboard,billboard->getGSet(i)); pfVec3 pos; billboard->getPos(i,pos); osgBillboard->setPos(i,osg::Vec3(pos[0],pos[1],pos[2])); @@ -413,6 +424,7 @@ osg::Node* ConvertFromPerformer::visitBillboard(osg::Group* osgParent,pfBillboar return (osg::Node*)osgBillboard; } + int ConvertFromPerformer::getNumVerts(pfGeoSet *gset) { int nv; @@ -454,10 +466,10 @@ int ConvertFromPerformer::getNumVerts(pfGeoSet *gset) } - return nv; } + osg::GeoSet* ConvertFromPerformer::visitGeoSet(osg::Geode* osgGeode,pfGeoSet* geoset) { if (geoset==NULL) return NULL; @@ -465,12 +477,12 @@ osg::GeoSet* ConvertFromPerformer::visitGeoSet(osg::Geode* osgGeode,pfGeoSet* ge osg::GeoSet* osgGeoSet = dynamic_cast(getOsgObject(geoset)); if (osgGeoSet) { - if (osgGeode) osgGeode->addGeoSet(osgGeoSet); + if (osgGeode) osgGeode->addDrawable(osgGeoSet); return osgGeoSet; } osgGeoSet = new osg::GeoSet; - if (osgGeode) osgGeode->addGeoSet(osgGeoSet); + if (osgGeode) osgGeode->addDrawable(osgGeoSet); regisiterPfObjectForOsgObject(geoset,osgGeoSet); @@ -520,7 +532,6 @@ osg::GeoSet* ConvertFromPerformer::visitGeoSet(osg::Geode* osgGeode,pfGeoSet* ge else cc = nv; - osg::Vec3* osg_coords = new osg::Vec3 [cc]; for( i = 0; i < cc; i++ ) { @@ -553,10 +564,10 @@ osg::GeoSet* ConvertFromPerformer::visitGeoSet(osg::Geode* osgGeode,pfGeoSet* ge { int bind = geoset->getAttrBind( PFGS_NORMAL3 ); int nn = bind == PFGS_OFF ? 0 : - bind == PFGS_OVERALL ? 1 : - bind == PFGS_PER_PRIM ? geoset->getNumPrims() : - bind == PFGS_PER_VERTEX ? nv-flat_shaded_offset : 0; - + bind == PFGS_OVERALL ? 1 : + bind == PFGS_PER_PRIM ? geoset->getNumPrims() : + bind == PFGS_PER_VERTEX ? nv-flat_shaded_offset : 0; + // set the normal binding type. osgGeoSet->setNormalBinding(_gsetBindMap[bind]); @@ -572,7 +583,6 @@ osg::GeoSet* ConvertFromPerformer::visitGeoSet(osg::Geode* osgGeode,pfGeoSet* ge else cc = nn; - osg::Vec3* osg_norms = new osg::Vec3 [cc]; for( i = 0; i < cc; i++ ) { @@ -605,9 +615,9 @@ osg::GeoSet* ConvertFromPerformer::visitGeoSet(osg::Geode* osgGeode,pfGeoSet* ge { int bind = geoset->getAttrBind( PFGS_TEXCOORD2 ); int nn = bind == PFGS_OFF ? 0 : - bind == PFGS_OVERALL ? 1 : - bind == PFGS_PER_PRIM ? geoset->getNumPrims() : - bind == PFGS_PER_VERTEX ? nv : 0; + bind == PFGS_OVERALL ? 1 : + bind == PFGS_PER_PRIM ? geoset->getNumPrims() : + bind == PFGS_PER_VERTEX ? nv : 0; // set the normal binding type. osgGeoSet->setTextureBinding(_gsetBindMap[bind]); @@ -624,7 +634,6 @@ osg::GeoSet* ConvertFromPerformer::visitGeoSet(osg::Geode* osgGeode,pfGeoSet* ge else cc = nn; - osg::Vec2* osg_tcoords = new osg::Vec2 [cc]; for( i = 0; i < cc; i++ ) { @@ -656,9 +665,9 @@ osg::GeoSet* ConvertFromPerformer::visitGeoSet(osg::Geode* osgGeode,pfGeoSet* ge { int bind = geoset->getAttrBind( PFGS_COLOR4 ); int nn = bind == PFGS_OFF ? 0 : - bind == PFGS_OVERALL ? 1 : - bind == PFGS_PER_PRIM ? geoset->getNumPrims() : - bind == PFGS_PER_VERTEX ? nv-flat_shaded_offset : 0; + bind == PFGS_OVERALL ? 1 : + bind == PFGS_PER_PRIM ? geoset->getNumPrims() : + bind == PFGS_PER_VERTEX ? nv-flat_shaded_offset : 0; // set the normal binding type. osgGeoSet->setColorBinding(_gsetBindMap[bind]); @@ -675,7 +684,6 @@ osg::GeoSet* ConvertFromPerformer::visitGeoSet(osg::Geode* osgGeode,pfGeoSet* ge else cc = nn; - osg::Vec4* osg_colors = new osg::Vec4 [cc]; for( i = 0; i < cc; i++ ) { @@ -704,313 +712,326 @@ osg::GeoSet* ConvertFromPerformer::visitGeoSet(osg::Geode* osgGeode,pfGeoSet* ge return osgGeoSet; } -osg::GeoState* ConvertFromPerformer::visitGeoState(osg::GeoSet* osgGeoSet,pfGeoState* geostate) + +osg::StateSet* ConvertFromPerformer::visitGeoState(osg::GeoSet* osgGeoSet,pfGeoState* geostate) { if (geostate==NULL) return NULL; - osg::GeoState* osgGeoState = dynamic_cast(getOsgObject(geostate)); - if (osgGeoState) + osg::StateSet* osgStateSet = dynamic_cast(getOsgObject(geostate)); + if (osgStateSet) { - if (osgGeoSet) osgGeoSet->setGeoState(osgGeoState); - return osgGeoState; + if (osgGeoSet) osgGeoSet->setStateSet(osgStateSet); + return osgStateSet; } - osgGeoState = new osg::GeoState; - if (osgGeoSet) osgGeoSet->setGeoState(osgGeoState); - - regisiterPfObjectForOsgObject(geostate,osgGeoState); + osgStateSet = new osg::StateSet; + if (osgGeoSet) osgGeoSet->setStateSet(osgStateSet); + regisiterPfObjectForOsgObject(geostate,osgStateSet); // Don could you fill in some of these blanks??? unsigned int inherit = geostate->getInherit(); -// osg::notify(DEBUG) << endl << "Inherit = "<setMode(osg::GeoState::TRANSPARENCY,osg::GeoState::INHERIT); - else + if (inherit & PFSTATE_TRANSPARENCY) osgStateSet->setMode(GL_BLEND,osg::StateAttribute::INHERIT); + else { int mode = geostate->getMode(PFSTATE_TRANSPARENCY); switch(mode) { - case(PFTR_FAST): - case(PFTR_HIGH_QUALITY): - case(PFTR_BLEND_ALPHA): - case(PFTR_MS_ALPHA): - case(PFTR_MS_ALPHA_MASK): - case(PFTR_NO_OCCLUDE): - case(PFTR_ON): osgGeoState->setMode(osg::GeoState::TRANSPARENCY,osg::GeoState::ON);break; - case(PFTR_OFF): osgGeoState->setMode(osg::GeoState::TRANSPARENCY,osg::GeoState::OFF);break; - default: osgGeoState->setMode(osg::GeoState::TRANSPARENCY,osg::GeoState::INHERIT);break; + case(PFTR_FAST): + case(PFTR_HIGH_QUALITY): + case(PFTR_BLEND_ALPHA): + case(PFTR_MS_ALPHA): + case(PFTR_MS_ALPHA_MASK): + case(PFTR_NO_OCCLUDE): + case(PFTR_ON): + osgStateSet->setMode(GL_BLEND,osg::StateAttribute::ON); + osgStateSet->setRenderingHint(osg::StateSet::TRANSPARENT_BIN); + break; + case(PFTR_OFF): osgStateSet->setMode(GL_BLEND,osg::StateAttribute::OFF);break; + default: osgStateSet->setMode(GL_BLEND,osg::StateAttribute::INHERIT);break; } } - if (inherit & PFSTATE_ENTEXTURE) osgGeoState->setMode(osg::GeoState::TEXTURE,osg::GeoState::INHERIT); + if (inherit & PFSTATE_ENTEXTURE) osgStateSet->setMode(GL_TEXTURE_2D,osg::StateAttribute::INHERIT); else { int mode = geostate->getMode(PFSTATE_ENTEXTURE); switch(mode) { - case(PF_ON): osgGeoState->setMode(osg::GeoState::TEXTURE,osg::GeoState::ON);break; - case(PF_OFF): - default: osgGeoState->setMode(osg::GeoState::TEXTURE,osg::GeoState::OFF);break; + case(PF_ON): osgStateSet->setMode(GL_TEXTURE_2D,osg::StateAttribute::ON);break; + case(PF_OFF): + default: osgStateSet->setMode(GL_TEXTURE_2D,osg::StateAttribute::OFF);break; } } - if (inherit & PFSTATE_CULLFACE) osgGeoState->setMode(osg::GeoState::FACE_CULL,osg::GeoState::INHERIT); - else + if (inherit & PFSTATE_CULLFACE) osgStateSet->setMode(GL_CULL_FACE,osg::StateAttribute::INHERIT); + else { int mode = geostate->getMode(PFSTATE_CULLFACE); switch(mode) { - case(PFCF_BACK): + case(PFCF_BACK): { - osgGeoState->setMode(osg::GeoState::FACE_CULL,osg::GeoState::ON); + osgStateSet->setMode(GL_CULL_FACE,osg::StateAttribute::ON); osg::CullFace *cf = new osg::CullFace; cf->setMode(osg::CullFace::BACK); - osgGeoState->setAttribute(osg::GeoState::FACE_CULL,cf); + osgStateSet->setAttribute(cf); } break; - - case(PFCF_FRONT): + + case(PFCF_FRONT): { - osgGeoState->setMode(osg::GeoState::FACE_CULL,osg::GeoState::ON); + osgStateSet->setMode(GL_CULL_FACE,osg::StateAttribute::ON); osg::CullFace *cf = new osg::CullFace; cf->setMode(osg::CullFace::FRONT); - osgGeoState->setAttribute(osg::GeoState::FACE_CULL,cf); + osgStateSet->setAttribute(cf); } break; - case(PFCF_BOTH): + case(PFCF_BOTH): { - osgGeoState->setMode(osg::GeoState::FACE_CULL,osg::GeoState::ON); + osgStateSet->setMode(GL_CULL_FACE,osg::StateAttribute::ON); osg::CullFace *cf = new osg::CullFace; cf->setMode(osg::CullFace::FRONT_AND_BACK); - osgGeoState->setAttribute(osg::GeoState::FACE_CULL,cf); + osgStateSet->setAttribute(cf); } break; - case(PFCF_OFF): - default: osgGeoState->setMode(osg::GeoState::FACE_CULL,osg::GeoState::OFF);break; + case(PFCF_OFF): + default: osgStateSet->setMode(GL_CULL_FACE,osg::StateAttribute::OFF);break; } } - if (inherit & PFSTATE_ENLIGHTING) osgGeoState->setMode(osg::GeoState::LIGHTING,osg::GeoState::INHERIT); - else + if (inherit & PFSTATE_ENLIGHTING) osgStateSet->setMode(GL_LIGHTING,osg::StateAttribute::INHERIT); + else { int mode = geostate->getMode(PFSTATE_ENLIGHTING); switch(mode) { - case(PF_ON): osgGeoState->setMode(osg::GeoState::LIGHTING,osg::GeoState::ON);break; - case(PF_OFF): - default: osgGeoState->setMode(osg::GeoState::LIGHTING,osg::GeoState::OFF);break; + case(PF_ON): osgStateSet->setMode(GL_LIGHTING,osg::StateAttribute::ON);break; + case(PF_OFF): + default: osgStateSet->setMode(GL_LIGHTING,osg::StateAttribute::OFF);break; } } - if (inherit & PFSTATE_ENFOG) osgGeoState->setMode(osg::GeoState::FOG,osg::GeoState::INHERIT); - else + if (inherit & PFSTATE_ENFOG) osgStateSet->setMode(GL_FOG,osg::StateAttribute::INHERIT); + else { int mode = geostate->getMode(PFSTATE_ENFOG); switch(mode) { - case(PF_ON): osgGeoState->setMode(osg::GeoState::FOG,osg::GeoState::ON);break; - case(PF_OFF): - default: osgGeoState->setMode(osg::GeoState::FOG,osg::GeoState::OFF);break; + case(PF_ON): osgStateSet->setMode(GL_FOG,osg::StateAttribute::ON);break; + case(PF_OFF): + default: osgStateSet->setMode(GL_FOG,osg::StateAttribute::OFF);break; } } -// not currently supported by OSG -// if (inherit & PFSTATE_ENWIREFRAME) osgGeoState->setMode(osg::GeoState::WIREFRAME,osg::GeoState::INHERIT); -// else -// { -// int mode = geostate->getMode(PFSTATE_ENWIREFRAME); -// switch(mode) -// { -// case(PF_ON): osgGeoState->setMode(osg::GeoState::WIREFRAME,osg::GeoState::ON);break; -// case(PF_OFF): -// default: osgGeoState->setMode(osg::GeoState::WIREFRAME,osg::GeoState::OFF);break; -// } -// } + // not currently supported by OSG + // if (inherit & PFSTATE_ENWIREFRAME) osgStateSet->setMode(osg::StateSet::WIREFRAME,osg::StateAttribute::INHERIT); + // else + // { + // int mode = geostate->getMode(PFSTATE_ENWIREFRAME); + // switch(mode) + // { + // case(PF_ON): osgStateSet->setMode(osg::StateSet::WIREFRAME,osg::StateAttribute::ON);break; + // case(PF_OFF): + // default: osgStateSet->setMode(osg::StateSet::WIREFRAME,osg::StateAttribute::OFF);break; + // } + // } + + // redundent in OSG's implementation of texmat mode + // if (inherit & PFSTATE_ENTEXMAT) osgStateSet->setMode(osg::StateSet::TEXMAT,osg::StateAttribute::INHERIT); + // else + // { + // int mode = geostate->getMode(PFSTATE_ENTEXMAT); + // switch(mode) + // { + // case(PF_ON): osgStateSet->setMode(osg::StateSet::TEXMAT,osg::StateAttribute::ON);break; + // case(PF_OFF): + // default: osgStateSet->setMode(osg::StateSet::TEXMAT,osg::StateAttribute::OFF);break; + // } + // } -// redundent in OSG's implementation of texmat mode -// if (inherit & PFSTATE_ENTEXMAT) osgGeoState->setMode(osg::GeoState::TEXMAT,osg::GeoState::INHERIT); -// else -// { -// int mode = geostate->getMode(PFSTATE_ENTEXMAT); -// switch(mode) -// { -// case(PF_ON): osgGeoState->setMode(osg::GeoState::TEXMAT,osg::GeoState::ON);break; -// case(PF_OFF): -// default: osgGeoState->setMode(osg::GeoState::TEXMAT,osg::GeoState::OFF);break; -// } -// } - - if (inherit & PFSTATE_ENTEXGEN) osgGeoState->setMode(osg::GeoState::TEXGEN,osg::GeoState::INHERIT); - else - { - int mode = geostate->getMode(PFSTATE_ENTEXGEN); - switch(mode) - { - case(PF_ON): osgGeoState->setMode(osg::GeoState::TEXGEN,osg::GeoState::ON);break; - case(PF_OFF): - default: osgGeoState->setMode(osg::GeoState::TEXGEN,osg::GeoState::OFF);break; - } - } - + // commenting out the following block since the TexGen should be set + // appropriately by the osg::TexGen block below. + // if (inherit & PFSTATE_ENTEXGEN) osgStateSet->setMode(osg::StateSet::TEXGEN,osg::StateAttribute::INHERIT); + // else + // { + // int mode = geostate->getMode(PFSTATE_ENTEXGEN); + // switch(mode) + // { + // case(PF_ON): osgStateSet->setMode(osg::StateSet::TEXGEN,osg::StateAttribute::ON);break; + // case(PF_OFF): + // default: osgStateSet->setMode(osg::StateSet::TEXGEN,osg::StateAttribute::OFF);break; + // } + // } + // + + pfMaterial* front_mat = (pfMaterial*)geostate->getAttr(PFSTATE_FRONTMTL); pfMaterial* back_mat = (pfMaterial*)geostate->getAttr(PFSTATE_BACKMTL); - visitMaterial(osgGeoState,front_mat,back_mat); - + visitMaterial(osgStateSet,front_mat,back_mat); + pfTexture* tex = (pfTexture*)geostate->getAttr(PFSTATE_TEXTURE); - visitTexture(osgGeoState,tex); + visitTexture(osgStateSet,tex); pfTexGen* texgen = (pfTexGen*)geostate->getAttr(PFSTATE_TEXGEN); + if (texgen) { osg::TexGen* osgTexGen = new osg::TexGen(); int mode = texgen->getMode(PF_S); + + // should this follow setPlane block be within the following switch? + float x, y, z, d; + texgen->getPlane(PF_S, &x, &y, &z, &d); + osgTexGen->setPlane(osg::TexGen::S, osg::Vec4(x,y,z,d)); + texgen->getPlane(PF_T, &x, &y, &z, &d); + osgTexGen->setPlane(osg::TexGen::T, osg::Vec4(x,y,z,d)); + switch(mode) { - case(PFTG_OBJECT_LINEAR) : - osgTexGen->setMode(osg::TexGen::OBJECT_LINEAR); - osgGeoState->setAttribute(osg::GeoState::TEXGEN,osgTexGen); - break; - case(PFTG_EYE_LINEAR_IDENT) : - cerr << "TexGen Mode PFTG_EYE_LINEAR_IDENT not currently supported by the OSG,"<setMode(osg::TexGen::EYE_LINEAR); - osgGeoState->setAttribute(osg::GeoState::TEXGEN,osgTexGen); - break; - case(PFTG_SPHERE_MAP) : - osgTexGen->setMode(osg::TexGen::SPHERE_MAP); - osgGeoState->setAttribute(osg::GeoState::TEXGEN,osgTexGen); - break; - case(PFTG_OFF) : - osgGeoState->setMode(osg::GeoState::TEXGEN,osg::GeoState::OFF); - break; - case(PFTG_OBJECT_DISTANCE_TO_LINE) : - cerr << "TexGen Mode PFTG_OBJECT_DISTANCE_TO_LINE not currently supported by the OSG."<setMode(osg::GeoState::TEXGEN,osg::GeoState::OFF); - break; - case(PFTG_EYE_DISTANCE_TO_LINE) : - cerr << "TexGen Mode PFTG_EYE_DISTANCE_TO_LINE not currently supported by the OSG."<setMode(osg::GeoState::TEXGEN,osg::GeoState::OFF); - break; - default: - cerr << "TexGen Mode "<setMode(osg::GeoState::TEXGEN,osg::GeoState::OFF); - break; + case(PFTG_OBJECT_LINEAR) : + osgTexGen->setMode(osg::TexGen::OBJECT_LINEAR); + osgStateSet->setAttribute(osgTexGen); + break; + case(PFTG_EYE_LINEAR_IDENT) : + cerr << "TexGen Mode PFTG_EYE_LINEAR_IDENT not currently supported by the OSG,"<setMode(osg::TexGen::EYE_LINEAR); + osgStateSet->setAttribute(osgTexGen); + break; + case(PFTG_SPHERE_MAP) : + osgTexGen->setMode(osg::TexGen::SPHERE_MAP); + osgStateSet->setAttribute(osgTexGen); + break; + case(PFTG_OFF) : + osgTexGen->setStateSetModes(*osgStateSet,osg::StateAttribute::OFF); + break; + case(PFTG_OBJECT_DISTANCE_TO_LINE) : + cerr << "TexGen Mode PFTG_OBJECT_DISTANCE_TO_LINE not currently supported by the OSG."<setStateSetModes(*osgStateSet,osg::StateAttribute::OFF); + break; + case(PFTG_EYE_DISTANCE_TO_LINE) : + cerr << "TexGen Mode PFTG_EYE_DISTANCE_TO_LINE not currently supported by the OSG."<setStateSetModes(*osgStateSet,osg::StateAttribute::OFF); + break; + default: + cerr << "TexGen Mode "<setStateSetModes(*osgStateSet,osg::StateAttribute::OFF); + break; } - } pfMatrix* texmat = (pfMatrix*)geostate->getAttr(PFSTATE_TEXMAT); if (texmat) { osg::Matrix osgMatrix((*texmat)[0][0],(*texmat)[0][1],(*texmat)[0][2],(*texmat)[0][3], - (*texmat)[1][0],(*texmat)[1][1],(*texmat)[1][2],(*texmat)[1][3], - (*texmat)[2][0],(*texmat)[2][1],(*texmat)[2][2],(*texmat)[2][3], - (*texmat)[3][0],(*texmat)[3][1],(*texmat)[3][2],(*texmat)[3][3]); + (*texmat)[1][0],(*texmat)[1][1],(*texmat)[1][2],(*texmat)[1][3], + (*texmat)[2][0],(*texmat)[2][1],(*texmat)[2][2],(*texmat)[2][3], + (*texmat)[3][0],(*texmat)[3][1],(*texmat)[3][2],(*texmat)[3][3]); osg::TexMat* osgTexMat = new osg::TexMat(); - osgTexMat->copy(osgMatrix); - osgGeoState->setAttribute(osg::GeoState::TEXMAT,osgTexMat); + osgTexMat->setMatrix(osgMatrix); + osgStateSet->setAttribute(osgTexMat); } - - return osgGeoState; + return osgStateSet; } -osg::Material* ConvertFromPerformer::visitMaterial(osg::GeoState* osgGeoState,pfMaterial* front_mat,pfMaterial* back_mat) + +osg::Material* ConvertFromPerformer::visitMaterial(osg::StateSet* osgStateSet,pfMaterial* front_mat,pfMaterial* back_mat) { if (front_mat==NULL && back_mat==NULL) return NULL; - osg::Material* osgMaterial = new osg::Material; - if (osgGeoState) osgGeoState->setAttribute(osg::GeoState::MATERIAL,osgMaterial); + if (osgStateSet) osgStateSet->setAttribute(osgMaterial); pfMaterial* material = NULL; if (front_mat==back_mat) material = front_mat; else if (back_mat==NULL) material = front_mat; else if (front_mat==NULL) material = back_mat; - if (material) // single materials for front and back. + if (material) // single materials for front and back. { - - int colorMode = material->getColorMode(material->getSide()); - - switch(colorMode){ - case(PFMTL_CMODE_AMBIENT_AND_DIFFUSE): osgMaterial->setColorMode(osg::Material::AMBIENT_AND_DIFFUSE); break; - case(PFMTL_CMODE_AMBIENT): osgMaterial->setColorMode(osg::Material::AMBIENT); break; - case(PFMTL_CMODE_DIFFUSE): osgMaterial->setColorMode(osg::Material::DIFFUSE); break; - case(PFMTL_CMODE_EMISSION): osgMaterial->setColorMode(osg::Material::EMISSION); break; - case(PFMTL_CMODE_SPECULAR): osgMaterial->setColorMode(osg::Material::SPECULAR); break; - case(PFMTL_CMODE_OFF): osgMaterial->setColorMode(osg::Material::OFF); break; - } - - float s = material->getShininess(); - osgMaterial->setShininess(osg::Material::FACE_FRONT_AND_BACK,s); + int colorMode = material->getColorMode(material->getSide()); + + switch(colorMode) + { + case(PFMTL_CMODE_AMBIENT_AND_DIFFUSE): osgMaterial->setColorMode(osg::Material::AMBIENT_AND_DIFFUSE); break; + case(PFMTL_CMODE_AMBIENT): osgMaterial->setColorMode(osg::Material::AMBIENT); break; + case(PFMTL_CMODE_DIFFUSE): osgMaterial->setColorMode(osg::Material::DIFFUSE); break; + case(PFMTL_CMODE_EMISSION): osgMaterial->setColorMode(osg::Material::EMISSION); break; + case(PFMTL_CMODE_SPECULAR): osgMaterial->setColorMode(osg::Material::SPECULAR); break; + case(PFMTL_CMODE_OFF): osgMaterial->setColorMode(osg::Material::OFF); break; + } + + float s = material->getShininess()/128.0f; + osgMaterial->setShininess(osg::Material::FRONT_AND_BACK,s); float a = material->getAlpha(); float r,g,b; material->getColor(PFMTL_AMBIENT,&r,&g,&b); - osgMaterial->setAmbient(osg::Material::FACE_FRONT_AND_BACK,osg::Vec4(r,g,b,a)); + osgMaterial->setAmbient(osg::Material::FRONT_AND_BACK,osg::Vec4(r,g,b,a)); material->getColor(PFMTL_DIFFUSE,&r,&g,&b); - osgMaterial->setDiffuse(osg::Material::FACE_FRONT_AND_BACK,osg::Vec4(r,g,b,a)); + osgMaterial->setDiffuse(osg::Material::FRONT_AND_BACK,osg::Vec4(r,g,b,a)); material->getColor(PFMTL_EMISSION,&r,&g,&b); - osgMaterial->setEmission(osg::Material::FACE_FRONT_AND_BACK,osg::Vec4(r,g,b,a)); + osgMaterial->setEmission(osg::Material::FRONT_AND_BACK,osg::Vec4(r,g,b,a)); material->getColor(PFMTL_SPECULAR,&r,&g,&b); - osgMaterial->setSpecular(osg::Material::FACE_FRONT_AND_BACK,osg::Vec4(r,g,b,a)); + osgMaterial->setSpecular(osg::Material::FRONT_AND_BACK,osg::Vec4(r,g,b,a)); } - else // seperate materials for front and back. + else // seperate materials for front and back. { int colorMode = front_mat->getColorMode(front_mat->getSide()); - - switch(colorMode){ - case(PFMTL_CMODE_AMBIENT_AND_DIFFUSE): osgMaterial->setColorMode(osg::Material::AMBIENT_AND_DIFFUSE); break; - case(PFMTL_CMODE_AMBIENT): osgMaterial->setColorMode(osg::Material::AMBIENT); break; - case(PFMTL_CMODE_DIFFUSE): osgMaterial->setColorMode(osg::Material::DIFFUSE); break; - case(PFMTL_CMODE_EMISSION): osgMaterial->setColorMode(osg::Material::EMISSION); break; - case(PFMTL_CMODE_SPECULAR): osgMaterial->setColorMode(osg::Material::SPECULAR); break; - case(PFMTL_CMODE_OFF): osgMaterial->setColorMode(osg::Material::OFF); break; + + switch(colorMode) + { + case(PFMTL_CMODE_AMBIENT_AND_DIFFUSE): osgMaterial->setColorMode(osg::Material::AMBIENT_AND_DIFFUSE); break; + case(PFMTL_CMODE_AMBIENT): osgMaterial->setColorMode(osg::Material::AMBIENT); break; + case(PFMTL_CMODE_DIFFUSE): osgMaterial->setColorMode(osg::Material::DIFFUSE); break; + case(PFMTL_CMODE_EMISSION): osgMaterial->setColorMode(osg::Material::EMISSION); break; + case(PFMTL_CMODE_SPECULAR): osgMaterial->setColorMode(osg::Material::SPECULAR); break; + case(PFMTL_CMODE_OFF): osgMaterial->setColorMode(osg::Material::OFF); break; } - float s; float a; @@ -1018,60 +1039,86 @@ osg::Material* ConvertFromPerformer::visitMaterial(osg::GeoState* osgGeoState,pf // front material s = front_mat->getShininess(); - osgMaterial->setShininess(osg::Material::FACE_FRONT,s); + osgMaterial->setShininess(osg::Material::FRONT,s); a = front_mat->getAlpha(); front_mat->getColor(PFMTL_AMBIENT,&r,&g,&b); - osgMaterial->setAmbient(osg::Material::FACE_FRONT,osg::Vec4(r,g,b,a)); + osgMaterial->setAmbient(osg::Material::FRONT,osg::Vec4(r,g,b,a)); front_mat->getColor(PFMTL_DIFFUSE,&r,&g,&b); - osgMaterial->setDiffuse(osg::Material::FACE_FRONT,osg::Vec4(r,g,b,a)); + osgMaterial->setDiffuse(osg::Material::FRONT,osg::Vec4(r,g,b,a)); front_mat->getColor(PFMTL_EMISSION,&r,&g,&b); - osgMaterial->setEmission(osg::Material::FACE_FRONT,osg::Vec4(r,g,b,a)); + osgMaterial->setEmission(osg::Material::FRONT,osg::Vec4(r,g,b,a)); front_mat->getColor(PFMTL_SPECULAR,&r,&g,&b); - osgMaterial->setSpecular(osg::Material::FACE_FRONT,osg::Vec4(r,g,b,a)); - + osgMaterial->setSpecular(osg::Material::FRONT,osg::Vec4(r,g,b,a)); // back material s = back_mat->getShininess(); - osgMaterial->setShininess(osg::Material::FACE_BACK,s); + osgMaterial->setShininess(osg::Material::BACK,s); a = back_mat->getAlpha(); back_mat->getColor(PFMTL_AMBIENT,&r,&g,&b); - osgMaterial->setAmbient(osg::Material::FACE_BACK,osg::Vec4(r,g,b,a)); + osgMaterial->setAmbient(osg::Material::BACK,osg::Vec4(r,g,b,a)); back_mat->getColor(PFMTL_DIFFUSE,&r,&g,&b); - osgMaterial->setDiffuse(osg::Material::FACE_BACK,osg::Vec4(r,g,b,a)); + osgMaterial->setDiffuse(osg::Material::BACK,osg::Vec4(r,g,b,a)); back_mat->getColor(PFMTL_EMISSION,&r,&g,&b); - osgMaterial->setEmission(osg::Material::FACE_BACK,osg::Vec4(r,g,b,a)); + osgMaterial->setEmission(osg::Material::BACK,osg::Vec4(r,g,b,a)); back_mat->getColor(PFMTL_SPECULAR,&r,&g,&b); - osgMaterial->setSpecular(osg::Material::FACE_BACK,osg::Vec4(r,g,b,a)); + osgMaterial->setSpecular(osg::Material::BACK,osg::Vec4(r,g,b,a)); } - + return osgMaterial; } -osg::Texture* ConvertFromPerformer::visitTexture(osg::GeoState* osgGeoState,pfTexture* tex) + +static osg::Texture::FilterMode getTexfilter(int filter, int pftype) +{ + if (filter == PFTEX_MINFILTER) + { + + if (pftype & PFTEX_LINEAR) + return osg::Texture::NEAREST_MIPMAP_LINEAR; + else if (pftype & PFTEX_BILINEAR) + return osg::Texture::LINEAR_MIPMAP_NEAREST; + else if (pftype & PFTEX_TRILINEAR) + return osg::Texture::LINEAR_MIPMAP_LINEAR; + + return osg::Texture::NEAREST_MIPMAP_LINEAR; + + } + else + { + // MAGFILTER + + // not quite sure what is supposed to be interpret the Peformer + // filter modes here so will simple go with OpenGL default. + + return osg::Texture::LINEAR; + } +} + + +osg::Texture* ConvertFromPerformer::visitTexture(osg::StateSet* osgStateSet,pfTexture* tex) { if (tex==NULL) return NULL; osg::Texture* osgTexture = new osg::Texture; _pfToOsgMap[tex] = osgTexture; - if (osgGeoState) osgGeoState->setAttribute(osg::GeoState::TEXTURE,osgTexture); - + if (osgStateSet) osgStateSet->setAttribute(osgTexture); int repeat_r = tex->getRepeat(PFTEX_WRAP_R); int repeat_s = tex->getRepeat(PFTEX_WRAP_S); int repeat_t = tex->getRepeat(PFTEX_WRAP_T); - + if (repeat_r==PFTEX_CLAMP) osgTexture->setWrap(osg::Texture::WRAP_R,osg::Texture::CLAMP); else osgTexture->setWrap(osg::Texture::WRAP_R,osg::Texture::REPEAT); @@ -1081,18 +1128,28 @@ osg::Texture* ConvertFromPerformer::visitTexture(osg::GeoState* osgGeoState,pfTe if (repeat_t==PFTEX_CLAMP) osgTexture->setWrap(osg::Texture::WRAP_T,osg::Texture::CLAMP); else osgTexture->setWrap(osg::Texture::WRAP_T,osg::Texture::REPEAT); + // filter + #if 1 + osgTexture->setFilter(osg::Texture::MIN_FILTER, + getTexfilter(PFTEX_MINFILTER, + tex->getFilter(PFTEX_MINFILTER))); + osgTexture->setFilter(osg::Texture::MAG_FILTER, + getTexfilter(PFTEX_MAGFILTER, + tex->getFilter(PFTEX_MAGFILTER))); + #endif + + // image std::string texName = tex->getName(); if (_saveImagesAsRGB) { - std::string strippedName = osg::getStrippedName(texName); + std::string strippedName = osgDB::getStrippedName(texName); texName = _saveImageDirectory+strippedName+".rgb"; tex->saveFile(texName.c_str()); } - if (!_saveAbsoluteImagePath) texName = osg::getSimpleFileName(texName); + if (!_saveAbsoluteImagePath) texName = osgDB::getSimpleFileName(texName); - int s=0; int t=0; int r=0; @@ -1105,20 +1162,20 @@ osg::Texture* ConvertFromPerformer::visitTexture(osg::GeoState* osgGeoState,pfTe unsigned int pixelFormat = comp == 1 ? GL_LUMINANCE : - comp == 2 ? GL_LUMINANCE_ALPHA : - comp == 3 ? GL_RGB : - comp == 4 ? GL_RGBA : (GLenum)-1; + comp == 2 ? GL_LUMINANCE_ALPHA : + comp == 3 ? GL_RGB : + comp == 4 ? GL_RGBA : (GLenum)-1; unsigned int dataType = GL_UNSIGNED_BYTE; osg::Image* image = new osg::Image; image->setFileName(texName.c_str()); image->setImage(s,t,r, - internalFormat, - pixelFormat, - dataType, - (unsigned char*)imageData); - + internalFormat, + pixelFormat, + dataType, + (unsigned char*)imageData); + osgTexture->setImage(image); return osgTexture; diff --git a/src/osgPlugins/pfb/ConvertFromPerformer.h b/src/osgPlugins/pfb/ConvertFromPerformer.h index 1cd4df47c..920792031 100644 --- a/src/osgPlugins/pfb/ConvertFromPerformer.h +++ b/src/osgPlugins/pfb/ConvertFromPerformer.h @@ -9,7 +9,9 @@ #include #include #include -#include +#include +#include +#include // Performer includes. #include @@ -44,19 +46,15 @@ class ConvertFromPerformer { int getNumVerts(pfGeoSet *gset); osg::GeoSet* visitGeoSet(osg::Geode* osgParent,pfGeoSet* geoset); - osg::GeoState* visitGeoState(osg::GeoSet* osgGeoSet,pfGeoState* geostate); - osg::Material* visitMaterial(osg::GeoState* osgGeoState,pfMaterial* front_mat,pfMaterial* back_mat); - osg::Texture* visitTexture(osg::GeoState* osgGeoState,pfTexture* tex); + osg::StateSet* visitGeoState(osg::GeoSet* osgGeoSet,pfGeoState* geostate); + osg::Material* visitMaterial(osg::StateSet* osgStateSet,pfMaterial* front_mat,pfMaterial* back_mat); + osg::Texture* visitTexture(osg::StateSet* osgStateSet,pfTexture* tex); typedef std::map GSetPrimitiveMap; typedef std::map GSetBindingMap; - typedef std::map GStateTypeMap; - typedef std::map GStateModeMap; GSetPrimitiveMap _gsetPrimMap; GSetBindingMap _gsetBindMap; - GStateTypeMap _gstateTypeMap; - GStateModeMap _gstateModeMap; bool _saveImagesAsRGB; bool _saveAbsoluteImagePath; diff --git a/src/osgPlugins/pfb/ConvertToPerformer.cpp b/src/osgPlugins/pfb/ConvertToPerformer.cpp index 49c842535..13b65acee 100644 --- a/src/osgPlugins/pfb/ConvertToPerformer.cpp +++ b/src/osgPlugins/pfb/ConvertToPerformer.cpp @@ -1,20 +1,20 @@ #include "ConvertToPerformer.h" -#include #include -#include +#include #include #include -#include #include #include #include #include -#include -#include - #include +#include +#include +#include + + #include #include #include @@ -36,24 +36,24 @@ using namespace std; #endif -extern "C" { - -extern pfNode * -pfdLoadFile_osg (char *fileName) +extern "C" { - osg::Node* node = osg::loadNodeFile(fileName); - if (node==NULL) return 0; - ConvertToPerformer converter; - return converter.convert(node); -} + extern pfNode * + pfdLoadFile_osg (char *fileName) + { + osg::Node* node = osgDB::readNodeFile(fileName); + if (node==NULL) return 0; + + ConvertToPerformer converter; + return converter.convert(node); + } }; - ConvertToPerformer::ConvertToPerformer() { - setTraverseMode(osg::NodeVisitor::TRAVERSE_ALL_CHILDREN); + setTraversalMode(osg::NodeVisitor::TRAVERSE_ALL_CHILDREN); _pfParent = NULL; _pfRoot = NULL; @@ -75,45 +75,40 @@ ConvertToPerformer::ConvertToPerformer() _gsetBindMap[osg::GeoSet::BIND_OVERALL] = PFGS_OVERALL; _gsetBindMap[osg::GeoSet::BIND_PERPRIM] = PFGS_PER_PRIM; _gsetBindMap[osg::GeoSet::BIND_PERVERTEX] = PFGS_PER_VERTEX; - - - _gstateTypeMap[osg::GeoState::TRANSPARENCY] = PFSTATE_TRANSPARENCY; - _gstateTypeMap[osg::GeoState::ANTIALIAS] = PFSTATE_ANTIALIAS; - _gstateTypeMap[osg::GeoState::LIGHTING] = PFSTATE_ENLIGHTING; - _gstateTypeMap[osg::GeoState::TEXTURE] = PFSTATE_ENTEXTURE; - _gstateTypeMap[osg::GeoState::FOG] = PFSTATE_ENFOG; - _gstateTypeMap[osg::GeoState::FACE_CULL] = PFSTATE_CULLFACE; - _gstateTypeMap[osg::GeoState::WIREFRAME] = PFSTATE_ENWIREFRAME; - _gstateTypeMap[osg::GeoState::TEXGEN] = PFSTATE_ENTEXGEN; - _gstateTypeMap[osg::GeoState::TEXMAT] = PFSTATE_ENTEXMAT; - } + ConvertToPerformer::~ConvertToPerformer() { } -pfNode* ConvertToPerformer::convert(osg::Node* node) + +pfNode* ConvertToPerformer::convert(const osg::Node* node) { _pfRoot = NULL; if (node) { - node->accept(*this); + // a hack to get round current limitation of node visitor which + // only handles non const operations. + osg::Node* non_const_node = const_cast(node); + non_const_node->accept(*this); } return _pfRoot; } + pfObject* ConvertToPerformer::getPfObject(osg::Object* osgObj) { OsgObjectToPfObjectMap::iterator fitr = _osgToPfMap.find(osgObj); if (fitr != _osgToPfMap.end()) { - osg::notify(osg::DEBUG) << "Found shared object"<(getPfObject(&osgDCS)); + pfDCS* pf_dcs = dynamic_cast(getPfObject(&osgTransform)); if (pf_dcs) { if (_pfParent) _pfParent->addChild(pf_dcs); @@ -166,28 +163,28 @@ void ConvertToPerformer::apply(osg::DCS& osgDCS) if (!_pfRoot) _pfRoot = pf_dcs; if (_pfParent) _pfParent->addChild(pf_dcs); - regisiterOsgObjectForPfObject(&osgDCS,pf_dcs); + regisiterOsgObjectForPfObject(&osgTransform,pf_dcs); - if (!osgDCS.getName().empty()) pf_dcs->setName(osgDCS.getName().c_str()); + if (!osgTransform.getName().empty()) pf_dcs->setName(osgTransform.getName().c_str()); + + osg::Matrix& matrix = osgTransform.getMatrix(); + + pfMatrix pf_matrix(matrix._mat[0][0],matrix._mat[0][1],matrix._mat[0][2],matrix._mat[0][3], + matrix._mat[1][0],matrix._mat[1][1],matrix._mat[1][2],matrix._mat[1][3], + matrix._mat[2][0],matrix._mat[2][1],matrix._mat[2][2],matrix._mat[2][3], + matrix._mat[3][0],matrix._mat[3][1],matrix._mat[3][2],matrix._mat[3][3]); - osg::Matrix* matrix = osgDCS.getMatrix(); - - pfMatrix pf_matrix(matrix->_mat[0][0],matrix->_mat[0][1],matrix->_mat[0][2],matrix->_mat[0][3], - matrix->_mat[1][0],matrix->_mat[1][1],matrix->_mat[1][2],matrix->_mat[1][3], - matrix->_mat[2][0],matrix->_mat[2][1],matrix->_mat[2][2],matrix->_mat[2][3], - matrix->_mat[3][0],matrix->_mat[3][1],matrix->_mat[3][2],matrix->_mat[3][3]); - pf_dcs->setMat(pf_matrix); - _pfParent = pf_dcs; - osgDCS.traverse(*this); + osgTransform.traverse(*this); _pfParent = parent; - + } + void ConvertToPerformer::apply(osg::Switch& node) { pfGroup* parent = _pfParent; @@ -214,6 +211,7 @@ void ConvertToPerformer::apply(osg::Switch& node) _pfParent = parent; } + void ConvertToPerformer::apply(osg::LOD& node) { pfGroup* parent = _pfParent; @@ -240,33 +238,6 @@ void ConvertToPerformer::apply(osg::LOD& node) _pfParent = parent; } -void ConvertToPerformer::apply(osg::Scene& scene) -{ - pfGroup* parent = _pfParent; - - pfScene* pf_scene = dynamic_cast(getPfObject(&scene)); - if (pf_scene) - { - if (_pfParent) _pfParent->addChild(pf_scene); - return; - } - - pf_scene = new pfScene; - if (!_pfRoot) _pfRoot = pf_scene; - if (_pfParent) _pfParent->addChild(pf_scene); - - regisiterOsgObjectForPfObject(&scene,pf_scene); - - if (!scene.getName().empty()) pf_scene->setName(scene.getName().c_str()); - - _pfParent = pf_scene; - - scene.traverse(*this); - - _pfParent = parent; -} - - void ConvertToPerformer::apply(osg::Billboard& node) { pfGroup* parent = _pfParent; @@ -286,15 +257,20 @@ void ConvertToPerformer::apply(osg::Billboard& node) if (!node.getName().empty()) pf_billboard->setName(node.getName().c_str()); - for(int i=0;iaddGSet(pf_geoset); + osg::GeoSet* osg_gset = dynamic_cast(node.getDrawable(i)); + if (osg_gset) + { + pfGeoSet* pf_geoset = visitGeoSet(osg_gset); + if (pf_geoset) pf_billboard->addGSet(pf_geoset); + } } _pfParent = parent; } + void ConvertToPerformer::apply(osg::Geode& node) { pfGroup* parent = _pfParent; @@ -314,24 +290,50 @@ void ConvertToPerformer::apply(osg::Geode& node) if (!node.getName().empty()) pf_geode->setName(node.getName().c_str()); - for(int i=0;iaddGSet(pf_geoset); + osg::GeoSet* osg_gset = dynamic_cast(node.getDrawable(i)); + if (osg_gset) + { + pfGeoSet* pf_geoset = visitGeoSet(osg_gset); + if (pf_geoset) pf_geode->addGSet(pf_geoset); + } } _pfParent = parent; } + pfGeoSet* ConvertToPerformer::visitGeoSet(osg::GeoSet* geoset) { if (geoset==NULL) return NULL; + osg::GeoSet::IndexPointer& cindex = geoset->getCoordIndices(); + if (cindex.valid() && !cindex._is_ushort) + { + osg::notify(osg::WARN)<<"Warning: Cannot convert osg::GeoSet to pfGeoSet due to uint coord index."<getNormalIndices(); + if (nindex.valid() && !nindex._is_ushort) + { + osg::notify(osg::WARN)<<"Warning: Cannot convert osg::GeoSet to pfGeoSet due to uint normal index."<getColorIndices(); + if (colindex.valid() && !colindex._is_ushort) + { + osg::notify(osg::WARN)<<"Warning: Cannot convert osg::GeoSet to pfGeoSet due to uint color index."<setGState(visitGeoState(geoset->getGeoState())); + pf_geoset->setGState(visitStateSet(geoset->getStateSet())); int i; @@ -354,8 +356,7 @@ pfGeoSet* ConvertToPerformer::visitGeoSet(osg::GeoSet* geoset) } osg::Vec3 *coords = geoset->getCoords(); - osg::ushort *ilist = geoset->getCIndex(); - + osg::ushort *ilist = cindex._ptr._ushort; // copy the vertex coordinates across. if( coords ) @@ -374,7 +375,7 @@ pfGeoSet* ConvertToPerformer::visitGeoSet(osg::GeoSet* geoset) if(ilist) { - int ni=geoset->getNumIndices(); + int ni=geoset->getNumCoordIndices(); ushort* pf_cindex = (ushort*) pfMalloc(sizeof(ushort) * ni, arena); for( i = 0; i < ni; i++ ) { @@ -390,7 +391,7 @@ pfGeoSet* ConvertToPerformer::visitGeoSet(osg::GeoSet* geoset) } osg::Vec3 *norms = geoset->getNormals(); - ilist = geoset->getNIndex(); + ilist = nindex._ptr._ushort; // copy normals if(norms) @@ -410,7 +411,7 @@ pfGeoSet* ConvertToPerformer::visitGeoSet(osg::GeoSet* geoset) if(ilist) { - int ni=geoset->getNumNIndices(); + int ni=geoset->getNumNormalIndices(); ushort* pf_nindex = (ushort*) pfMalloc(sizeof(ushort) * ni, arena); for( i = 0; i < ni; i++ ) { @@ -426,7 +427,7 @@ pfGeoSet* ConvertToPerformer::visitGeoSet(osg::GeoSet* geoset) } osg::Vec4 *colors = geoset->getColors(); - ilist = geoset->getColIndex(); + ilist = colindex._ptr._ushort; // copy colors if(colors) @@ -447,7 +448,7 @@ pfGeoSet* ConvertToPerformer::visitGeoSet(osg::GeoSet* geoset) if(ilist) { - int ni=geoset->getNumCIndices(); + int ni=geoset->getNumColorIndices(); ushort* pf_cindex = (ushort*) pfMalloc(sizeof(ushort) * ni, arena); for( i = 0; i < ni; i++ ) { @@ -462,141 +463,91 @@ pfGeoSet* ConvertToPerformer::visitGeoSet(osg::GeoSet* geoset) } -// -// pfVec2 *tcoords; -// geoset->getAttrLists( PFGS_TEXCOORD2, (void **)&tcoords, &ilist ); -// -// // copy texture coords -// if(tcoords) -// { -// int bind = geoset->getAttrBind( PFGS_TEXCOORD2 ); -// int nn = bind == PFGS_OFF ? 0 : -// bind == PFGS_OVERALL ? 1 : -// bind == PFGS_PER_PRIM ? geoset->getNumPrims() : -// bind == PFGS_PER_VERTEX ? nv : 0; -// -// // set the normal binding type. -// pf_geoset->setTextureBinding(_gsetBindMap[bind]); -// -// // calc the maximum num of vertex from the index list. -// int cc; -// if (ilist) -// { -// cc = 0; -// for( i = 0; i < nv; i++ ) -// if( ilist[i] > cc ) cc = ilist[i]; -// cc++; -// } -// else -// cc = nn; -// -// -// osg::Vec2* osg_tcoords = new osg::Vec2 [cc]; -// for( i = 0; i < cc; i++ ) -// { -// osg_tcoords[i][0] = tcoords[i][0]; -// osg_tcoords[i][1] = tcoords[i][1]; -// } -// -// if(ilist) -// { -// osg::ushort* osg_cindex = new osg::ushort [nn]; -// for( i = 0; i < nn; i++ ) -// { -// osg_cindex[i] = ilist[i]; -// } -// pf_geoset->setTextureCoords(osg_tcoords, osg_cindex ); -// } -// else -// { -// pf_geoset->setTextureCoords(osg_tcoords); -// } -// -// } -// -// pfVec4 *colors; -// geoset->getAttrLists( PFGS_COLOR4, (void **)&colors, &ilist ); -// -// // copy color coords -// if(colors) -// { -// int bind = geoset->getAttrBind( PFGS_COLOR4 ); -// int nn = bind == PFGS_OFF ? 0 : -// bind == PFGS_OVERALL ? 1 : -// bind == PFGS_PER_PRIM ? geoset->getNumPrims() : -// bind == PFGS_PER_VERTEX ? nv-flat_shaded_offset : 0; -// -// // set the normal binding type. -// pf_geoset->setColorBinding(_gsetBindMap[bind]); -// -// // calc the maximum num of vertex from the index list. -// int cc; -// if (ilist) -// { -// cc = 0; -// for( i = 0; i < nn; i++ ) -// if( ilist[i] > cc ) cc = ilist[i]; -// cc++; -// } -// else -// cc = nn; -// -// -// osg::Vec4* osg_colors = new osg::Vec4 [cc]; -// for( i = 0; i < cc; i++ ) -// { -// osg_colors[i][0] = colors[i][0]; -// osg_colors[i][1] = colors[i][1]; -// osg_colors[i][2] = colors[i][2]; -// osg_colors[i][3] = colors[i][3]; -// } -// -// if(ilist) -// { -// osg::ushort* osg_cindex = new osg::ushort [nn]; -// for( i = 0; i < nn; i++ ) -// { -// osg_cindex[i] = ilist[i]; -// } -// pf_geoset->setColors(osg_colors, osg_cindex ); -// } -// else -// { -// pf_geoset->setColors(osg_colors); -// } -// -// } -// + // Copy texture coords + + osg::Vec2 *tcoords = geoset->getTextureCoords(); + ilist = geoset->getTextureIndices()._ptr._ushort; + if( tcoords ) + { + int bind = _gsetBindMap[geoset->getTextureBinding()]; + int ct = geoset->getNumTextureCoords(); + pfVec2 *pf_tcoords = (pfVec2 *)pfMalloc( sizeof( pfVec2 ) * ct, arena ); + for( i = 0; i < ct; i++ ) + { + pf_tcoords[i].set( tcoords[i][0], tcoords[i][1] ); + } + if( ilist ) + { + int nt = geoset->getNumTextureIndices(); + ushort *pf_tindex = (ushort *)pfMalloc( sizeof( ushort ) * nt, arena ); + for( i = 0; i < nt; i++ ) + pf_tindex[i] = ilist[i]; + + pf_geoset->setAttr( PFGS_TEXCOORD2, bind, pf_tcoords, pf_tindex ); + } + else + pf_geoset->setAttr( PFGS_TEXCOORD2, bind, pf_tcoords, NULL ); + } return pf_geoset; } -pfGeoState* ConvertToPerformer::visitGeoState(osg::GeoState* geostate) + +pfGeoState* ConvertToPerformer::visitStateSet(osg::StateSet* stateset) { - if (geostate==NULL) return NULL; + if (stateset==NULL) return NULL; pfGeoState* pf_geostate = new pfGeoState(); - switch(geostate->getMode(osg::GeoState::LIGHTING)) + switch(stateset->getMode(GL_LIGHTING)) { - case(osg::GeoState::OVERRIDE_ON): - case(osg::GeoState::ON): pf_geostate->setMode(PFSTATE_ENLIGHTING,PF_ON);break; - case(osg::GeoState::OVERRIDE_OFF): - case(osg::GeoState::OFF): pf_geostate->setMode(PFSTATE_ENLIGHTING,PF_OFF);break; + case(osg::StateAttribute::OVERRIDE_ON): + case(osg::StateAttribute::ON): pf_geostate->setMode(PFSTATE_ENLIGHTING,PF_ON);break; + case(osg::StateAttribute::OVERRIDE_OFF): + case(osg::StateAttribute::OFF): pf_geostate->setMode(PFSTATE_ENLIGHTING,PF_OFF);break; + // pfGeostate value as default inherit. + case(osg::StateAttribute::INHERIT): break; } - switch(geostate->getMode(osg::GeoState::TEXTURE)) + switch(stateset->getMode(GL_TEXTURE_2D)) { - case(osg::GeoState::OVERRIDE_ON): - case(osg::GeoState::ON): pf_geostate->setMode(PFSTATE_ENTEXTURE,PF_ON);break; - case(osg::GeoState::OVERRIDE_OFF): - case(osg::GeoState::OFF): pf_geostate->setMode(PFSTATE_ENTEXTURE,PF_OFF);break; + case(osg::StateAttribute::OVERRIDE_ON): + case(osg::StateAttribute::ON): pf_geostate->setMode(PFSTATE_ENTEXTURE,PF_ON);break; + case(osg::StateAttribute::OVERRIDE_OFF): + case(osg::StateAttribute::OFF): pf_geostate->setMode(PFSTATE_ENTEXTURE,PF_OFF);break; + // pfGeostate value as default inherit. + case(osg::StateAttribute::INHERIT): break; + } + + const osg::Texture *tex = dynamic_cast(stateset->getAttribute( osg::StateAttribute::TEXTURE)); + + if( tex != NULL ) + { + pfTexture *pf_tex = new pfTexture; + const osg::Image *img = tex->getImage(); + int ns = img->s(); + int nt = img->t(); + int ncomp = + img->pixelFormat() == GL_LUMINANCE ? 1 : + img->pixelFormat() == GL_LUMINANCE_ALPHA ? 2 : + img->pixelFormat() == GL_RGB ? 3 : + img->pixelFormat() == GL_RGBA ? 4 : 3; + + uint *uim = (uint *)pfMalloc( ns * nt * ncomp, pfGetSharedArena() ); + + memcpy( uim, img->data(), ns * nt * ncomp ); + + pf_tex->setImage( uim, ncomp, ns, nt, 0 ); + + pf_geostate->setAttr( PFSTATE_TEXTURE, pf_tex ); + pf_geostate->setAttr( PFSTATE_TEXENV, new pfTexEnv ); } return pf_geostate; } + pfMaterial* ConvertToPerformer::visitMaterial(osg::Material* material) { if (material==NULL) return NULL; @@ -606,6 +557,7 @@ pfMaterial* ConvertToPerformer::visitMaterial(osg::Material* material) return pf_material; } + pfTexture* ConvertToPerformer::visitTexture(osg::Texture* tex) { if (tex==NULL) return NULL; @@ -614,4 +566,3 @@ pfTexture* ConvertToPerformer::visitTexture(osg::Texture* tex) return pf_texture; } - diff --git a/src/osgPlugins/pfb/ConvertToPerformer.h b/src/osgPlugins/pfb/ConvertToPerformer.h index 64c281c17..e115a0146 100644 --- a/src/osgPlugins/pfb/ConvertToPerformer.h +++ b/src/osgPlugins/pfb/ConvertToPerformer.h @@ -10,7 +10,9 @@ #include #include #include -#include +#include +#include +#include // Performer includes. #include @@ -21,7 +23,7 @@ class ConvertToPerformer : protected osg::NodeVisitor { ConvertToPerformer(); ~ConvertToPerformer(); - pfNode* convert(osg::Node* node); + pfNode* convert(const osg::Node* node); virtual void apply(osg::Node&); @@ -29,10 +31,9 @@ class ConvertToPerformer : protected osg::NodeVisitor { virtual void apply(osg::Billboard& node); virtual void apply(osg::Group& node); - virtual void apply(osg::DCS& node); + virtual void apply(osg::Transform& node); virtual void apply(osg::Switch& node); virtual void apply(osg::LOD& node); - virtual void apply(osg::Scene& node); private: @@ -44,7 +45,7 @@ class ConvertToPerformer : protected osg::NodeVisitor { virtual void regisiterOsgObjectForPfObject(osg::Object* osgObj,pfObject* pfObj); pfGeoSet* visitGeoSet(osg::GeoSet* geoset); - pfGeoState* visitGeoState(osg::GeoState* geostate); + pfGeoState* visitStateSet(osg::StateSet* geostate); pfMaterial* visitMaterial(osg::Material* material); pfTexture* visitTexture(osg::Texture* tex); @@ -52,14 +53,10 @@ class ConvertToPerformer : protected osg::NodeVisitor { typedef std::map OsgObjectToPfObjectMap; typedef std::map GSetPrimitiveMap; typedef std::map GSetBindingMap; - typedef std::map GStateTypeMap; - typedef std::map GStateModeMap; OsgObjectToPfObjectMap _osgToPfMap; GSetPrimitiveMap _gsetPrimMap; GSetBindingMap _gsetBindMap; - GStateTypeMap _gstateTypeMap; - GStateModeMap _gstateModeMap; }; diff --git a/src/osgPlugins/pfb/Makefile b/src/osgPlugins/pfb/Makefile index 5520f948c..f48575df1 100644 --- a/src/osgPlugins/pfb/Makefile +++ b/src/osgPlugins/pfb/Makefile @@ -8,10 +8,8 @@ C++FILES = \ LIB = ../../../lib/osgPlugins/osgdb_pfb.so -#LIB = ../../../lib/libpfosg.so - -#LIBS = -u __ucmpdi2 -lgcc -losg ${PFLIBS} -LIBS = -losg ${PFLIBS} +#LIBS = -u __ucmpdi2 -lgcc -losg -losgDB ${PFLIBS} +LIBS = -losg -losgDB ${PFLIBS} TARGET_LOADER_FILES = osgPlugins/osgdb_pfb.so diff --git a/src/osgPlugins/pfb/ReaderWriterPFB.cpp b/src/osgPlugins/pfb/ReaderWriterPFB.cpp index 96ea6848b..38bbf17f1 100644 --- a/src/osgPlugins/pfb/ReaderWriterPFB.cpp +++ b/src/osgPlugins/pfb/ReaderWriterPFB.cpp @@ -1,37 +1,37 @@ #include #include -#include -#include +#include #include -#include #include +#include + #include "ConvertToPerformer.h" #include "ConvertFromPerformer.h" #include #include -class ReaderWriterPFB : public osg::ReaderWriter { +class ReaderWriterPFB : public osgDB::ReaderWriter +{ + + public: - public: - ReaderWriterPFB(); ~ReaderWriterPFB(); - - void initPerformer(); - - virtual const char* className() { return "Performer Reader/Writer"; } - virtual bool acceptsExtension(const std::string& extension) { return extension=="pfb"; } - virtual osg::Image* readImage(const std::string& fileName) + void initPerformer(); + + virtual const char* className() { return "Performer Reader/Writer"; } + virtual bool acceptsExtension(const std::string& extension) { return extension=="pfb"; } + + virtual osg::Image* readImage(const std::string& fileName) { osg::notify(osg::INFO)<< "ReaderWriterPFB::readImage( "<loadFile(fileName.c_str())) { @@ -47,28 +47,27 @@ class ReaderWriterPFB : public osg::ReaderWriter { unsigned int pixelFormat = comp == 1 ? GL_LUMINANCE : - comp == 2 ? GL_LUMINANCE_ALPHA : - comp == 3 ? GL_RGB : - comp == 4 ? GL_RGBA : (GLenum)-1; + comp == 2 ? GL_LUMINANCE_ALPHA : + comp == 3 ? GL_RGB : + comp == 4 ? GL_RGBA : (GLenum)-1; unsigned int dataType = GL_UNSIGNED_BYTE; osg::Image* image = new osg::Image; image->setFileName(fileName.c_str()); image->setImage(s,t,r, - internalFormat, - pixelFormat, - dataType, - (unsigned char*)imageData); + internalFormat, + pixelFormat, + dataType, + (unsigned char*)imageData); return image; } - + return NULL; } - - virtual osg::Node* readNode(const std::string& fileName) + virtual osg::Node* readNode(const std::string& fileName) { osg::notify(osg::INFO)<< "ReaderWriterPFB::readNode( "< g_readerWriter_PFB_Proxy; +osgDB::RegisterReaderWriterProxy g_readerWriter_PFB_Proxy; diff --git a/src/osgPlugins/pic/ReaderWriterPIC.cpp b/src/osgPlugins/pic/ReaderWriterPIC.cpp index 019f0942f..2b00ea377 100644 --- a/src/osgPlugins/pic/ReaderWriterPIC.cpp +++ b/src/osgPlugins/pic/ReaderWriterPIC.cpp @@ -1,27 +1,24 @@ #include -#include -#include -#include #include -#include #include - #include +#include + /**************************************************************************** * * Follows is code extracted from the simage library. Original Authors: * - * Systems in Motion, + * Systems in Motion, * - * + * * Peder Blekken * Morten Eriksen - * Marius Bugge Monsen + * Marius Bugge Monsen * - * The original COPYING notice + * The original COPYING notice * - * All files in this library are public domain, except simage_rgb.cpp which is + * All files in this library are public domain, except simage_rgb.cpp which is * Copyright (c) Mark J Kilgard . I will contact Mark * very soon to hear if this source also can become public domain. * @@ -49,155 +46,149 @@ static int picerror = ERROR_NO_ERROR; - int simage_pic_error(char *buffer, int bufferlen) { - switch (picerror) { - case ERROR_READING_HEADER: - strncpy(buffer, "PIC loader: Error reading header", bufferlen); - break; - case ERROR_READING_PALETTE: - strncpy(buffer, "PIC loader: Error reading palette", bufferlen); - break; - case ERROR_MEMORY: - strncpy(buffer, "PIC loader: Out of memory error", bufferlen); - break; - case ERROR_READ_ERROR: - strncpy(buffer, "PIC loader: Read error", bufferlen); - break; - } - return picerror; + switch (picerror) + { + case ERROR_READING_HEADER: + strncpy(buffer, "PIC loader: Error reading header", bufferlen); + break; + case ERROR_READING_PALETTE: + strncpy(buffer, "PIC loader: Error reading palette", bufferlen); + break; + case ERROR_MEMORY: + strncpy(buffer, "PIC loader: Out of memory error", bufferlen); + break; + case ERROR_READ_ERROR: + strncpy(buffer, "PIC loader: Read error", bufferlen); + break; + } + return picerror; } + /* byte order workaround *sigh* */ -static int +static int readint16(FILE *fp, int * res) { - unsigned char tmp = 0; - unsigned int tmp2; - if (fread(&tmp, 1, 1, fp) != 1) return 0; - *res = tmp; - if (fread(&tmp, 1, 1, fp) != 1) return 0; - tmp2 = tmp; - tmp2 <<= 8; - *res |= tmp2; - return 1; + unsigned char tmp = 0; + unsigned int tmp2; + if (fread(&tmp, 1, 1, fp) != 1) return 0; + *res = tmp; + if (fread(&tmp, 1, 1, fp) != 1) return 0; + tmp2 = tmp; + tmp2 <<= 8; + *res |= tmp2; + return 1; } -int -simage_pic_identify(const char * ptr, - const unsigned char *header, - int headerlen) +int +simage_pic_identify(const char *, const unsigned char *header, int headerlen) { - static unsigned char piccmp[] = {0x19, 0x91}; - if (headerlen < 2) return 0; - if (memcmp((const void*)header, - (const void*)piccmp, 2) == 0) return 1; - return 0; + static unsigned char piccmp[] = {0x19, 0x91}; + if (headerlen < 2) return 0; + if (memcmp((const void*)header, + (const void*)piccmp, 2) == 0) return 1; + return 0; } + unsigned char * simage_pic_load(const char *filename, - int *width_ret, - int *height_ret, - int *numComponents_ret) +int *width_ret, +int *height_ret, +int *numComponents_ret) { - int w, h, width, height, i, j, format; - unsigned char palette[256][3]; - unsigned char * tmpbuf, * buffer, * ptr; + int w, h, width, height, i, j, format; + unsigned char palette[256][3]; + unsigned char * tmpbuf, * buffer, * ptr; - FILE *fp = fopen(filename, "rb"); - if (!fp) return NULL; + FILE *fp = fopen(filename, "rb"); + if (!fp) return NULL; - picerror = ERROR_NO_ERROR; - - fseek(fp, 2, SEEK_SET); - if (!readint16(fp, &w)) { - picerror = ERROR_READING_HEADER; - fclose(fp); - return NULL; - } + picerror = ERROR_NO_ERROR; - fseek(fp, 4, SEEK_SET); - if (!readint16(fp, &h)) { - picerror = ERROR_READING_HEADER; - fclose(fp); - return NULL; - } - - width = w; - height = h; - - if (width <= 0 || height <= 0) { - fclose(fp); - return NULL; - } - fseek(fp, 32, SEEK_SET); - - if (fread(&palette, 3, 256, fp) != 256) { - picerror = ERROR_READING_PALETTE; - } - - tmpbuf = (unsigned char *)malloc(width); - buffer = (unsigned char*) malloc(3*width*height); - if (tmpbuf == NULL || buffer == NULL) { - picerror = ERROR_MEMORY; - if (tmpbuf) free(tmpbuf); - if (buffer) free(buffer); - fclose(fp); - return NULL; - } - ptr = buffer; - for (i = 0; i < height; i++) { - if (fread(tmpbuf, 1, width, fp) != (size_t) width) { - picerror = ERROR_READ_ERROR; - fclose(fp); - if (tmpbuf) free(tmpbuf); - if (buffer) free(buffer); - buffer = NULL; - width = height = 0; - return NULL; + fseek(fp, 2, SEEK_SET); + if (!readint16(fp, &w)) + { + picerror = ERROR_READING_HEADER; + fclose(fp); + return NULL; } - for (j = 0; j < width; j++) { - int idx = tmpbuf[j]; - *ptr++ = palette[idx][0]; - *ptr++ = palette[idx][1]; - *ptr++ = palette[idx][2]; - } - } - format = 3; - fclose(fp); - *width_ret = width; - *height_ret = height; - *numComponents_ret = format; - return buffer; + fseek(fp, 4, SEEK_SET); + if (!readint16(fp, &h)) + { + picerror = ERROR_READING_HEADER; + fclose(fp); + return NULL; + } + + width = w; + height = h; + + if (width <= 0 || height <= 0) + { + fclose(fp); + return NULL; + } + fseek(fp, 32, SEEK_SET); + + if (fread(&palette, 3, 256, fp) != 256) + { + picerror = ERROR_READING_PALETTE; + } + + tmpbuf = (unsigned char *)malloc(width); + buffer = (unsigned char*) malloc(3*width*height); + if (tmpbuf == NULL || buffer == NULL) + { + picerror = ERROR_MEMORY; + if (tmpbuf) free(tmpbuf); + if (buffer) free(buffer); + fclose(fp); + return NULL; + } + ptr = buffer; + for (i = 0; i < height; i++) + { + if (fread(tmpbuf, 1, width, fp) != (size_t) width) + { + picerror = ERROR_READ_ERROR; + fclose(fp); + if (tmpbuf) free(tmpbuf); + if (buffer) free(buffer); + buffer = NULL; + width = height = 0; + return NULL; + } + for (j = 0; j < width; j++) + { + int idx = tmpbuf[j]; + *ptr++ = palette[idx][0]; + *ptr++ = palette[idx][1]; + *ptr++ = palette[idx][2]; + } + } + format = 3; + fclose(fp); + + *width_ret = width; + *height_ret = height; + *numComponents_ret = format; + return buffer; } -class ReaderWriterPIC : public osg::ReaderWriter + +class ReaderWriterPIC : public osgDB::ReaderWriter { public: virtual const char* className() { return "PIC Image Reader"; } virtual bool acceptsExtension(const std::string& extension) { return extension=="pic"; } - virtual osg::Node* readNode(const std::string& fileName) - { - osg::Image* image = readImage(fileName); - if (image) - { - osg::Geode* geode = osg::createGeodeForImage(image); - if (geode==NULL) image->unref(); - return geode; - } - else - { - return NULL; - } - } - virtual osg::Image* readImage(const std::string& fileName) { @@ -207,7 +198,7 @@ class ReaderWriterPIC : public osg::ReaderWriter int numComponents_ret; imageData = simage_pic_load(fileName.c_str(),&width_ret,&height_ret,&numComponents_ret); - + if (imageData==NULL) return NULL; int s = width_ret; @@ -218,19 +209,19 @@ class ReaderWriterPIC : public osg::ReaderWriter unsigned int pixelFormat = numComponents_ret == 1 ? GL_LUMINANCE : - numComponents_ret == 2 ? GL_LUMINANCE_ALPHA : - numComponents_ret == 3 ? GL_RGB : - numComponents_ret == 4 ? GL_RGBA : (GLenum)-1; + numComponents_ret == 2 ? GL_LUMINANCE_ALPHA : + numComponents_ret == 3 ? GL_RGB : + numComponents_ret == 4 ? GL_RGBA : (GLenum)-1; unsigned int dataType = GL_UNSIGNED_BYTE; osg::Image* pOsgImage = new osg::Image; pOsgImage->setFileName(fileName.c_str()); - pOsgImage->setImage(s,t,r, - internalFormat, - pixelFormat, - dataType, - imageData); + pOsgImage->setImage(s,t,r, + internalFormat, + pixelFormat, + dataType, + imageData); return pOsgImage; @@ -239,4 +230,4 @@ class ReaderWriterPIC : public osg::ReaderWriter // now register with Registry to instantiate the above // reader/writer. -osg::RegisterReaderWriterProxy g_readerWriter_PIC_Proxy; +osgDB::RegisterReaderWriterProxy g_readerWriter_PIC_Proxy; diff --git a/src/osgPlugins/png/ReaderWriterPNG.cpp b/src/osgPlugins/png/ReaderWriterPNG.cpp index 75f2aa65c..03ee1da1e 100644 --- a/src/osgPlugins/png/ReaderWriterPNG.cpp +++ b/src/osgPlugins/png/ReaderWriterPNG.cpp @@ -1,183 +1,170 @@ #include -#include "osg/Image" -#include "osg/Input" -#include "osg/Output" #include "osg/Notify" -#include "osg/Registry" #include - #include "osg/GL" +#include "osgDB/Registry" + using namespace osg; -extern "C" { -#include +extern "C" +{ + #include } -/* Transparency parameters */ -#define PNG_ALPHA -2 /* Use alpha channel in PNG file, if there is one */ -#define PNG_SOLID -1 /* No transparency */ -#define PNG_STENCIL 0 /* Sets alpha to 0 for r=g=b=0, 1 otherwise */ -typedef struct { - unsigned int Width; - unsigned int Height; - unsigned int Depth; - unsigned int Alpha; +/* Transparency parameters */ +#define PNG_ALPHA -2 /* Use alpha channel in PNG file, if there is one */ +#define PNG_SOLID -1 /* No transparency */ +#define PNG_STENCIL 0 /* Sets alpha to 0 for r=g=b=0, 1 otherwise */ + +typedef struct +{ + unsigned int Width; + unsigned int Height; + unsigned int Depth; + unsigned int Alpha; } pngInfo; -class ReaderWriterPNG : public ReaderWriter +class ReaderWriterPNG : public osgDB::ReaderWriter { public: virtual const char* className() { return "PNG Image Reader/Writer"; } virtual bool acceptsExtension(const std::string& extension) { return extension=="png"; } - virtual osg::Node* readNode(const std::string& fileName) - { - osg::Image* image = readImage(fileName); - if (image) - { - osg::Geode* geode = osg::createGeodeForImage(image); - if (geode==NULL) image->unref(); - return geode; - } - else - { - return NULL; - } - } - virtual Image* readImage(const std::string& fileName) { - int trans = PNG_ALPHA; - FILE *fp = NULL; - pngInfo pInfo; - pngInfo *pinfo = &pInfo; + int trans = PNG_ALPHA; + FILE *fp = NULL; + pngInfo pInfo; + pngInfo *pinfo = &pInfo; - unsigned char header[8]; - png_structp png; - png_infop info; - png_infop endinfo; - png_bytep data;//, data2; - png_bytep *row_p; - double fileGamma; + unsigned char header[8]; + png_structp png; + png_infop info; + png_infop endinfo; + png_bytep data; //, data2; + png_bytep *row_p; + double fileGamma; - png_uint_32 width, height; - int depth, color; + png_uint_32 width, height; + int depth, color; - png_uint_32 i; - png = png_create_read_struct(PNG_LIBPNG_VER_STRING, NULL, NULL, NULL); - info = png_create_info_struct(png); - endinfo = png_create_info_struct(png); + png_uint_32 i; + png = png_create_read_struct(PNG_LIBPNG_VER_STRING, NULL, NULL, NULL); + info = png_create_info_struct(png); + endinfo = png_create_info_struct(png); - fp = fopen(fileName.c_str(), "rb"); - if (fp && fread(header, 1, 8, fp) && png_check_sig(header, 8)) - png_init_io(png, fp); - else - { - png_destroy_read_struct(&png, &info, &endinfo); - return NULL; - } - png_set_sig_bytes(png, 8); + fp = fopen(fileName.c_str(), "rb"); + if (fp && fread(header, 1, 8, fp) && png_check_sig(header, 8)) + png_init_io(png, fp); + else + { + png_destroy_read_struct(&png, &info, &endinfo); + return NULL; + } + png_set_sig_bytes(png, 8); - png_read_info(png, info); - png_get_IHDR(png, info, &width, &height, &depth, &color, NULL, NULL, NULL); + png_read_info(png, info); + png_get_IHDR(png, info, &width, &height, &depth, &color, NULL, NULL, NULL); - if (pinfo != NULL) { - pinfo->Width = width; - pinfo->Height = height; - pinfo->Depth = depth; - } + if (pinfo != NULL) + { + pinfo->Width = width; + pinfo->Height = height; + pinfo->Depth = depth; + } - if (color == PNG_COLOR_TYPE_GRAY || color == PNG_COLOR_TYPE_GRAY_ALPHA) - png_set_gray_to_rgb(png); + if (color == PNG_COLOR_TYPE_GRAY || color == PNG_COLOR_TYPE_GRAY_ALPHA) + png_set_gray_to_rgb(png); - if (color&PNG_COLOR_MASK_ALPHA && trans != PNG_ALPHA) - { - png_set_strip_alpha(png); - color &= ~PNG_COLOR_MASK_ALPHA; - } + if (color&PNG_COLOR_MASK_ALPHA && trans != PNG_ALPHA) + { + png_set_strip_alpha(png); + color &= ~PNG_COLOR_MASK_ALPHA; + } - // if (!(PalettedTextures && mipmap >= 0 && trans == PNG_SOLID)) - if (color == PNG_COLOR_TYPE_PALETTE) - png_set_expand(png); + // if (!(PalettedTextures && mipmap >= 0 && trans == PNG_SOLID)) + if (color == PNG_COLOR_TYPE_PALETTE) + png_set_expand(png); - /*--GAMMA--*/ - // checkForGammaEnv(); - double screenGamma = 2.2 / 1.0; - if (png_get_gAMA(png, info, &fileGamma)) - png_set_gamma(png, screenGamma, fileGamma); - else - png_set_gamma(png, screenGamma, 1.0/2.2); + /*--GAMMA--*/ + // checkForGammaEnv(); + double screenGamma = 2.2 / 1.0; + if (png_get_gAMA(png, info, &fileGamma)) + png_set_gamma(png, screenGamma, fileGamma); + else + png_set_gamma(png, screenGamma, 1.0/2.2); - png_read_update_info(png, info); + png_read_update_info(png, info); - data = (png_bytep) malloc(png_get_rowbytes(png, info)*height); - row_p = (png_bytep *) malloc(sizeof(png_bytep)*height); + data = (png_bytep) malloc(png_get_rowbytes(png, info)*height); + row_p = (png_bytep *) malloc(sizeof(png_bytep)*height); - bool StandardOrientation = false; - for (i = 0; i < height; i++) { - if (StandardOrientation) - row_p[height - 1 - i] = &data[png_get_rowbytes(png, info)*i]; - else - row_p[i] = &data[png_get_rowbytes(png, info)*i]; - } + bool StandardOrientation = false; + for (i = 0; i < height; i++) + { + if (StandardOrientation) + row_p[height - 1 - i] = &data[png_get_rowbytes(png, info)*i]; + else + row_p[i] = &data[png_get_rowbytes(png, info)*i]; + } - png_read_image(png, row_p); - free(row_p); + png_read_image(png, row_p); + free(row_p); - int iBitCount; + int iBitCount; - if (trans == PNG_SOLID || trans == PNG_ALPHA || color == PNG_COLOR_TYPE_RGB_ALPHA || color == PNG_COLOR_TYPE_GRAY_ALPHA) - { - switch (color) - { - case PNG_COLOR_TYPE_GRAY: - case PNG_COLOR_TYPE_RGB: - case PNG_COLOR_TYPE_PALETTE: - iBitCount = 24; - if (pinfo != NULL) pinfo->Alpha = 0; - break; + if (trans == PNG_SOLID || trans == PNG_ALPHA || color == PNG_COLOR_TYPE_RGB_ALPHA || color == PNG_COLOR_TYPE_GRAY_ALPHA) + { + switch (color) + { + case PNG_COLOR_TYPE_GRAY: + case PNG_COLOR_TYPE_RGB: + case PNG_COLOR_TYPE_PALETTE: + iBitCount = 24; + if (pinfo != NULL) pinfo->Alpha = 0; + break; - case PNG_COLOR_TYPE_GRAY_ALPHA: - case PNG_COLOR_TYPE_RGB_ALPHA: - iBitCount = 32; - if (pinfo != NULL) pinfo->Alpha = 8; - break; + case PNG_COLOR_TYPE_GRAY_ALPHA: + case PNG_COLOR_TYPE_RGB_ALPHA: + iBitCount = 32; + if (pinfo != NULL) pinfo->Alpha = 8; + break; - default: - return NULL; - } - } + default: + return NULL; + } + } - png_read_end(png, endinfo); - png_destroy_read_struct(&png, &info, &endinfo); + png_read_end(png, endinfo); + png_destroy_read_struct(&png, &info, &endinfo); - // free(data); + // free(data); - if (fp) - fclose(fp); + if (fp) + fclose(fp); - osg::Image* pOsgImage = new osg::Image(); + osg::Image* pOsgImage = new osg::Image(); - pOsgImage->setFileName(fileName.c_str()); - if (iBitCount == 24) - pOsgImage->setImage(width, height, 1, - iBitCount / 8, // int internalFormat, - GL_RGB, // unsigned int pixelFormat - GL_UNSIGNED_BYTE, // unsigned int dataType - data); - else - pOsgImage->setImage(width, height, 1, - iBitCount / 8, // int internalFormat, - GL_RGBA, // unsigned int pixelFormat - GL_UNSIGNED_BYTE, // unsigned int dataType - data); - return pOsgImage; + pOsgImage->setFileName(fileName.c_str()); + if (iBitCount == 24) + pOsgImage->setImage(width, height, 1, + iBitCount / 8,// int internalFormat, + GL_RGB, // unsigned int pixelFormat + GL_UNSIGNED_BYTE,// unsigned int dataType + data); + else + pOsgImage->setImage(width, height, 1, + iBitCount / 8,// int internalFormat, + GL_RGBA, // unsigned int pixelFormat + GL_UNSIGNED_BYTE,// unsigned int dataType + data); + return pOsgImage; } }; // now register with Registry to instantiate the above // reader/writer. -RegisterReaderWriterProxy g_readerWriter_PNG_Proxy; +osgDB::RegisterReaderWriterProxy g_readerWriter_PNG_Proxy; diff --git a/src/osgPlugins/rgb/Makedepend b/src/osgPlugins/rgb/Makedepend new file mode 100644 index 000000000..e69de29bb diff --git a/src/osgPlugins/rgb/Makefile b/src/osgPlugins/rgb/Makefile new file mode 100644 index 000000000..5f6cd06d6 --- /dev/null +++ b/src/osgPlugins/rgb/Makefile @@ -0,0 +1,18 @@ +#!smake +include ../../../Make/makedefs + +C++FILES = \ + ReaderWriterRGB.cpp\ + +LIB = ../../../lib/osgPlugins/osgdb_rgb.so + +TARGET_LOADER_FILES = osgPlugins/osgdb_rgb.so + +LIBS = +C++FLAGS += -I. -I../../../include +LDFLAGS += -L../../../lib + +include ../../../Make/makerules + + + diff --git a/src/osgPlugins/rgb/ReaderWriterRGB.cpp b/src/osgPlugins/rgb/ReaderWriterRGB.cpp new file mode 100644 index 000000000..0e1119f10 --- /dev/null +++ b/src/osgPlugins/rgb/ReaderWriterRGB.cpp @@ -0,0 +1,359 @@ +#include "osg/Image" +#include "osg/Notify" + +#include +#include +#include + +#include "osg/GL" + +#include "osgDB/FileNameUtils" +#include "osgDB/Registry" + +#include +#include +#include + +#ifndef SEEK_SET +# define SEEK_SET 0 +#endif + +using namespace osg; + +typedef struct _rawImageRec +{ + unsigned short imagic; + unsigned short type; + unsigned short dim; + unsigned short sizeX, sizeY, sizeZ; + unsigned long min, max; + unsigned long wasteBytes; + char name[80]; + unsigned long colorMap; + FILE *file; + unsigned char *tmp, *tmpR, *tmpG, *tmpB, *tmpA; + unsigned long rleEnd; + GLuint *rowStart; + GLint *rowSize; +} rawImageRec; + +static void ConvertShort(unsigned short *array, long length) +{ + unsigned long b1, b2; + unsigned char *ptr; + + ptr = (unsigned char *)array; + while (length--) + { + b1 = *ptr++; + b2 = *ptr++; + *array++ = (unsigned short) ((b1 << 8) | (b2)); + } +} + + +static void ConvertLong(GLuint *array, long length) +{ + unsigned long b1, b2, b3, b4; + unsigned char *ptr; + + ptr = (unsigned char *)array; + while (length--) + { + b1 = *ptr++; + b2 = *ptr++; + b3 = *ptr++; + b4 = *ptr++; + *array++ = (b1 << 24) | (b2 << 16) | (b3 << 8) | (b4); + } +} + + +static rawImageRec *RawImageOpen(const char *fileName) +{ + union + { + int testWord; + char testByte[4]; + } endianTest; + rawImageRec *raw; + GLenum swapFlag; + int x; + + endianTest.testWord = 1; + if (endianTest.testByte[0] == 1) + { + swapFlag = GL_TRUE; + } + else + { + swapFlag = GL_FALSE; + } + + raw = (rawImageRec *)malloc(sizeof(rawImageRec)); + if (raw == NULL) + { + notify(WARN)<< "Out of memory!"<file = fopen(fileName, "rb")) == NULL) + { + perror(fileName); + return NULL; + } + + fread(raw, 1, 12, raw->file); + + if (swapFlag) + { + ConvertShort(&raw->imagic, 6); + } + + raw->tmp = raw->tmpR = raw->tmpG = raw->tmpB = raw->tmpA = 0L; + + raw->tmp = (unsigned char *)malloc(raw->sizeX*256); + if (raw->tmp == NULL ) + { + notify(FATAL)<< "Out of memory!"<sizeZ >= 1 ) + { + if( (raw->tmpR = (unsigned char *)malloc(raw->sizeX)) == NULL ) + { + notify(FATAL)<< "Out of memory!"<tmp ); + return NULL; + } + } + if( raw->sizeZ >= 2 ) + { + if( (raw->tmpG = (unsigned char *)malloc(raw->sizeX)) == NULL ) + { + notify(FATAL)<< "Out of memory!"<tmp ); + free( raw->tmpR ); + return NULL; + } + } + if( raw->sizeZ >= 3 ) + { + if( (raw->tmpB = (unsigned char *)malloc(raw->sizeX)) == NULL ) + { + notify(FATAL)<< "Out of memory!"<tmp ); + free( raw->tmpR ); + free( raw->tmpG ); + return NULL; + } + } + if (raw->sizeZ >= 4) + { + if( (raw->tmpA = (unsigned char *)malloc(raw->sizeX)) == NULL ) + { + notify(FATAL)<< "Out of memory!"<tmp ); + free( raw->tmpR ); + free( raw->tmpG ); + free( raw->tmpB ); + return NULL; + } + } + + if ((raw->type & 0xFF00) == 0x0100) + { + x = raw->sizeY * raw->sizeZ * sizeof(GLuint); + raw->rowStart = (GLuint *)malloc(x); + raw->rowSize = (GLint *)malloc(x); + if (raw->rowStart == NULL || raw->rowSize == NULL) + { + notify(FATAL)<< "Out of memory!"<rleEnd = 512 + (2 * x); + fseek(raw->file, 512, SEEK_SET); + fread(raw->rowStart, 1, x, raw->file); + fread(raw->rowSize, 1, x, raw->file); + if (swapFlag) + { + ConvertLong(raw->rowStart, (long) (x/sizeof(GLuint))); + ConvertLong((GLuint *)raw->rowSize, (long) (x/sizeof(GLint))); + } + } + return raw; +} + + +static void RawImageClose(rawImageRec *raw) +{ + fclose(raw->file); + free(raw->tmp); + if( raw->tmpR ) + free(raw->tmpR); + if( raw->tmpG ) + free(raw->tmpG); + if( raw->tmpB ) + free(raw->tmpB); + if( raw->tmpA ) + free(raw->tmpA); + + free(raw); +} + + +static void RawImageGetRow(rawImageRec *raw, unsigned char *buf, int y, int z) +{ + unsigned char *iPtr, *oPtr, pixel; + int count, done = 0; + + if ((raw->type & 0xFF00) == 0x0100) + { + fseek(raw->file, (long) raw->rowStart[y+z*raw->sizeY], SEEK_SET); + fread(raw->tmp, 1, (unsigned int)raw->rowSize[y+z*raw->sizeY], + raw->file); + + iPtr = raw->tmp; + oPtr = buf; + while (!done) + { + pixel = *iPtr++; + count = (int)(pixel & 0x7F); + if (!count) + { + done = 1; + return; + } + if (pixel & 0x80) + { + while (count--) + { + *oPtr++ = *iPtr++; + } + } + else + { + pixel = *iPtr++; + while (count--) + { + *oPtr++ = pixel; + } + } + } + } + else + { + fseek(raw->file, 512+(y*raw->sizeX)+(z*raw->sizeX*raw->sizeY), + SEEK_SET); + fread(buf, 1, raw->sizeX, raw->file); + } +} + + +static void RawImageGetData(rawImageRec *raw, unsigned char **data ) +{ + unsigned char *ptr; + int i, j; + + // // round the width to a factor 4 + // int width = (int)(floorf((float)raw->sizeX/4.0f)*4.0f); + // if (width!=raw->sizeX) width += 4; + + *data = (unsigned char *)malloc(2 * (raw->sizeX+1)*(raw->sizeY+1)*4); + // *data = (unsigned char *)malloc(2 * (width+1)*(raw->sizeY+1)*4); + + ptr = *data; + for (i = 0; i < (int)(raw->sizeY); i++) + { + if( raw->sizeZ >= 1 ) + RawImageGetRow(raw, raw->tmpR, i, 0); + if( raw->sizeZ >= 2 ) + RawImageGetRow(raw, raw->tmpG, i, 1); + if( raw->sizeZ >= 3 ) + RawImageGetRow(raw, raw->tmpB, i, 2); + if( raw->sizeZ >= 4 ) + RawImageGetRow(raw, raw->tmpA, i, 3); + for (j = 0; j < (int)(raw->sizeX); j++) + { + if( raw->sizeZ >= 1 ) + *ptr++ = *(raw->tmpR + j); + if( raw->sizeZ >= 2 ) + *ptr++ = *(raw->tmpG + j); + if( raw->sizeZ >= 3 ) + *ptr++ = *(raw->tmpB + j); + if( raw->sizeZ >= 4 ) + *ptr++ = *(raw->tmpA + j); + } + // // pad the image width with blanks to bring it up to the rounded width. + // for(;jsizeX; + int t = raw->sizeY; + int r = 1; + + #if 0 + int internalFormat = raw->sizeZ == 3 ? GL_RGB5 : + raw->sizeZ == 4 ? GL_RGB5_A1 : GL_RGB; + #else + int internalFormat = raw->sizeZ; + #endif + unsigned int pixelFormat = + raw->sizeZ == 1 ? GL_LUMINANCE : + raw->sizeZ == 2 ? GL_LUMINANCE_ALPHA : + raw->sizeZ == 3 ? GL_RGB : + raw->sizeZ == 4 ? GL_RGBA : (GLenum)-1; + + unsigned int dataType = GL_UNSIGNED_BYTE; + + unsigned char *data; + RawImageGetData(raw, &data); + RawImageClose(raw); + + Image* image = new Image(); + image->setFileName(fileName.c_str()); + image->setImage(s,t,r, + internalFormat, + pixelFormat, + dataType, + data); + + notify(INFO) << "image read ok "< g_readerWriter_RGB_Proxy; diff --git a/src/osgPlugins/tga/ReaderWriterTGA.cpp b/src/osgPlugins/tga/ReaderWriterTGA.cpp index 92702cc35..e34056430 100644 --- a/src/osgPlugins/tga/ReaderWriterTGA.cpp +++ b/src/osgPlugins/tga/ReaderWriterTGA.cpp @@ -1,13 +1,10 @@ #include -#include -#include -#include #include -#include #include - #include +#include + #include #include #include @@ -17,16 +14,16 @@ * * Follows is code extracted from the simage library. Original Authors: * - * Systems in Motion, + * Systems in Motion, * - * + * * Peder Blekken * Morten Eriksen - * Marius Bugge Monsen + * Marius Bugge Monsen * - * The original COPYING notice + * The original COPYING notice * - * All files in this library are public domain, except simage_rgb.cpp which is + * All files in this library are public domain, except simage_rgb.cpp which is * Copyright (c) Mark J Kilgard . I will contact Mark * very soon to hear if this source also can become public domain. * @@ -51,7 +48,6 @@ /* 10 RLE RGB */ /* */ - #define ERR_NO_ERROR 0 #define ERR_OPEN 1 #define ERR_READ 2 @@ -62,386 +58,417 @@ static int tgaerror = ERR_NO_ERROR; int simage_tga_error(char * buffer, int buflen) { - switch (tgaerror) { - case ERR_OPEN: - strncpy(buffer, "TGA loader: Error opening file", buflen); - break; - case ERR_READ: - strncpy(buffer, "TGA loader: Error reading file", buflen); - break; - case ERR_MEM: - strncpy(buffer, "TGA loader: Out of memory error", buflen); - break; - } - return tgaerror; + switch (tgaerror) + { + case ERR_OPEN: + strncpy(buffer, "TGA loader: Error opening file", buflen); + break; + case ERR_READ: + strncpy(buffer, "TGA loader: Error reading file", buflen); + break; + case ERR_MEM: + strncpy(buffer, "TGA loader: Out of memory error", buflen); + break; + } + return tgaerror; } + /* TODO: */ /* - bottom-up images */ /* - huffman, delta encoding */ -static void +static void convert_16_to_24(const unsigned char * const src, unsigned char * const dest) { - /* RGB for opengl, lo-hi 16 bit for TGA */ - unsigned int t0 = src[0]; - unsigned int t1 = src[1]; - dest[0] = (unsigned char) (t0 & 0x1f) << 2; /* r */ - dest[1] = (unsigned char) (t1 & 0x7c) >> 2; /* g */ - dest[2] = (unsigned char) ((t1 & 0x3)<<3) | ((t0&0xe)>>5); /*b */ + /* RGB for opengl, lo-hi 16 bit for TGA */ + unsigned int t0 = src[0]; + unsigned int t1 = src[1]; + /* r */ + dest[0] = (unsigned char) (t0 & 0x1f) << 2; + /* g */ + dest[1] = (unsigned char) (t1 & 0x7c) >> 2; + /*b */ + dest[2] = (unsigned char) ((t1 & 0x3)<<3) | ((t0&0xe)>>5); } -static void + +static void convert_16_to_32(const unsigned char * const src, unsigned char * const dest) { - /* RGBA for opengl, lo-hi 16 bit for TGA */ - unsigned int t0 = src[0]; - unsigned int t1 = src[1]; - dest[0] = (unsigned char) (t0 & 0x1f) << 2; /* r */ - dest[1] = (unsigned char) (t1 & 0x7c) >> 2; /* g */ - dest[2] = (unsigned char) ((t1 & 0x3)<<3) | ((t0&0xe)>>5); /*b */ - dest[3] = (t1&0x70)?255:0; /* a */ + /* RGBA for opengl, lo-hi 16 bit for TGA */ + unsigned int t0 = src[0]; + unsigned int t1 = src[1]; + /* r */ + dest[0] = (unsigned char) (t0 & 0x1f) << 2; + /* g */ + dest[1] = (unsigned char) (t1 & 0x7c) >> 2; + /*b */ + dest[2] = (unsigned char) ((t1 & 0x3)<<3) | ((t0&0xe)>>5); + dest[3] = (t1&0x70)?255:0; /* a */ } -static void + +static void convert_24_to_24(const unsigned char * const src, unsigned char * const dest) { - /* RGB for opengl */ - /* BGR for TGA */ - dest[0] = src[2]; - dest[1] = src[1]; - dest[2] = src[0]; + /* RGB for opengl */ + /* BGR for TGA */ + dest[0] = src[2]; + dest[1] = src[1]; + dest[2] = src[0]; } -static void + +static void convert_32_to_32(const unsigned char * const src, unsigned char * const dest) { - /* opengl image format is RGBA, not ARGB */ - /* TGA image format is BGRA for 32 bit */ - dest[0] = src[2]; - dest[1] = src[1]; - dest[2] = src[0]; - dest[3] = src[3]; + /* opengl image format is RGBA, not ARGB */ + /* TGA image format is BGRA for 32 bit */ + dest[0] = src[2]; + dest[1] = src[1]; + dest[2] = src[0]; + dest[3] = src[3]; } -static void -convert_data(const unsigned char * const src, unsigned char * const dest, - const int x, const int srcformat, - const int destformat) + +static void +convert_data(const unsigned char * const src, unsigned char * const dest, +const int x, const int srcformat, +const int destformat) { - if (srcformat == 2) { - if (destformat == 3) - convert_16_to_24(src+x*srcformat, - dest+x*destformat); - else { - assert(destformat == 4); - convert_16_to_32(src+x*srcformat, - dest+x*destformat); + if (srcformat == 2) + { + if (destformat == 3) + convert_16_to_24(src+x*srcformat, + dest+x*destformat); + else + { + assert(destformat == 4); + convert_16_to_32(src+x*srcformat, + dest+x*destformat); + } + } + else if (srcformat == 3) + { + assert(destformat == 3); + convert_24_to_24(src+x*srcformat, + dest+x*destformat); + } + else + { + assert(srcformat == 4 && destformat == 4); + convert_32_to_32(src+x*srcformat, + dest+x*destformat); } - } - else if (srcformat == 3) { - assert(destformat == 3); - convert_24_to_24(src+x*srcformat, - dest+x*destformat); - } - else { - assert(srcformat == 4 && destformat == 4); - convert_32_to_32(src+x*srcformat, - dest+x*destformat); - } } + /* Intel byte order workaround */ static int getInt16(unsigned char *ptr) { - int res = ptr[0]; - int tmp = ptr[1]; - return res | (tmp<<8); + int res = ptr[0]; + int tmp = ptr[1]; + return res | (tmp<<8); } + /* */ /* decode a new rle packet */ /* */ -static void +static void rle_new_packet(unsigned char ** src, - int * rleRemaining, - int * rleIsCompressed, - unsigned char *rleCurrent, - const int rleEntrySize) +int * rleRemaining, +int * rleIsCompressed, +unsigned char *rleCurrent, +const int rleEntrySize) { - int i; - unsigned char code = *(*src)++; - *rleRemaining = (code & 127) + 1; /* number of bytes left in this packet */ - if (code & 128) { /* rle */ - *rleIsCompressed = 1; - for (i = 0; i < rleEntrySize; i++) - rleCurrent[i] = *(*src)++; - } - else { /* uncompressed */ - *rleIsCompressed = 0; - } + int i; + unsigned char code = *(*src)++; + /* number of bytes left in this packet */ + *rleRemaining = (code & 127) + 1; + if (code & 128) /* rle */ + { + *rleIsCompressed = 1; + for (i = 0; i < rleEntrySize; i++) + rleCurrent[i] = *(*src)++; + } + else /* uncompressed */ + { + *rleIsCompressed = 0; + } } + /* */ /* decode the # of specified bytes */ /* */ -static void -rle_decode(unsigned char ** src, - unsigned char *dest, - const int numbytes, - int * rleRemaining, - int * rleIsCompressed, - unsigned char *rleCurrent, - const int rleEntrySize) +static void +rle_decode(unsigned char ** src, +unsigned char *dest, +const int numbytes, +int * rleRemaining, +int * rleIsCompressed, +unsigned char *rleCurrent, +const int rleEntrySize) { - int i; - int size = rleEntrySize; - unsigned char *stop = dest + numbytes; - while (dest < stop) { - if (*rleRemaining == 0) /* start new packet */ - rle_new_packet(src, rleRemaining, rleIsCompressed, - rleCurrent, rleEntrySize); - - if (*rleIsCompressed) { - for (i = 0; i < size; i++) { - *dest++ = rleCurrent[i]; - } + int i; + int size = rleEntrySize; + unsigned char *stop = dest + numbytes; + while (dest < stop) + { + if (*rleRemaining == 0) /* start new packet */ + rle_new_packet(src, rleRemaining, rleIsCompressed, + rleCurrent, rleEntrySize); + + if (*rleIsCompressed) + { + for (i = 0; i < size; i++) + { + *dest++ = rleCurrent[i]; + } + } + else + { + for (i = 0; i < size; i++) + { + *dest++ = *(*src)++; + } + } + // original code : *rleRemaining)--; + (*rleRemaining)--; } - else { - for (i = 0; i < size; i++) { - *dest++ = *(*src)++; - } - } - *rleRemaining--; - } } + unsigned char * simage_tga_load(const char *filename, - int *width_ret, - int *height_ret, - int *numComponents_ret) +int *width_ret, +int *height_ret, +int *numComponents_ret) { - FILE * fp; - unsigned char header[18]; - int type; - int width; - int height; - int depth; - int flags; - int format; - unsigned char *colormap; - int indexsize; - int rleIsCompressed; - int rleRemaining; - int rleEntrySize; - unsigned char rleCurrent[4]; - unsigned char *buffer; - unsigned char *dest; - int bpr; - unsigned char *linebuf; + FILE * fp; + unsigned char header[18]; + int type; + int width; + int height; + int depth; + int flags; + int format; + unsigned char *colormap; + int indexsize; + int rleIsCompressed; + int rleRemaining; + int rleEntrySize; + unsigned char rleCurrent[4]; + unsigned char *buffer; + unsigned char *dest; + int bpr; + unsigned char *linebuf; - tgaerror = ERR_NO_ERROR; /* clear error */ + tgaerror = ERR_NO_ERROR; /* clear error */ - fp = fopen(filename, "rb"); - if (!fp) { - tgaerror = ERR_OPEN; - return NULL; - } - - if (fread(header, 1, 18, fp) != 18) { - tgaerror = ERR_READ; + fp = fopen(filename, "rb"); + if (!fp) + { + tgaerror = ERR_OPEN; + return NULL; + } + + if (fread(header, 1, 18, fp) != 18) + { + tgaerror = ERR_READ; + fclose(fp); + return NULL; + } + + type = header[2]; + width = getInt16(&header[12]); + height = getInt16(&header[14]); + depth = header[16] >> 3; + flags = header[17]; + + /* check for reasonable values in case this is not a tga file */ + if ((type != 2 && type != 10) || + (width < 0 || width > 4096) || + (height < 0 || height > 4096) || + (depth < 2 || depth > 4)) + { + tgaerror = ERR_UNSUPPORTED; + fclose(fp); + return NULL; + } + + if (header[0]) /* skip identification field */ + fseek(fp, header[0], SEEK_CUR); + + colormap = NULL; + if (header[1] == 1) /* there is a colormap */ + { + int len = getInt16(&header[5]); + indexsize = header[7]>>3; + colormap = (unsigned char *)malloc(len*indexsize); + fread(colormap, 1, len*indexsize, fp); + } + + if (depth == 2) /* 16 bits */ + { + if (flags & 1) format = 4; + else format = 3; + } + else format = depth; + + /* SoDebugError::postInfo("simage_tga_load", "TARGA file: %d %d %d %d %d\n", */ + /* type, width, height, depth, format); */ + + rleIsCompressed = 0; + rleRemaining = 0; + rleEntrySize = depth; + buffer = (unsigned char*)malloc(width*height*format); + dest = buffer; + bpr = format * width; + linebuf = (unsigned char *)malloc(width*depth); + + switch(type) + { + case 1: /* colormap, uncompressed */ + { + /* FIXME: write code */ + /* should never get here because simage_tga_identify returns 0 */ + /* for this filetype */ + /* I need example files in this format to write the code... */ + tgaerror = ERR_UNSUPPORTED; + } + break; + case 2: /* RGB, uncompressed */ + { + int x, y; + for (y = 0; y < height; y++) + { + if (fread(linebuf, 1, width*depth, fp) != (unsigned int)width*depth) + { + tgaerror = ERR_READ; + break; + } + for (x = 0; x < width; x++) + { + convert_data(linebuf, dest, x, depth, format); + } + dest += bpr; + } + } + break; + case 9: /* colormap, compressed */ + { + /* FIXME: write code */ + /* should never get here because simage_tga_identify returns 0 */ + /* for this filetype */ + /* I need example files in this format to write the code... */ + tgaerror = ERR_UNSUPPORTED; + } + break; + case 10: /* RGB, compressed */ + { + int size, x, y; + unsigned char *buf; + unsigned char *src; + int pos = ftell(fp); + fseek(fp, 0, SEEK_END); + size = ftell(fp) - pos; + fseek(fp, pos, SEEK_SET); + buf = (unsigned char *)malloc(size); + if (buf == NULL) + { + tgaerror = ERR_MEM; + break; + } + src = buf; + if (fread(buf, 1, size, fp) != (unsigned int) size) + { + tgaerror = ERR_READ; + break; + } + for (y = 0; y < height; y++) + { + rle_decode(&src, linebuf, width*depth, &rleRemaining, + &rleIsCompressed, rleCurrent, rleEntrySize); + assert(src <= buf + size); + for (x = 0; x < width; x++) + { + convert_data(linebuf, dest, x, depth, format); + } + dest += bpr; + } + if (buf) free(buf); + } + break; + default: + tgaerror = ERR_UNSUPPORTED; + } + + if (linebuf) free(linebuf); fclose(fp); - return NULL; - } - type = header[2]; - width = getInt16(&header[12]); - height = getInt16(&header[14]); - depth = header[16] >> 3; - flags = header[17]; - - /* check for reasonable values in case this is not a tga file */ - if ((type != 2 && type != 10) || - (width < 0 || width > 4096) || - (height < 0 || height > 4096) || - (depth < 2 || depth > 4)) { - tgaerror = ERR_UNSUPPORTED; - fclose(fp); - return NULL; - } - - if (header[0]) /* skip identification field */ - fseek(fp, header[0], SEEK_CUR); - - colormap = NULL; - if (header[1] == 1) { /* there is a colormap */ - int len = getInt16(&header[5]); - indexsize = header[7]>>3; - colormap = (unsigned char *)malloc(len*indexsize); - fread(colormap, 1, len*indexsize, fp); - } - - if (depth == 2) { /* 16 bits */ - if (flags & 1) format = 4; - else format = 3; - } - else format = depth; - - /* SoDebugError::postInfo("simage_tga_load", "TARGA file: %d %d %d %d %d\n", */ - /* type, width, height, depth, format); */ - - - rleIsCompressed = 0; - rleRemaining = 0; - rleEntrySize = depth; - buffer = (unsigned char*)malloc(width*height*format); - dest = buffer; - bpr = format * width; - linebuf = (unsigned char *)malloc(width*depth); - - switch(type) { - case 1: /* colormap, uncompressed */ + if (tgaerror) { - /* FIXME: write code */ - /* should never get here because simage_tga_identify returns 0 */ - /* for this filetype */ - /* I need example files in this format to write the code... */ - tgaerror = ERR_UNSUPPORTED; + if (buffer) free(buffer); + return NULL; } - break; - case 2: /* RGB, uncompressed */ - { - int x, y; - for (y = 0; y < height; y++) { - if (fread(linebuf, 1, width*depth, fp) != (unsigned int)width*depth) { - tgaerror = ERR_READ; - break; - } - for (x = 0; x < width; x++) { - convert_data(linebuf, dest, x, depth, format); - } - dest += bpr; - } - } - break; - case 9: /* colormap, compressed */ - { - /* FIXME: write code */ - /* should never get here because simage_tga_identify returns 0 */ - /* for this filetype */ - /* I need example files in this format to write the code... */ - tgaerror = ERR_UNSUPPORTED; - } - break; - case 10: /* RGB, compressed */ - { - int size, x, y; - unsigned char *buf; - unsigned char *src; - int pos = ftell(fp); - fseek(fp, 0, SEEK_END); - size = ftell(fp) - pos; - fseek(fp, pos, SEEK_SET); - buf = (unsigned char *)malloc(size); - if (buf == NULL) { - tgaerror = ERR_MEM; - break; - } - src = buf; - if (fread(buf, 1, size, fp) != (unsigned int) size) { - tgaerror = ERR_READ; - break; - } - for (y = 0; y < height; y++) { - rle_decode(&src, linebuf, width*depth, &rleRemaining, - &rleIsCompressed, rleCurrent, rleEntrySize); - assert(src <= buf + size); - for (x = 0; x < width; x++) { - convert_data(linebuf, dest, x, depth, format); - } - dest += bpr; - } - if (buf) free(buf); - } - break; - default: - tgaerror = ERR_UNSUPPORTED; - } - - if (linebuf) free(linebuf); - fclose(fp); - if (tgaerror) { - if (buffer) free(buffer); - return NULL; - } - - *width_ret = width; - *height_ret = height; - *numComponents_ret = format; - return buffer; + *width_ret = width; + *height_ret = height; + *numComponents_ret = format; + return buffer; } -int +int simage_tga_identify(const char *filename, - const unsigned char *buf, - int headerlen) +const unsigned char *buf, +int headerlen) { - char * ptr; - if (headerlen < 18) return 0; - ptr = strrchr(filename, '.'); - if (!ptr) return 0; /* TGA files must end with .tga|.TGA */ - - if (strcmp(ptr, ".tga") && strcmp(ptr, ".TGA")) return 0; - - if (buf[1] == 1 && buf[2] == 1 && buf[17] < 64) { - /* SoDebugError::postInfo("simage_tga_identify", */ - /* "TARGA colormap file: %s\n", filename); */ - return 0; - } - if ((buf[1] == 0 || buf[1] == 1) && buf[2] == 2 && buf[17] < 64) return 1; - if (buf[1] == 1 && buf[2] == 9 && buf[17] < 64) { - /* SoDebugError::postInfo("simage_tga_identity", */ - /* "TARGA RLE and colormap file: %s\n", filename); */ + char * ptr; + if (headerlen < 18) return 0; + ptr = strrchr(filename, '.'); + if (!ptr) return 0; /* TGA files must end with .tga|.TGA */ - /* will soon be supported */ + if (strcmp(ptr, ".tga") && strcmp(ptr, ".TGA")) return 0; + + if (buf[1] == 1 && buf[2] == 1 && buf[17] < 64) + { + /* SoDebugError::postInfo("simage_tga_identify", */ + /* "TARGA colormap file: %s\n", filename); */ + return 0; + } + if ((buf[1] == 0 || buf[1] == 1) && buf[2] == 2 && buf[17] < 64) return 1; + if (buf[1] == 1 && buf[2] == 9 && buf[17] < 64) + { + /* SoDebugError::postInfo("simage_tga_identity", */ + /* "TARGA RLE and colormap file: %s\n", filename); */ + + /* will soon be supported */ + return 0; + } + if ((buf[1] == 0 || buf[1] == 1) && buf[2] == 10 && buf[17] < 64) + { + /* RLE and RGB */ + return 1; + } + else /* unsupported */ + { + /* SoDebugError::postInfo("simage_tga_identify", */ + /* "Unsupported TARGA type.\n"); */ + } + /* not a TGA, or not supported type */ return 0; - } - if ((buf[1] == 0 || buf[1] == 1) && buf[2] == 10 && buf[17] < 64) { - /* RLE and RGB */ - return 1; - } - else { /* unsupported */ - /* SoDebugError::postInfo("simage_tga_identify", */ - /* "Unsupported TARGA type.\n"); */ - } - /* not a TGA, or not supported type */ - return 0; } -class ReaderWriterTGA : public osg::ReaderWriter +class ReaderWriterTGA : public osgDB::ReaderWriter { public: virtual const char* className() { return "TGA Image Reader"; } virtual bool acceptsExtension(const std::string& extension) { return extension=="tga"; } - virtual osg::Node* readNode(const std::string& fileName) - { - osg::Image* image = readImage(fileName); - if (image) - { - osg::Geode* geode = osg::createGeodeForImage(image); - if (geode==NULL) image->unref(); - return geode; - } - else - { - return NULL; - } - } - virtual osg::Image* readImage(const std::string& fileName) { @@ -451,7 +478,7 @@ class ReaderWriterTGA : public osg::ReaderWriter int numComponents_ret; imageData = simage_tga_load(fileName.c_str(),&width_ret,&height_ret,&numComponents_ret); - + if (imageData==NULL) return NULL; int s = width_ret; @@ -462,19 +489,19 @@ class ReaderWriterTGA : public osg::ReaderWriter unsigned int pixelFormat = numComponents_ret == 1 ? GL_LUMINANCE : - numComponents_ret == 2 ? GL_LUMINANCE_ALPHA : - numComponents_ret == 3 ? GL_RGB : - numComponents_ret == 4 ? GL_RGBA : (GLenum)-1; + numComponents_ret == 2 ? GL_LUMINANCE_ALPHA : + numComponents_ret == 3 ? GL_RGB : + numComponents_ret == 4 ? GL_RGBA : (GLenum)-1; unsigned int dataType = GL_UNSIGNED_BYTE; osg::Image* pOsgImage = new osg::Image; pOsgImage->setFileName(fileName.c_str()); - pOsgImage->setImage(s,t,r, - internalFormat, - pixelFormat, - dataType, - imageData); + pOsgImage->setImage(s,t,r, + internalFormat, + pixelFormat, + dataType, + imageData); return pOsgImage; @@ -483,4 +510,4 @@ class ReaderWriterTGA : public osg::ReaderWriter // now register with Registry to instantiate the above // reader/writer. -osg::RegisterReaderWriterProxy g_readerWriter_TGA_Proxy; +osgDB::RegisterReaderWriterProxy g_readerWriter_TGA_Proxy; diff --git a/src/osgPlugins/tgz/ReaderWriterTGZ.cpp b/src/osgPlugins/tgz/ReaderWriterTGZ.cpp index 4c3c6b79a..a78139665 100644 --- a/src/osgPlugins/tgz/ReaderWriterTGZ.cpp +++ b/src/osgPlugins/tgz/ReaderWriterTGZ.cpp @@ -1,109 +1,121 @@ #include #include #include -#include #include -#include #include -#include -#include + +#include #include -#include #include -#include "osg/FileNameUtils" + +#include +#include +#include +#include + +#ifdef _WIN32 +#include +#else +#include +#endif using namespace osg; -#ifdef __sgi -static int dirent_select( dirent *dent ) -#else -static int dirent_select( const dirent *dent ) -#endif +class ReaderWriterTGZ : public osgDB::ReaderWriter { - // if blank name don't pass selection. - if (dent->d_name[0]==0) return 0; + public: + virtual const char* className() { return "TGZ Database Reader/Writer"; } - // if current directory '.' don't pass selection. - if (strcmp(dent->d_name,".")==0) return 0; - - // if parent directory '..' don't pass selection. - if (strcmp(dent->d_name,"..")==0) return 0; - - // should test for file being a directory? - - // if length < 4 chars then can't be .tgz extension three pass test. - if (strlen(dent->d_name)<4) return 1; - - // return 1 (for pass) if - return strncmp( ".tgz", &dent->d_name[strlen(dent->d_name)-4], 4 ); -} - -class ReaderWriterTGZ : public ReaderWriter { - public: - virtual const char* className() { return "TGZ Database Reader/Writer"; } - virtual bool acceptsExtension(const std::string& extension) { return extension=="tgz"; } - - virtual Node* readNode(const std::string& fileName) + virtual bool acceptsExtension(const std::string& extension) { - std::string ext = getLowerCaseFileExtension(fileName); + return osgDB::equalCaseInsensitive(extension,"tgz"); + } + + virtual Node* readNode(const std::string& fileName) + { + std::string ext = osgDB::getLowerCaseFileExtension(fileName); if (!acceptsExtension(ext)) return NULL; osg::notify(osg::INFO)<< "ReaderWriterTGZ::readNode( "<getCreateNodeFromImage(); + osgDB::Registry::instance()->setCreateNodeFromImage(false); - ndent = scandir( dirname, &dent, dirent_select, alphasort ); + osgDB::DirectoryContents contents = osgDB::getDirectoryContents(dirname); + for(osgDB::DirectoryContents::iterator itr = contents.begin(); + itr != contents.end(); + ++itr) + { + std::string file_ext = osgDB::getFileExtension(*itr); + if (!acceptsExtension(file_ext) && + *itr!=std::string(".") && + *itr!=std::string("..")) + { + osg::Node *node = osgDB::readNodeFile(*itr); + grp->addChild( node ); + } + } - for( int i = 0; i < ndent; i++ ) - { - osg::Node *node = osg::loadNodeFile( dent[i]->d_name ); - grp->addChild( node ); - } + // restorre original state of the automatic generation of images to geode's. + osgDB::Registry::instance()->setCreateNodeFromImage(prevCreateNodeFromImage); + #ifdef _WIN32 + // note, is this the right command for windows? + // is there any way of overiding the Y/N option? RO. + sprintf( command, "erase %s", dirname ); + system( command ); + #else + sprintf( command, "rm -rf %s", dirname ); + system( command ); + #endif - sprintf( command, "rm -rf %s", dirname ); - system( command ); + if( grp->getNumChildren() == 0 ) + { + grp->unref(); + return NULL; + } - if( grp->getNumChildren() == 0 ) - { - grp->unref(); - return NULL; - } + return grp; - else - return grp; } - - virtual bool writeNode(Node& obj,const std::string& fileName) { - return false; - } }; // now register with sgRegistry to instantiate the above // reader/writer. -RegisterReaderWriterProxy g_readerWriter_TGZ_Proxy; +osgDB::RegisterReaderWriterProxy g_readerWriter_TGZ_Proxy; diff --git a/src/osgPlugins/tiff/Makefile b/src/osgPlugins/tiff/Makefile index 83849d496..e75645526 100644 --- a/src/osgPlugins/tiff/Makefile +++ b/src/osgPlugins/tiff/Makefile @@ -4,13 +4,13 @@ include ../../../Make/makedefs C++FILES = \ ReaderWriterTIFF.cpp\ -LIB = ../../../lib/osgPlugins/osgdb_tif.so +LIB = ../../../lib/osgPlugins/osgdb_tiff.so -TARGET_LOADER_FILES = osgPlugins/osgdb_tif.so +TARGET_LOADER_FILES = osgPlugins/osgdb_tiff.so LIBS = -ltiff C++FLAGS += -I. -I../../../include -LDFLAGS += -L../../../lib +LDFLAGS += -L../../../lib $(FREEBSD_LOCALLIBS) include ../../../Make/makerules diff --git a/src/osgPlugins/tiff/ReaderWriterTIFF.cpp b/src/osgPlugins/tiff/ReaderWriterTIFF.cpp index ccca7e77d..be96c1788 100644 --- a/src/osgPlugins/tiff/ReaderWriterTIFF.cpp +++ b/src/osgPlugins/tiff/ReaderWriterTIFF.cpp @@ -1,29 +1,28 @@ -#include -#include -#include -#include -#include -#include -#include +#include +#include +#include +#include #include +#include + #include /**************************************************************************** * * Follows is code extracted from the simage library. Original Authors: * - * Systems in Motion, + * Systems in Motion, * - * + * * Peder Blekken * Morten Eriksen - * Marius Bugge Monsen + * Marius Bugge Monsen * - * The original COPYING notice + * The original COPYING notice * - * All files in this library are public domain, except simage_rgb.cpp which is + * All files in this library are public domain, except simage_rgb.cpp which is * Copyright (c) Mark J Kilgard . I will contact Mark * very soon to hear if this source also can become public domain. * @@ -39,7 +38,6 @@ * **********************************************************************/ -#include #include #include @@ -58,331 +56,355 @@ static int tifferror = ERR_NO_ERROR; int simage_tiff_error(char * buffer, int buflen) { - switch (tifferror) { - case ERR_OPEN: - strncpy(buffer, "TIFF loader: Error opening file", buflen); - break; - case ERR_MEM: - strncpy(buffer, "TIFF loader: Out of memory error", buflen); - break; - case ERR_UNSUPPORTED: - strncpy(buffer, "TIFF loader: Unsupported image type", buflen); - break; - case ERR_TIFFLIB: - strncpy(buffer, "TIFF loader: Illegal tiff file", buflen); - break; - } - return tifferror; + switch (tifferror) + { + case ERR_OPEN: + strncpy(buffer, "TIFF loader: Error opening file", buflen); + break; + case ERR_MEM: + strncpy(buffer, "TIFF loader: Out of memory error", buflen); + break; + case ERR_UNSUPPORTED: + strncpy(buffer, "TIFF loader: Unsupported image type", buflen); + break; + case ERR_TIFFLIB: + strncpy(buffer, "TIFF loader: Illegal tiff file", buflen); + break; + } + return tifferror; } -static void -tiff_error(const char* module, const char* fmt, va_list list) +static void +tiff_error(const char*, const char*, va_list) { - /* FIXME: store error message ? */ + // values are (const char* module, const char* fmt, va_list list) + /* FIXME: store error message ? */ } -static void -tiff_warn(const char * module, const char * fmt, va_list list) + +static void +tiff_warn(const char *, const char *, va_list) { - /* FIXME: notify? */ + // values are (const char* module, const char* fmt, va_list list) + /* FIXME: notify? */ } + static int checkcmap(int n, uint16* r, uint16* g, uint16* b) { - while (n-- > 0) - if (*r++ >= 256 || *g++ >= 256 || *b++ >= 256) - return (16); - /* Assuming 8-bit colormap */ - return (8); + while (n-- > 0) + if (*r++ >= 256 || *g++ >= 256 || *b++ >= 256) + return (16); + /* Assuming 8-bit colormap */ + return (8); } -static void + +static void invert_row(unsigned char *ptr, unsigned char *data, int n, int invert) { - while (n--) { - if (invert) *ptr++ = 255 - *data++; - else *ptr++ = *data++; - } + while (n--) + { + if (invert) *ptr++ = 255 - *data++; + else *ptr++ = *data++; + } } -static void +static void remap_row(unsigned char *ptr, unsigned char *data, int n, - unsigned short *rmap, unsigned short *gmap, unsigned short *bmap) +unsigned short *rmap, unsigned short *gmap, unsigned short *bmap) { - unsigned int ix; - while (n--) { - ix = *data++; - *ptr++ = (unsigned char) rmap[ix]; - *ptr++ = (unsigned char) gmap[ix]; - *ptr++ = (unsigned char) bmap[ix]; - } + unsigned int ix; + while (n--) + { + ix = *data++; + *ptr++ = (unsigned char) rmap[ix]; + *ptr++ = (unsigned char) gmap[ix]; + *ptr++ = (unsigned char) bmap[ix]; + } } -static void + +static void copy_row(unsigned char *ptr, unsigned char *data, int n) { - while (n--) { - *ptr++ = *data++; - *ptr++ = *data++; - *ptr++ = *data++; - } + while (n--) + { + *ptr++ = *data++; + *ptr++ = *data++; + *ptr++ = *data++; + } } -static void + +static void interleave_row(unsigned char *ptr, - unsigned char *red, unsigned char *blue, unsigned char *green, - int n) +unsigned char *red, unsigned char *blue, unsigned char *green, +int n) { - while (n--) { - *ptr++ = *red++; - *ptr++ = *green++; - *ptr++ = *blue++; - } + while (n--) + { + *ptr++ = *red++; + *ptr++ = *green++; + *ptr++ = *blue++; + } } -int -simage_tiff_identify(const char *ptr, - const unsigned char *header, - int headerlen) + +int +simage_tiff_identify(const char *, +const unsigned char *header, +int headerlen) { - static unsigned char tifcmp[] = {0x4d, 0x4d, 0x0, 0x2a}; - static unsigned char tifcmp2[] = {0x49, 0x49, 0x2a, 0}; - - if (headerlen < 4) return 0; - if (memcmp((const void*)header, (const void*)tifcmp, 4) == 0) return 1; - if (memcmp((const void*)header, (const void*)tifcmp2, 4) == 0) return 1; - return 0; + static unsigned char tifcmp[] = {0x4d, 0x4d, 0x0, 0x2a}; + static unsigned char tifcmp2[] = {0x49, 0x49, 0x2a, 0}; + + if (headerlen < 4) return 0; + if (memcmp((const void*)header, (const void*)tifcmp, 4) == 0) return 1; + if (memcmp((const void*)header, (const void*)tifcmp2, 4) == 0) return 1; + return 0; } + /* useful defines (undef'ed below) */ -#define CVT(x) (((x) * 255L) / ((1L<<16)-1)) -#define pack(a,b) ((a)<<8 | (b)) +#define CVT(x) (((x) * 255L) / ((1L<<16)-1)) +#define pack(a,b) ((a)<<8 | (b)) unsigned char * simage_tiff_load(const char *filename, - int *width_ret, - int *height_ret, - int *numComponents_ret) +int *width_ret, +int *height_ret, +int *numComponents_ret) { - TIFF *in; - uint16 samplesperpixel; - uint16 bitspersample; - uint16 photometric; - uint32 w, h; - uint16 config; - uint16* red; - uint16* green; - uint16* blue; - unsigned char *inbuf = NULL; - tsize_t rowsize; - uint32 row; - int format; - unsigned char *buffer; - int width; - int height; - unsigned char *currPtr; + TIFF *in; + uint16 samplesperpixel; + uint16 bitspersample; + uint16 photometric; + uint32 w, h; + uint16 config; + uint16* red; + uint16* green; + uint16* blue; + unsigned char *inbuf = NULL; + tsize_t rowsize; + uint32 row; + int format; + unsigned char *buffer; + int width; + int height; + unsigned char *currPtr; + TIFFSetErrorHandler(tiff_error); + TIFFSetWarningHandler(tiff_warn); - TIFFSetErrorHandler(tiff_error); - TIFFSetWarningHandler(tiff_warn); - - in = TIFFOpen(filename, "r"); - if (in == NULL) { - tifferror = ERR_OPEN; - return NULL; - } - if (TIFFGetField(in, TIFFTAG_PHOTOMETRIC, &photometric) == 1) { - if (photometric != PHOTOMETRIC_RGB && photometric != PHOTOMETRIC_PALETTE && - photometric != PHOTOMETRIC_MINISWHITE && - photometric != PHOTOMETRIC_MINISBLACK) { - /*Bad photometric; can only handle Grayscale, RGB and Palette images :-( */ - TIFFClose(in); - tifferror = ERR_UNSUPPORTED; - return NULL; + in = TIFFOpen(filename, "r"); + if (in == NULL) + { + tifferror = ERR_OPEN; + return NULL; } - } - else { - tifferror = ERR_READ; + if (TIFFGetField(in, TIFFTAG_PHOTOMETRIC, &photometric) == 1) + { + if (photometric != PHOTOMETRIC_RGB && photometric != PHOTOMETRIC_PALETTE && + photometric != PHOTOMETRIC_MINISWHITE && + photometric != PHOTOMETRIC_MINISBLACK) + { + /*Bad photometric; can only handle Grayscale, RGB and Palette images :-( */ + TIFFClose(in); + tifferror = ERR_UNSUPPORTED; + return NULL; + } + } + else + { + tifferror = ERR_READ; + TIFFClose(in); + return NULL; + } + + if (TIFFGetField(in, TIFFTAG_SAMPLESPERPIXEL, &samplesperpixel) == 1) + { + if (samplesperpixel != 1 && samplesperpixel != 3) + { + /* Bad samples/pixel */ + tifferror = ERR_UNSUPPORTED; + TIFFClose(in); + return NULL; + } + } + else + { + tifferror = ERR_READ; + TIFFClose(in); + return NULL; + } + + if (TIFFGetField(in, TIFFTAG_BITSPERSAMPLE, &bitspersample) == 1) + { + if (bitspersample != 8) + { + /* can only handle 8-bit samples. */ + TIFFClose(in); + tifferror = ERR_UNSUPPORTED; + return NULL; + } + } + else + { + tifferror = ERR_READ; + TIFFClose(in); + return NULL; + } + + if (TIFFGetField(in, TIFFTAG_IMAGEWIDTH, &w) != 1 || + TIFFGetField(in, TIFFTAG_IMAGELENGTH, &h) != 1 || + TIFFGetField(in, TIFFTAG_PLANARCONFIG, &config) != 1) + { + TIFFClose(in); + tifferror = ERR_READ; + return NULL; + } + + if (photometric == PHOTOMETRIC_MINISWHITE || + photometric == PHOTOMETRIC_MINISBLACK) + format = 1; + else + format = 3; + + buffer = (unsigned char*)malloc(w*h*format); + + if (!buffer) + { + tifferror = ERR_MEM; + TIFFClose(in); + return NULL; + } + + width = w; + height = h; + + currPtr = buffer + (h-1)*w*format; + + tifferror = ERR_NO_ERROR; + + switch (pack(photometric, config)) + { + case pack(PHOTOMETRIC_MINISWHITE, PLANARCONFIG_CONTIG): + case pack(PHOTOMETRIC_MINISBLACK, PLANARCONFIG_CONTIG): + case pack(PHOTOMETRIC_MINISWHITE, PLANARCONFIG_SEPARATE): + case pack(PHOTOMETRIC_MINISBLACK, PLANARCONFIG_SEPARATE): + + inbuf = (unsigned char *)malloc(TIFFScanlineSize(in)); + for (row = 0; row < h; row++) + { + if (TIFFReadScanline(in, inbuf, row, 0) < 0) + { + tifferror = ERR_READ; + break; + } + invert_row(currPtr, inbuf, w, photometric == PHOTOMETRIC_MINISWHITE); + currPtr -= format*w; + } + break; + + case pack(PHOTOMETRIC_PALETTE, PLANARCONFIG_CONTIG): + case pack(PHOTOMETRIC_PALETTE, PLANARCONFIG_SEPARATE): + if (TIFFGetField(in, TIFFTAG_COLORMAP, &red, &green, &blue) != 1) + tifferror = ERR_READ; + /* */ + /* Convert 16-bit colormap to 8-bit (unless it looks */ + /* like an old-style 8-bit colormap). */ + /* */ + if (!tifferror && checkcmap(1<= 0; i--) + { + red[i] = CVT(red[i]); + green[i] = CVT(green[i]); + blue[i] = CVT(blue[i]); + } + } + + inbuf = (unsigned char *)malloc(TIFFScanlineSize(in)); + for (row = 0; row < h; row++) + { + if (TIFFReadScanline(in, inbuf, row, 0) < 0) + { + tifferror = ERR_READ; + break; + } + remap_row(currPtr, inbuf, w, red, green, blue); + currPtr -= format*w; + } + break; + + case pack(PHOTOMETRIC_RGB, PLANARCONFIG_CONTIG): + inbuf = (unsigned char *)malloc(TIFFScanlineSize(in)); + for (row = 0; row < h; row++) + { + if (TIFFReadScanline(in, inbuf, row, 0) < 0) + { + tifferror = ERR_READ; + break; + } + copy_row(currPtr, inbuf, w); + currPtr -= format*w; + } + break; + + case pack(PHOTOMETRIC_RGB, PLANARCONFIG_SEPARATE): + rowsize = TIFFScanlineSize(in); + inbuf = (unsigned char *)malloc(3*rowsize); + for (row = 0; !tifferror && row < h; row++) + { + int s; + for (s = 0; s < 3; s++) + { + if (TIFFReadScanline(in, (tdata_t)(inbuf+s*rowsize), (uint32)row, (tsample_t)s) < 0) + { + tifferror = ERR_READ; break; + } + } + if (!tifferror) + { + interleave_row(currPtr, inbuf, inbuf+rowsize, inbuf+2*rowsize, w); + currPtr -= format*w; + } + } + break; + default: + tifferror = ERR_UNSUPPORTED; + break; + } + + if (inbuf) free(inbuf); TIFFClose(in); - return NULL; - } - - if (TIFFGetField(in, TIFFTAG_SAMPLESPERPIXEL, &samplesperpixel) == 1) { - if (samplesperpixel != 1 && samplesperpixel != 3) { - /* Bad samples/pixel */ - tifferror = ERR_UNSUPPORTED; - TIFFClose(in); - return NULL; + + if (tifferror) + { + if (buffer) free(buffer); + return NULL; } - } - else { - tifferror = ERR_READ; - TIFFClose(in); - return NULL; - } - - if (TIFFGetField(in, TIFFTAG_BITSPERSAMPLE, &bitspersample) == 1) { - if (bitspersample != 8) { - /* can only handle 8-bit samples. */ - TIFFClose(in); - tifferror = ERR_UNSUPPORTED; - return NULL; - } - } - else { - tifferror = ERR_READ; - TIFFClose(in); - return NULL; - } - - if (TIFFGetField(in, TIFFTAG_IMAGEWIDTH, &w) != 1 || - TIFFGetField(in, TIFFTAG_IMAGELENGTH, &h) != 1 || - TIFFGetField(in, TIFFTAG_PLANARCONFIG, &config) != 1) { - TIFFClose(in); - tifferror = ERR_READ; - return NULL; - } - - if (photometric == PHOTOMETRIC_MINISWHITE || - photometric == PHOTOMETRIC_MINISBLACK) - format = 1; - else - format = 3; - - buffer = (unsigned char*)malloc(w*h*format); - - if (!buffer) { - tifferror = ERR_MEM; - TIFFClose(in); - return NULL; - } - - width = w; - height = h; - - currPtr = buffer + (h-1)*w*format; - - tifferror = ERR_NO_ERROR; - - switch (pack(photometric, config)) { - case pack(PHOTOMETRIC_MINISWHITE, PLANARCONFIG_CONTIG): - case pack(PHOTOMETRIC_MINISBLACK, PLANARCONFIG_CONTIG): - case pack(PHOTOMETRIC_MINISWHITE, PLANARCONFIG_SEPARATE): - case pack(PHOTOMETRIC_MINISBLACK, PLANARCONFIG_SEPARATE): - - inbuf = (unsigned char *)malloc(TIFFScanlineSize(in)); - for (row = 0; row < h; row++) { - if (TIFFReadScanline(in, inbuf, row, 0) < 0) { - tifferror = ERR_READ; - break; - } - invert_row(currPtr, inbuf, w, photometric == PHOTOMETRIC_MINISWHITE); - currPtr -= format*w; - } - break; - - case pack(PHOTOMETRIC_PALETTE, PLANARCONFIG_CONTIG): - case pack(PHOTOMETRIC_PALETTE, PLANARCONFIG_SEPARATE): - if (TIFFGetField(in, TIFFTAG_COLORMAP, &red, &green, &blue) != 1) - tifferror = ERR_READ; - /* */ - /* Convert 16-bit colormap to 8-bit (unless it looks */ - /* like an old-style 8-bit colormap). */ - /* */ - if (!tifferror && checkcmap(1<= 0; i--) { - red[i] = CVT(red[i]); - green[i] = CVT(green[i]); - blue[i] = CVT(blue[i]); - } - } - - inbuf = (unsigned char *)malloc(TIFFScanlineSize(in)); - for (row = 0; row < h; row++) { - if (TIFFReadScanline(in, inbuf, row, 0) < 0) { - tifferror = ERR_READ; - break; - } - remap_row(currPtr, inbuf, w, red, green, blue); - currPtr -= format*w; - } - break; - - case pack(PHOTOMETRIC_RGB, PLANARCONFIG_CONTIG): - inbuf = (unsigned char *)malloc(TIFFScanlineSize(in)); - for (row = 0; row < h; row++) { - if (TIFFReadScanline(in, inbuf, row, 0) < 0) { - tifferror = ERR_READ; - break; - } - copy_row(currPtr, inbuf, w); - currPtr -= format*w; - } - break; - - case pack(PHOTOMETRIC_RGB, PLANARCONFIG_SEPARATE): - rowsize = TIFFScanlineSize(in); - inbuf = (unsigned char *)malloc(3*rowsize); - for (row = 0; !tifferror && row < h; row++) { - int s; - for (s = 0; s < 3; s++) { - if (TIFFReadScanline(in, (tdata_t)(inbuf+s*rowsize), (uint32)row, (tsample_t)s) < 0) { - tifferror = ERR_READ; break; - } - } - if (!tifferror) { - interleave_row(currPtr, inbuf, inbuf+rowsize, inbuf+2*rowsize, w); - currPtr -= format*w; - } - } - break; - default: - tifferror = ERR_UNSUPPORTED; - break; - } - - if (inbuf) free(inbuf); - TIFFClose(in); - - if (tifferror) { - if (buffer) free(buffer); - return NULL; - } - *width_ret = width; - *height_ret = height; - *numComponents_ret = format; - return buffer; + *width_ret = width; + *height_ret = height; + *numComponents_ret = format; + return buffer; } + #undef CVT #undef pack - -class ReaderWriterTIFF : public osg::ReaderWriter +class ReaderWriterTIFF : public osgDB::ReaderWriter { public: virtual const char* className() { return "TIFF Image Reader"; } virtual bool acceptsExtension(const std::string& extension) { return extension=="tiff"; } - virtual osg::Node* readNode(const std::string& fileName) - { - osg::Image* image = readImage(fileName); - if (image) - { - osg::Geode* geode = osg::createGeodeForImage(image); - if (geode==NULL) image->unref(); - return geode; - } - else - { - return NULL; - } - } - virtual osg::Image* readImage(const std::string& fileName) { @@ -392,7 +414,7 @@ class ReaderWriterTIFF : public osg::ReaderWriter int numComponents_ret; imageData = simage_tiff_load(fileName.c_str(),&width_ret,&height_ret,&numComponents_ret); - + if (imageData==NULL) return NULL; int s = width_ret; @@ -403,19 +425,19 @@ class ReaderWriterTIFF : public osg::ReaderWriter unsigned int pixelFormat = numComponents_ret == 1 ? GL_LUMINANCE : - numComponents_ret == 2 ? GL_LUMINANCE_ALPHA : - numComponents_ret == 3 ? GL_RGB : - numComponents_ret == 4 ? GL_RGBA : (GLenum)-1; + numComponents_ret == 2 ? GL_LUMINANCE_ALPHA : + numComponents_ret == 3 ? GL_RGB : + numComponents_ret == 4 ? GL_RGBA : (GLenum)-1; unsigned int dataType = GL_UNSIGNED_BYTE; osg::Image* pOsgImage = new osg::Image; pOsgImage->setFileName(fileName.c_str()); - pOsgImage->setImage(s,t,r, - internalFormat, - pixelFormat, - dataType, - imageData); + pOsgImage->setImage(s,t,r, + internalFormat, + pixelFormat, + dataType, + imageData); return pOsgImage; @@ -424,4 +446,4 @@ class ReaderWriterTIFF : public osg::ReaderWriter // now register with Registry to instantiate the above // reader/writer. -osg::RegisterReaderWriterProxy g_readerWriter_TIFF_Proxy; +osgDB::RegisterReaderWriterProxy g_readerWriter_TIFF_Proxy; diff --git a/src/osgPlugins/zip/ReaderWriterZIP.cpp b/src/osgPlugins/zip/ReaderWriterZIP.cpp index 12be2bd2c..98ff4e6b8 100644 --- a/src/osgPlugins/zip/ReaderWriterZIP.cpp +++ b/src/osgPlugins/zip/ReaderWriterZIP.cpp @@ -1,104 +1,110 @@ #include #include #include -#include #include -#include #include -#include -#include + +#include #include -#include #include -#include "osg/FileNameUtils" -using namespace osg; +#include +#include +#include +#include -#ifdef __sgi -static int dirent_select( dirent *dent ) +#ifdef _WIN32 +#include #else -static int dirent_select( const dirent *dent ) +#include #endif + +class ReaderWriterZIP : public osgDB::ReaderWriter { - // if blank name don't pass selection. - if (dent->d_name[0]==0) return 0; + public: + virtual const char* className() { return "ZIP Database Reader/Writer"; } - // if current directory '.' don't pass selection. - if (strcmp(dent->d_name,".")==0) return 0; + virtual bool acceptsExtension(const std::string& extension) + { + return osgDB::equalCaseInsensitive(extension,"zip"); + } - // if parent directory '..' don't pass selection. - if (strcmp(dent->d_name,"..")==0) return 0; - - // should test for file being a directory? - - // if length < 4 chars then can't be .tgz extension three pass test. - if (strlen(dent->d_name)<4) return 1; - - // return 1 (for pass) if - return strncmp( ".zip", &dent->d_name[strlen(dent->d_name)-4], 4 ); -} - -class ReaderWriterZIP : public ReaderWriter { - public: - virtual const char* className() { return "ZIP Database Reader/Writer"; } - virtual bool acceptsExtension(const std::string& extension) { return extension=="zip"; } - - virtual Node* readNode(const std::string& fileName) + virtual osg::Node* readNode(const std::string& fileName) { - std::string ext = osg::getLowerCaseFileExtension(fileName); + std::string ext = osgDB::getLowerCaseFileExtension(fileName); if (!acceptsExtension(ext)) return NULL; osg::notify(osg::INFO)<<"ReaderWriterZIP::readNode( "<d_name<d_name ); - grp->addChild( node ); - } + osg::Group *grp = new osg::Group; + osgDB::setFilePath( dirname ); + bool prevCreateNodeFromImage = osgDB::Registry::instance()->getCreateNodeFromImage(); + osgDB::Registry::instance()->setCreateNodeFromImage(false); - sprintf( command, "rm -rf %s", dirname ); - system( command ); + osgDB::DirectoryContents contents = osgDB::getDirectoryContents(dirname); + for(osgDB::DirectoryContents::iterator itr = contents.begin(); + itr != contents.end(); + ++itr) + { + std::string file_ext = osgDB::getFileExtension(*itr); + if (!acceptsExtension(file_ext) && + *itr!=std::string(".") && + *itr!=std::string("..")) + { + osg::Node *node = osgDB::readNodeFile( *itr ); + grp->addChild( node ); + } + } - if( grp->getNumChildren() == 0 ) - { - grp->unref(); - return NULL; - } + osgDB::Registry::instance()->setCreateNodeFromImage(prevCreateNodeFromImage); - else - return grp; + #ifdef _WIN32 + // note, is this the right command for windows? + // is there any way of overiding the Y/N option? RO. + sprintf( command, "erase %s", dirname ); + system( command ); + #else + + sprintf( command, "rm -rf %s", dirname ); + system( command ); + #endif + + if( grp->getNumChildren() == 0 ) + { + grp->unref(); + return NULL; + } + + return grp; } - - virtual bool writeNode(Node& obj,const std::string& fileName) { - return false; - } }; // now register with sgRegistry to instantiate the above // reader/writer. -RegisterReaderWriterProxy g_readerWriter_ZIP_Proxy; +osgDB::RegisterReaderWriterProxy g_readerWriter_ZIP_Proxy; diff --git a/src/osgUtil/CameraManipulator.cpp b/src/osgUtil/CameraManipulator.cpp index 8961c134b..622a71ceb 100644 --- a/src/osgUtil/CameraManipulator.cpp +++ b/src/osgUtil/CameraManipulator.cpp @@ -9,21 +9,25 @@ CameraManipulator::CameraManipulator(): _camera(NULL) { } + CameraManipulator::~CameraManipulator() { } + void CameraManipulator::setCamera(Camera *camera) { _camera=camera; } -Camera *CameraManipulator::getCamera() const + +const Camera *CameraManipulator::getCamera() const { return _camera.get(); } -bool CameraManipulator::update(GUIEventAdapter&,GUIActionAdapter&) + +bool CameraManipulator::handle(const GUIEventAdapter&,GUIActionAdapter&) { return false; } diff --git a/src/osgUtil/DisplayListVisitor.cpp b/src/osgUtil/DisplayListVisitor.cpp index a7b1cb252..b98909b15 100644 --- a/src/osgUtil/DisplayListVisitor.cpp +++ b/src/osgUtil/DisplayListVisitor.cpp @@ -1,37 +1,56 @@ #include "osgUtil/DisplayListVisitor" -#include "osg/GeoSet" +#include "osg/Drawable" using namespace osg; using namespace osgUtil; DisplayListVisitor::DisplayListVisitor(DisplayListMode mode) { - setTraverseMode(osg::NodeVisitor::TRAVERSE_ALL_CHILDREN); + setTraversalMode(osg::NodeVisitor::TRAVERSE_ALL_CHILDREN); _displayListMode = mode; + + _localState = new osg::State; + _externalState = NULL; + + _activeState = _localState; } + void DisplayListVisitor::apply(osg::Geode& node) { switch(_displayListMode) { - case(SWITCH_OFF_DISPLAY_LISTS): + case(SWITCH_OFF_DISPLAY_LISTS): { - for(int i=0;isetUseDisplayList(false); + node.getDrawable(i)->setUseDisplayList(false); } } break; - case(SWITCH_ON_DISPLAY_LISTS): + case(SWITCH_ON_DISPLAY_LISTS): { - for(int i=0;isetUseDisplayList(true); + node.getDrawable(i)->setUseDisplayList(true); } } break; - case(SWITCH_ON_AND_COMPILE_DISPLAY_LISTS): - node.compileGeoSets(); + case(COMPILE_ON_DISPLAY_LISTS): + { + for(int i=0;igetUseDisplayList()) + { + node.getDrawable(i)->compile(*_activeState); + } + } + } + break; + case(SWITCH_ON_AND_COMPILE_DISPLAY_LISTS): + { + node.compileDrawables(*_activeState); + } break; } } diff --git a/src/osgUtil/DriveManipulator.cpp b/src/osgUtil/DriveManipulator.cpp index 5284ebd89..33b66596e 100644 --- a/src/osgUtil/DriveManipulator.cpp +++ b/src/osgUtil/DriveManipulator.cpp @@ -1,3 +1,7 @@ +#if defined(_MSC_VER) + #pragma warning( disable : 4786 ) +#endif + #include "osgUtil/DriveManipulator" #include "osgUtil/IntersectVisitor" #include "osg/Notify" @@ -9,37 +13,42 @@ DriveManipulator::DriveManipulator() { _modelScale = 0.01f; _velocity = 0.0f; - _speedMode = USE_MOUSE_Y_FOR_SPEED; + //_speedMode = USE_MOUSE_Y_FOR_SPEED; + _speedMode = USE_MOUSE_BUTTONS_FOR_SPEED; } + DriveManipulator::~DriveManipulator() { } + void DriveManipulator::setNode(osg::Node* node) { _node = node; if (_node.get()) { - const osg::BoundingSphere& boundingSphere=_node->getBound(); + const osg::BoundingSphere& boundingSphere=_node->getBound(); _modelScale = boundingSphere._radius; _height = sqrtf(_modelScale)*0.03f; _buffer = sqrtf(_modelScale)*0.05f; } } -osg::Node* DriveManipulator::getNode() const + +const osg::Node* DriveManipulator::getNode() const { return _node.get(); } -void DriveManipulator::home(GUIEventAdapter& ea,GUIActionAdapter& us) + +void DriveManipulator::home(const GUIEventAdapter& ea,GUIActionAdapter& us) { if(_node.get() && _camera.get()) { - const osg::BoundingSphere& boundingSphere=_node->getBound(); + const osg::BoundingSphere& boundingSphere=_node->getBound(); osg::Vec3 ep = boundingSphere._center; osg::Vec3 bp = ep; @@ -51,9 +60,9 @@ void DriveManipulator::home(GUIEventAdapter& ea,GUIActionAdapter& us) bool cameraSet = false; - osg::ref_ptr segDown = new osg::Seg; + osg::ref_ptr segDown = new osg::LineSegment; segDown->set(ep,bp); - iv.addSeg(segDown.get()); + iv.addLineSegment(segDown.get()); _node->accept(iv); @@ -62,10 +71,10 @@ void DriveManipulator::home(GUIEventAdapter& ea,GUIActionAdapter& us) osgUtil::IntersectVisitor::HitList& hitList = iv.getHitList(segDown.get()); if (!hitList.empty()) { - // notify(INFO) << "Hit terrain ok"<0.0f) uv = np; else uv = -np; @@ -75,11 +84,10 @@ void DriveManipulator::home(GUIEventAdapter& ea,GUIActionAdapter& us) ep = ip; ep.z() += _height; osg::Vec3 lv = uv^osg::Vec3(1.0f,0.0f,0.0f); - osg::Vec3 lp = ep+lv*lookDistance; + osg::Vec3 cp = ep+lv*lookDistance; + + _camera->setLookAt(ep,cp,uv); - _camera->setView(ep,lp,uv); - _camera->ensureOrthogonalUpVector(); - cameraSet = true; } @@ -91,9 +99,9 @@ void DriveManipulator::home(GUIEventAdapter& ea,GUIActionAdapter& us) bp = ep; bp.z() += _modelScale; - osg::ref_ptr segUp = new osg::Seg; + osg::ref_ptr segUp = new osg::LineSegment; segUp->set(ep,bp); - iv.addSeg(segUp.get()); + iv.addLineSegment(segUp.get()); _node->accept(iv); @@ -102,55 +110,58 @@ void DriveManipulator::home(GUIEventAdapter& ea,GUIActionAdapter& us) osgUtil::IntersectVisitor::HitList& hitList = iv.getHitList(segUp.get()); if (!hitList.empty()) { - // notify(INFO) << "Hit terrain ok"<0.0f) uv = np; - else uv = -np; + osg::Vec3 uv; + if (np.z()>0.0f) uv = np; + else uv = -np; - float lookDistance = _modelScale*0.1f; + float lookDistance = _modelScale*0.1f; - ep = ip; - ep.z() += _height; - osg::Vec3 lv = uv^osg::Vec3(1.0f,0.0f,0.0f); - osg::Vec3 lp = ep+lv*lookDistance; + ep = ip; + ep.z() += _height; + osg::Vec3 lv = uv^osg::Vec3(1.0f,0.0f,0.0f); + osg::Vec3 cp = ep+lv*lookDistance; - _camera->setView(ep,lp,uv); - _camera->ensureOrthogonalUpVector(); - - cameraSet = true; + _camera->setLookAt(ep,cp,uv); + + cameraSet = true; } } } - + if (!cameraSet) { - _camera->setView(boundingSphere._center+osg::Vec3( 0.0,-2.0f * boundingSphere._radius,0.0f), // eye - boundingSphere._center, // look - osg::Vec3(0.0f,0.0f,1.0f)); // up + // eye + _camera->setLookAt(boundingSphere._center+osg::Vec3( 0.0,-2.0f * boundingSphere._radius,0.0f), + // look + boundingSphere._center, + // up + osg::Vec3(0.0f,0.0f,1.0f)); } - + } _velocity = 0.0f; - us.needRedraw(); + us.requestRedraw(); - us.needWarpPointer((ea.getXmin()+ea.getXmax())/2,(ea.getYmin()+ea.getYmax())/2); + us.requestWarpPointer((ea.getXmin()+ea.getXmax())/2,(ea.getYmin()+ea.getYmax())/2); flushMouseEventStack(); } -void DriveManipulator::init(GUIEventAdapter& ea,GUIActionAdapter& us) + +void DriveManipulator::init(const GUIEventAdapter& ea,GUIActionAdapter& us) { flushMouseEventStack(); - us.needContinuousUpdate(false); + us.requestContinuousUpdate(false); _velocity = 0.0f; @@ -164,9 +175,9 @@ void DriveManipulator::init(GUIEventAdapter& ea,GUIActionAdapter& us) bool cameraSet = false; - osg::ref_ptr segDown = new osg::Seg; + osg::ref_ptr segDown = new osg::LineSegment; segDown->set(ep,bp); - iv.addSeg(segDown.get()); + iv.addLineSegment(segDown.get()); _node->accept(iv); @@ -175,7 +186,7 @@ void DriveManipulator::init(GUIEventAdapter& ea,GUIActionAdapter& us) osgUtil::IntersectVisitor::HitList& hitList = iv.getHitList(segDown.get()); if (!hitList.empty()) { -// notify(INFO) << "Hit terrain ok"<setView(ep,lp,uv); + _camera->setLookAt(ep,lp,uv); _camera->ensureOrthogonalUpVector(); cameraSet = true; @@ -203,9 +214,9 @@ void DriveManipulator::init(GUIEventAdapter& ea,GUIActionAdapter& us) bp = ep; bp.z() += _modelScale; - osg::ref_ptr segUp = new osg::Seg; + osg::ref_ptr segUp = new osg::LineSegment; segUp->set(ep,bp); - iv.addSeg(segUp.get()); + iv.addLineSegment(segUp.get()); _node->accept(iv); @@ -214,120 +225,123 @@ void DriveManipulator::init(GUIEventAdapter& ea,GUIActionAdapter& us) osgUtil::IntersectVisitor::HitList& hitList = iv.getHitList(segUp.get()); if (!hitList.empty()) { - // notify(INFO) << "Hit terrain ok"<0.0f) uv = np; - else uv = -np; + osg::Vec3 uv; + if (np.z()>0.0f) uv = np; + else uv = -np; - float lookDistance = _modelScale*0.1f; + float lookDistance = _modelScale*0.1f; - ep = ip+uv*_height; - osg::Vec3 lv = uv^sv; - osg::Vec3 lp = ep+lv*lookDistance; + ep = ip+uv*_height; + osg::Vec3 lv = uv^sv; + osg::Vec3 lp = ep+lv*lookDistance; - _camera->setView(ep,lp,uv); - _camera->ensureOrthogonalUpVector(); + _camera->setLookAt(ep,lp,uv); + _camera->ensureOrthogonalUpVector(); - cameraSet = true; + cameraSet = true; } } } - us.needWarpPointer((ea.getXmin()+ea.getXmax())/2,(ea.getYmin()+ea.getYmax())/2); + us.requestWarpPointer((ea.getXmin()+ea.getXmax())/2,(ea.getYmin()+ea.getYmax())/2); } -bool DriveManipulator::update(GUIEventAdapter& ea,GUIActionAdapter& us) + +bool DriveManipulator::handle(const GUIEventAdapter& ea,GUIActionAdapter& us) { if(!_camera.get()) return false; - + switch(ea.getEventType()) { - case(GUIEventAdapter::PUSH): + case(GUIEventAdapter::PUSH): { - + addMouseEvent(ea); - us.needContinuousUpdate(true); - if (calcMovement()) us.needRedraw(); + us.requestContinuousUpdate(true); + if (calcMovement()) us.requestRedraw(); } return true; - case(GUIEventAdapter::RELEASE): + case(GUIEventAdapter::RELEASE): { - + addMouseEvent(ea); - us.needContinuousUpdate(true); - if (calcMovement()) us.needRedraw(); + us.requestContinuousUpdate(true); + if (calcMovement()) us.requestRedraw(); } return true; - case(GUIEventAdapter::DRAG): + case(GUIEventAdapter::DRAG): { - + addMouseEvent(ea); - us.needContinuousUpdate(true); - if (calcMovement()) us.needRedraw(); + us.requestContinuousUpdate(true); + if (calcMovement()) us.requestRedraw(); } return true; - case(GUIEventAdapter::MOVE): + case(GUIEventAdapter::MOVE): { - + addMouseEvent(ea); - us.needContinuousUpdate(true); - if (calcMovement()) us.needRedraw(); + us.requestContinuousUpdate(true); + if (calcMovement()) us.requestRedraw(); } return true; - case(GUIEventAdapter::KEYBOARD): - if (ea.getKey()==' ') - { - flushMouseEventStack(); - home(ea,us); - us.needRedraw(); - us.needContinuousUpdate(false); + case(GUIEventAdapter::KEYBOARD): + if (ea.getKey()==' ') + { + flushMouseEventStack(); + home(ea,us); + us.requestRedraw(); + us.requestContinuousUpdate(false); + return true; + } + else if (ea.getKey()=='q') + { + _speedMode = USE_MOUSE_Y_FOR_SPEED; + return true; + } + else if (ea.getKey()=='a') + { + _speedMode = USE_MOUSE_BUTTONS_FOR_SPEED; + return true; + } + + return false; + case(GUIEventAdapter::FRAME): + addMouseEvent(ea); + if (calcMovement()) us.requestRedraw(); return true; - } - else if (ea.getKey()=='q') - { - _speedMode = USE_MOUSE_Y_FOR_SPEED; - return true; - } - else if (ea.getKey()=='a') - { - _speedMode = USE_MOUSE_BUTTONS_FOR_SPEED; - return true; - } - - return false; - case(GUIEventAdapter::FRAME): - addMouseEvent(ea); - if (calcMovement()) us.needRedraw(); - return true; - case(GUIEventAdapter::RESIZE): + case(GUIEventAdapter::RESIZE): { init(ea,us); - us.needRedraw(); + us.requestRedraw(); } return true; - default: - return false; + default: + return false; } } + void DriveManipulator::flushMouseEventStack() { _ga_t1 = NULL; _ga_t0 = NULL; } -void DriveManipulator::addMouseEvent(GUIEventAdapter& ea) + +void DriveManipulator::addMouseEvent(const GUIEventAdapter& ea) { _ga_t1 = _ga_t0; _ga_t0 = &ea; @@ -341,24 +355,23 @@ bool DriveManipulator::calcMovement() float dt = _ga_t0->time()-_ga_t1->time(); - if (dt<0.0f) { - notify(WARN) << "warning dt = "< segNormal = new osg::Seg; + + osg::ref_ptr segNormal = new osg::LineSegment; segNormal->set(fp,lfp); - iv.addSeg(segNormal.get()); + iv.addLineSegment(segNormal.get()); _node->accept(iv); @@ -461,7 +471,7 @@ bool DriveManipulator::calcMovement() osgUtil::IntersectVisitor::HitList& hitList = iv.getHitList(segNormal.get()); if (!hitList.empty()) { -// notify(INFO) << "Hit terrain ok"<setView(ep,lp,uv); + + _camera->setLookAt(ep,lp,uv); _camera->ensureOrthogonalUpVector(); return true; - + } } @@ -485,12 +495,12 @@ bool DriveManipulator::calcMovement() // under the influence of gravity. osg::Vec3 dp = lfp; dp.z() -= 2*_modelScale; - + iv.reset(); - - osg::ref_ptr segFall = new osg::Seg; + + osg::ref_ptr segFall = new osg::LineSegment; segFall->set(lfp,dp); - iv.addSeg(segFall.get()); + iv.addLineSegment(segFall.get()); _node->accept(iv); @@ -510,10 +520,10 @@ bool DriveManipulator::calcMovement() ep = ip+uv*_height; lv = uv^sv; osg::Vec3 lp = ep+lv*lookDistance; - - _camera->setView(ep,lp,uv); + + _camera->setLookAt(ep,lp,uv); _camera->ensureOrthogonalUpVector(); - + return true; } } @@ -522,14 +532,12 @@ bool DriveManipulator::calcMovement() lv *= (_velocity*dt); ep += lv; - osg::Vec3 lp = _camera->getLookPoint()+lv; + osg::Vec3 lp = _camera->getCenterPoint()+lv; - _camera->setView(ep,lp,uv); - _camera->ensureOrthogonalUpVector(); + _camera->setLookAt(ep,lp,uv); + _camera->ensureOrthogonalUpVector(); } - - return true; } diff --git a/src/osgUtil/FlightManipulator.cpp b/src/osgUtil/FlightManipulator.cpp index 25d3eab36..cfdacdfeb 100644 --- a/src/osgUtil/FlightManipulator.cpp +++ b/src/osgUtil/FlightManipulator.cpp @@ -1,5 +1,6 @@ -#include "osgUtil/FlightManipulator" -#include "osg/Notify" +#include +#include +#include using namespace osg; using namespace osgUtil; @@ -11,140 +12,150 @@ FlightManipulator::FlightManipulator() _yawMode = YAW_AUTOMATICALLY_WHEN_BANKED; } + FlightManipulator::~FlightManipulator() { } + void FlightManipulator::setNode(osg::Node* node) { _node = node; if (_node.get()) { - const osg::BoundingSphere& boundingSphere=_node->getBound(); + const osg::BoundingSphere& boundingSphere=_node->getBound(); _modelScale = boundingSphere._radius; } } -osg::Node* FlightManipulator::getNode() const + +const osg::Node* FlightManipulator::getNode() const { return _node.get(); } -void FlightManipulator::home(GUIEventAdapter& ea,GUIActionAdapter& us) + +void FlightManipulator::home(const GUIEventAdapter& ea,GUIActionAdapter& us) { if(_node.get() && _camera.get()) { - const osg::BoundingSphere& boundingSphere=_node->getBound(); + const osg::BoundingSphere& boundingSphere=_node->getBound(); + + _camera->setLookAt( + boundingSphere._center+osg::Vec3( 0.0,-2.0f * boundingSphere._radius,0.0f), + boundingSphere._center, + osg::Vec3(0.0f,0.0f,1.0f)); - _camera->setView(boundingSphere._center+osg::Vec3( 0.0,-2.0f * boundingSphere._radius,0.0f), // eye - boundingSphere._center, // look - osg::Vec3(0.0f,0.0f,1.0f)); // up - _velocity = 0.0f; - us.needRedraw(); + us.requestRedraw(); - us.needWarpPointer((ea.getXmin()+ea.getXmax())/2,(ea.getYmin()+ea.getYmax())/2); + us.requestWarpPointer((ea.getXmin()+ea.getXmax())/2,(ea.getYmin()+ea.getYmax())/2); flushMouseEventStack(); } - + } -void FlightManipulator::init(GUIEventAdapter& ea,GUIActionAdapter& us) + +void FlightManipulator::init(const GUIEventAdapter& ea,GUIActionAdapter& us) { flushMouseEventStack(); - us.needContinuousUpdate(false); + us.requestContinuousUpdate(false); _velocity = 0.0f; - us.needWarpPointer((ea.getXmin()+ea.getXmax())/2,(ea.getYmin()+ea.getYmax())/2); + us.requestWarpPointer((ea.getXmin()+ea.getXmax())/2,(ea.getYmin()+ea.getYmax())/2); } -bool FlightManipulator::update(GUIEventAdapter& ea,GUIActionAdapter& us) + +bool FlightManipulator::handle(const GUIEventAdapter& ea,GUIActionAdapter& us) { if(!_camera.get()) return false; - + switch(ea.getEventType()) { - case(GUIEventAdapter::PUSH): + case(GUIEventAdapter::PUSH): { - + addMouseEvent(ea); - us.needContinuousUpdate(true); - if (calcMovement()) us.needRedraw(); + us.requestContinuousUpdate(true); + if (calcMovement()) us.requestRedraw(); } return true; - case(GUIEventAdapter::RELEASE): + case(GUIEventAdapter::RELEASE): { - + addMouseEvent(ea); - us.needContinuousUpdate(true); - if (calcMovement()) us.needRedraw(); + us.requestContinuousUpdate(true); + if (calcMovement()) us.requestRedraw(); } return true; - case(GUIEventAdapter::DRAG): + case(GUIEventAdapter::DRAG): { - + addMouseEvent(ea); - us.needContinuousUpdate(true); - if (calcMovement()) us.needRedraw(); + us.requestContinuousUpdate(true); + if (calcMovement()) us.requestRedraw(); } return true; - case(GUIEventAdapter::MOVE): + case(GUIEventAdapter::MOVE): { - + addMouseEvent(ea); - us.needContinuousUpdate(true); - if (calcMovement()) us.needRedraw(); + us.requestContinuousUpdate(true); + if (calcMovement()) us.requestRedraw(); } return true; - case(GUIEventAdapter::KEYBOARD): - if (ea.getKey()==' ') - { - flushMouseEventStack(); - home(ea,us); - us.needRedraw(); - us.needContinuousUpdate(false); + case(GUIEventAdapter::KEYBOARD): + if (ea.getKey()==' ') + { + flushMouseEventStack(); + home(ea,us); + us.requestRedraw(); + us.requestContinuousUpdate(false); + return true; + } + return false; + case(GUIEventAdapter::FRAME): + addMouseEvent(ea); + if (calcMovement()) us.requestRedraw(); return true; - } - return false; - case(GUIEventAdapter::FRAME): - addMouseEvent(ea); - if (calcMovement()) us.needRedraw(); - return true; - case(GUIEventAdapter::RESIZE): + case(GUIEventAdapter::RESIZE): { init(ea,us); - us.needRedraw(); + us.requestRedraw(); } return true; - default: - return false; + default: + return false; } } + void FlightManipulator::flushMouseEventStack() { _ga_t1 = NULL; _ga_t0 = NULL; } -void FlightManipulator::addMouseEvent(GUIEventAdapter& ea) + +void FlightManipulator::addMouseEvent(const GUIEventAdapter& ea) { _ga_t1 = _ga_t0; _ga_t0 = &ea; } + bool FlightManipulator::calcMovement() { // return if less then two events have been added. @@ -152,11 +163,10 @@ bool FlightManipulator::calcMovement() float dt = _ga_t0->time()-_ga_t1->time(); - if (dt<0.0f) { - notify(WARN) << "warning dt = "<unref(); if (_inverse) _inverse->unref(); - for(SegList::iterator itr=_segList.begin(); - itr!=_segList.end(); - ++itr) + for(LineSegmentList::iterator itr=_segList.begin(); + itr!=_segList.end(); + ++itr) { itr->first->unref(); itr->second->unref(); @@ -40,40 +41,42 @@ IntersectState::~IntersectState() _inverse = (osg::Matrix *)0xffffffff; } -bool IntersectState::isCulled(const BoundingSphere& bs,SegmentMask& segMaskOut) + +bool IntersectState::isCulled(const BoundingSphere& bs,LineSegmentmentMask& segMaskOut) { bool hit = false; - SegmentMask mask = 0x00000001; + LineSegmentmentMask mask = 0x00000001; segMaskOut = 0x00000000; - SegmentMask segMaskIn = _segmentMaskStack.back(); -// notify(INFO) << << "IntersectState::isCulled() mask in "<second)->intersect(bs)) + if ((segMaskIn & mask) && (sitr->second)->intersect(bs)) { -// notify(INFO) << << "Hit "; + // notify(INFO) << << "Hit "; segMaskOut = segMaskOut| mask; hit = true; } mask = mask << 1; } -// notify(INFO) << << "mask = "<unref(); + // IntersectState* pvs = _intersectStateStack.back().get(); + // pvs->unref(); _intersectStateStack.pop_back(); } -// notify(INFO) << << "IntersectVisitor::popMatrix()"<isCulled(bs,sm)) return false; cis->_segmentMaskStack.push_back(sm); _nodePath.push_back(&node); @@ -304,24 +312,27 @@ bool IntersectVisitor::enterNode(Node& node) } } + void IntersectVisitor::leaveNode() { - IntersectState* cis = _intersectStateStack.back(); + IntersectState* cis = _intersectStateStack.back().get(); cis->_segmentMaskStack.pop_back(); } + void IntersectVisitor::apply(Node& node) { if (!enterNode(node)) return; - + traverse(node); leaveNode(); } + struct TriangleIntersect { - Seg _seg; + LineSegment _seg; Vec3 _s; Vec3 _d; @@ -333,9 +344,8 @@ struct TriangleIntersect typedef std::multimap > TriangleHitList; TriangleHitList _thl; - - TriangleIntersect(const Seg& seg,float ratio=FLT_MAX) + TriangleIntersect(const LineSegment& seg,float ratio=FLT_MAX) { _seg=seg; _hit=false; @@ -348,19 +358,19 @@ struct TriangleIntersect _d /= _length; } - -// void operator () (const Vec3& v1,const Vec3& v2,const Vec3& v3) -// { -// float r; -// if (_seg.intersect(v1,v2,v3,r)) -// { -// _thl.insert(std::pair(r,_index)); -// _hit = true; -// } -// ++_index; -// } -// bool intersect(const Vec3& v1,const Vec3& v2,const Vec3& v3,float& r) + // void operator () (const Vec3& v1,const Vec3& v2,const Vec3& v3) + // { + // float r; + // if (_seg.intersect(v1,v2,v3,r)) + // { + // _thl.insert(std::pair(r,_index)); + // _hit = true; + // } + // ++_index; + // } + + // bool intersect(const Vec3& v1,const Vec3& v2,const Vec3& v3,float& r) void operator () (const Vec3& v1,const Vec3& v2,const Vec3& v3) { ++_index; @@ -376,13 +386,12 @@ struct TriangleIntersect if (ds12<0.0f) return; if (ds12>d312) return; } - else // d312 < 0 + else // d312 < 0 { if (ds12>0.0f) return; if (ds12d123) return; } - else // d123 < 0 + else // d123 < 0 { if (ds23>0.0f) return; if (ds23d231) return; } - else // d231 < 0 + else // d231 < 0 { if (ds31>0.0f) return; if (ds31_length) return; @@ -433,28 +440,26 @@ struct TriangleIntersect float r = d/_length; - _thl.insert(std::pair > - (r,std::pair(_index-1,normal))); + _thl.insert(std::pair > (r,std::pair(_index-1,normal))); _hit = true; } - }; bool IntersectVisitor::intersect(GeoSet& gset) { bool hitFlag = false; - IntersectState* cis = _intersectStateStack.back(); + IntersectState* cis = _intersectStateStack.back().get(); const BoundingBox& bb = gset.getBound(); - for(IntersectState::SegList::iterator sitr=cis->_segList.begin(); - sitr!=cis->_segList.end(); - ++sitr) + for(IntersectState::LineSegmentList::iterator sitr=cis->_segList.begin(); + sitr!=cis->_segList.end(); + ++sitr) { - if (sitr->second->intersect(bb)) + if (sitr->second->intersect(bb)) { TriangleIntersect ti(*sitr->second); for_each_triangle(gset,ti); @@ -462,8 +467,8 @@ bool IntersectVisitor::intersect(GeoSet& gset) { for(TriangleIntersect::TriangleHitList::iterator thitr=ti._thl.begin(); - thitr!=ti._thl.end(); - ++thitr) + thitr!=ti._thl.end(); + ++thitr) { Hit hit; hit._nodePath = _nodePath; @@ -475,26 +480,26 @@ bool IntersectVisitor::intersect(GeoSet& gset) hit._ratio = thitr->first; hit._primitiveIndex = thitr->second.first; - hit._originalSeg = sitr->first; - if (hit._originalSeg) hit._originalSeg->ref(); - hit._localSeg = sitr->second; - if (hit._localSeg) hit._localSeg->ref(); + hit._originalLineSegment = sitr->first; + if (hit._originalLineSegment) hit._originalLineSegment->ref(); + hit._localLineSegment = sitr->second; + if (hit._localLineSegment) hit._localLineSegment->ref(); hit._intersectPoint = sitr->second->start()*(1.0f-hit._ratio)+ - sitr->second->end()*hit._ratio; - + sitr->second->end()*hit._ratio; + hit._intersectNormal = thitr->second.second; -// _segHitList[sitr->first].insert(hit); + // _segHitList[sitr->first].insert(hit); _segHitList[sitr->first].push_back(hit); - std::sort(_segHitList[sitr->first].begin(),_segHitList[sitr->first].end()); + std::sort(_segHitList[sitr->first].begin(),_segHitList[sitr->first].end()); hitFlag = true; } } } -// else notify(INFO) << << "no BB hit"<(geode.getDrawable(i)); + if (gset) intersect(*gset); } - + leaveNode(); } + void IntersectVisitor::apply(Billboard& node) { if (!enterNode(node)) return; -// Vec3 eye_local = getEyeLocal(); -// for(int i=0;imult(local_mat,*(currMatrix)); -// } -// else -// { -// matrix = new Matrix(local_mat); -// } -// -// matrix->ref(); -// matrix->unref(); -// -// } + // Vec3 eye_local = getEyeLocal(); + // for(int i=0;imult(local_mat,*(currMatrix)); + // } + // else + // { + // matrix = new Matrix(local_mat); + // } + // + // matrix->ref(); + // matrix->unref(); + // + // } leaveNode(); } + void IntersectVisitor::apply(Group& node) { if (!enterNode(node)) return; - + traverse(node); leaveNode(); } -void IntersectVisitor::apply(DCS& node) + +void IntersectVisitor::apply(Transform& node) { if (!enterNode(node)) return; - - pushMatrix(*node.getMatrix()); + + pushMatrix(node.getMatrix()); traverse(node); @@ -583,9 +589,3 @@ void IntersectVisitor::apply(LOD& node) { apply((Group&)node); } - - -void IntersectVisitor::apply(Scene& node) -{ - apply((Group&)node); -} diff --git a/src/osgUtil/Makefile b/src/osgUtil/Makefile index 197a78490..7093a4b4f 100644 --- a/src/osgUtil/Makefile +++ b/src/osgUtil/Makefile @@ -2,21 +2,37 @@ include ../../Make/makedefs C++FILES = \ - DisplayListVisitor.cpp\ - RenderVisitor.cpp\ - SceneView.cpp\ + CameraManipulator.cpp\ + CullVisitor.cpp\ + CullViewState.cpp\ + DisplayListVisitor.cpp\ + DepthSortedBin.cpp\ + DriveManipulator.cpp\ + FlightManipulator.cpp\ IntersectVisitor.cpp\ - CameraManipulator.cpp\ + InsertImpostorsVisitor.cpp\ + NvTriStripObjects.cpp\ + RenderBin.cpp\ + RenderGraph.cpp\ + RenderLeaf.cpp\ + RenderStage.cpp\ + RenderStageLighting.cpp\ + RenderToTextureStage.cpp\ + SceneView.cpp\ + SceneViewManipulator.cpp\ + SmoothingVisitor.cpp\ + StateSetManipulator.cpp\ + Tesselator.cpp\ TrackballManipulator.cpp\ - FlightManipulator.cpp\ - DriveManipulator.cpp\ + TriStripVisitor.cpp\ Version.cpp\ + VisualsRequirementsVisitor.cpp\ TARGET_BASENAME = osgUtil -LIBS = -ldl +LIBS = -L../../lib -losg -lGLU -lGL -lm LIB = ../../lib/lib$(TARGET_BASENAME).so #LIB = ../../lib/lib$(TARGET_BASENAME).a @@ -24,17 +40,34 @@ LIB = ../../lib/lib$(TARGET_BASENAME).so TARGET_LIB_FILES = lib$(TARGET_BASENAME).so TARGET_INCLUDE_FILES = \ osgUtil/CameraManipulator\ + osgUtil/CullVisitor\ + osgUtil/CullViewState\ + osgUtil/DepthSortedBin\ osgUtil/DisplayListVisitor\ osgUtil/DriveManipulator\ osgUtil/Export\ + osgUtil/FlightManipulator\ osgUtil/GUIActionAdapter\ osgUtil/GUIEventAdapter\ + osgUtil/GUIEventHandler\ osgUtil/IntersectVisitor\ - osgUtil/RenderVisitor\ + osgUtil/InsertImpostorsVisitor\ + osgUtil/RenderBin\ + osgUtil/RenderGraph\ + osgUtil/RenderLeaf\ + osgUtil/RenderStage\ + osgUtil/RenderStageLighting\ + osgUtil/RenderToTextureStage\ osgUtil/SceneView\ + osgUtil/SceneViewManipulator\ + osgUtil/SmoothingVisitor\ + osgUtil/StateSetManipulator\ + osgUtil/Statistics\ + osgUtil/Tesselator\ osgUtil/TrackballManipulator\ - osgUtil/FlightManipulator\ + osgUtil/TriStripVisitor\ osgUtil/Version\ + osgUtil/VisualsRequirementsVisitor\ C++FLAGS += -I ../../include diff --git a/src/osgUtil/SceneView.cpp b/src/osgUtil/SceneView.cpp index 95e6e069c..b0ea80398 100644 --- a/src/osgUtil/SceneView.cpp +++ b/src/osgUtil/SceneView.cpp @@ -1,5 +1,11 @@ -#include "osgUtil/SceneView" -#include "osg/Notify" +#include + +#include +#include +#include +#include + +#include using namespace osg; using namespace osgUtil; @@ -12,152 +18,225 @@ SceneView::SceneView() _near_plane = 1.0f; _far_plane = 1.0f; - + _lodBias = 1.0f; _lightingMode=HEADLIGHT; + + _prioritizeTextures = false; + + _view[0] = 0; + _view[1] = 0; + _view[2] = 1024; + _view[3] = 768; + + _frameNumber = 0; + } + SceneView::~SceneView() { } + void SceneView::setDefaults() { - _globalState = new osg::GeoState; + _globalState = new osg::StateSet; _lightingMode=HEADLIGHT; _light = new osg::Light; + _light->setAmbient(Vec4(0.05f,0.05f,0.05f,1.0f)); + _light->setDiffuse(Vec4(0.8f,0.8f,0.8f,1.0f)); + _light->setSpecular(Vec4(0.1f,0.1f,0.1f,1.0f)); + + _camera = new osg::Camera; - - _renderVisitor = new osgUtil::RenderVisitor; + _state = new osg::State; + + _rendergraph = new osgUtil::RenderGraph; + _renderStage = new osgUtil::RenderStage; + _cullVisitor = new osgUtil::CullVisitor; + + _cullVisitor->setRenderGraph(_rendergraph.get()); + _cullVisitor->setRenderStage(_renderStage.get()); + _globalState->setGlobalDefaults(); - _globalState->setMode(osg::GeoState::LIGHTING, osg::GeoState::ON); + + // enable lighting by default. + _globalState->setMode(GL_LIGHTING, osg::StateAttribute::ON); + + // enable depth testing by default. + _globalState->setMode(GL_DEPTH_TEST, osg::StateAttribute::ON); + + // set up an alphafunc by default to speed up blending operations. + osg::AlphaFunc* alphafunc = new osg::AlphaFunc(); + alphafunc->setFunction(osg::AlphaFunc::GREATER,0.0f); + _globalState->setAttributeAndModes(alphafunc, osg::StateAttribute::ON); + + // set up an alphafunc by default to speed up blending operations. + osg::TexEnv* texenv = new osg::TexEnv(); + texenv->setMode(osg::TexEnv::MODULATE); + _globalState->setAttributeAndModes(texenv, osg::StateAttribute::ON); _backgroundColor.set(0.2f, 0.2f, 0.4f, 1.0f); } +void SceneView::app() +{ + ++_frameNumber; + + if (_sceneData.valid() && _appVisitor.valid()) + { + _appVisitor->reset(); + _sceneData->accept(*_appVisitor.get()); + } +} + void SceneView::cull() { - if (!_renderVisitor) return; if (!_sceneData) return; - - _camera->setAspectRatio((GLfloat)_view[2]/(GLfloat) _view[3]); - _renderVisitor->reset(); + _camera->adjustAspectRatio((GLfloat)_view[2]/(GLfloat) _view[3]); - _renderVisitor->setGlobalState(_globalState.get()); - _renderVisitor->setLODBias(_lodBias); -// _renderVisitor->setPerspective(60.0f, (GLfloat)_view[2]/(GLfloat) _view[3], _near_plane, _far_plane ); - _renderVisitor->setPerspective(*_camera); - _renderVisitor->setLookAt(*_camera); + + _rendergraph->clean(); - _sceneData->accept(*_renderVisitor); + _cullVisitor->reset(); + + // comment out reset of rendergraph since clean is more efficient. + // _rendergraph->reset(); + + // use clean of the rendergraph rather than reset, as it is able to + // reuse the structure on the rendergraph in the next frame. This + // achieves a certain amount of frame cohereancy of memory allocation. + + _cullVisitor->setFrameNumber(_frameNumber); + _cullVisitor->setLODBias(_lodBias); + _cullVisitor->setCamera(*_camera); + _cullVisitor->setViewport(_view[0],_view[1],_view[2],_view[3]); + + _renderStage->reset(); + + _renderStage->setViewport(_view[0],_view[1],_view[2],_view[3]); + _renderStage->setCamera(_camera.get()); + _renderStage->setClearColor(_backgroundColor); + _renderStage->setLight(_light.get()); + + + switch(_lightingMode) + { + case(HEADLIGHT): + _renderStage->setLightingMode(RenderStageLighting::HEADLIGHT); + break; + case(SKY_LIGHT): + _renderStage->setLightingMode(RenderStageLighting::SKY_LIGHT); + break; + case(NO_SCENEVIEW_LIGHT): + _renderStage->setLightingMode(RenderStageLighting::NO_SCENEVIEW_LIGHT); + break; + } + + if (_globalState.valid()) _cullVisitor->pushStateSet(_globalState.get()); + + + // traverse the scene graph to generate the rendergraph. + _sceneData->accept(*_cullVisitor); + + if (_globalState.valid()) _cullVisitor->popStateSet(); + + + // do any state sorting required. + _renderStage->sort(); + + + // prune out any empty RenderGraph children. + // note, this would be not required if the _renderGraph had been + // reset at the start of each frame (see top of this method) but + // a clean has been used instead to try to minimize the amount of + // allocation and deleteing of the RenderGraph nodes. + _rendergraph->prune(); if (_calc_nearfar) { - if (_renderVisitor->calcNearFar(_near_plane,_far_plane)) - { - // shift the far plane slight further away from the eye point. - // and shift the near plane slightly near the eye point, this - // will give a little space betwenn the near and far planes - // and the model, crucial when the naer and far planes are - // coincedent. - _far_plane *= 1.05; - _near_plane *= 0.95; + _near_plane = _cullVisitor->getCalculatedNearPlane(); + _far_plane = _cullVisitor->getCalculatedFarPlane(); - // if required clamp the near plane to prevent negative or near zero - // near planes. - float min_near_plane = _far_plane*0.0005f; - if (_near_planesetNearPlane(_near_plane); - _camera->setFarPlane(_far_plane); + // if required clamp the near plane to prevent negative or near zero + // near planes. + float min_near_plane = _far_plane*0.0005f; + if (_near_planesetNearFar(_near_plane,_far_plane); } + } - + + void SceneView::draw() { - if (!_renderVisitor) return; if (!_sceneData) return; - glViewport( _view[0], _view[1], _view[2], _view[3] ); - - glEnable( GL_DEPTH_TEST ); - - glClearColor( _backgroundColor[0], _backgroundColor[1], _backgroundColor[2], _backgroundColor[3]); - - glClear( GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT ); - -// glMatrixMode( GL_PROJECTION ); -// glLoadIdentity(); -// gluPerspective( 60.0f, (GLfloat)_view[2]/(GLfloat) _view[3], _near_plane, _far_plane ); - - _camera->draw_PROJECTION(); - - glMatrixMode( GL_MODELVIEW ); - glLoadIdentity(); - - if (_lightingMode==HEADLIGHT) + if (!_state) { - _light->apply(); - } + osg::notify(osg::WARN) << "Warning: no valid osgUtil::SceneView::_state"<draw_MODELVIEW(); + // note the constructor for osg::State will set ContextID to 0. + _state = new osg::State; + } + // we in theory should be able to + _state->reset(); + + // note, to support multi-pipe systems the deletion of OpenGL display list + // and texture objects is deferred until the OpenGL context is the correct + // context for when the object were originally created. Here we know what + // context we are in so can flush the appropriate caches. + osg::Drawable::flushDeletedDisplayLists(_state->getContextID()); + osg::Texture::flushDeletedTextureObjects(_state->getContextID()); + + RenderLeaf* previous = NULL; + _renderStage->draw(*_state,previous); -// gluLookAt( _camera->getEyePoint().x(), _camera->getEyePoint().y(), _camera->getEyePoint().z(), -// _camera->getLookPoint().x(), _camera->getLookPoint().y(), _camera->getLookPoint().z(), -// _camera->getUpVector().x(), _camera->getUpVector().y(), _camera->getUpVector().z()); - - if (_lightingMode==SKY_LIGHT) + GLenum errorNo = glGetError(); + if (errorNo!=GL_NO_ERROR) { - _light->apply(); + osg::notify(WARN)<<"Warning: detected OpenGL error '"<render(); - - + } + /** Calculate, via glUnProject, the object coordinates of a window point. Note, current implementation requires that SceneView::draw() has been previously called for projectWindowIntoObject to produce valid values. As per OpenGL windows coordinates are calculated relative to the bottom left of the window.*/ bool SceneView::projectWindowIntoObject(const osg::Vec3& window,osg::Vec3& object) const { - GLdouble sX,sY,sZ; - GLint result_start = gluUnProject((GLdouble)window[0],(GLdouble)window[1],(GLdouble)window[2], - _model,_proj,_view, - &sX,&sY,&sZ); - if (result_start) - { - object.set(sX,sY,sZ); - return true; - } - else - { - return false; - } + return _camera->unproject(window,_view,object); } + /** Calculate, via glUnProject, the object coordinates of a window x,y when projected onto the near and far planes. Note, current implementation requires that SceneView::draw() has been previously called @@ -165,44 +244,17 @@ bool SceneView::projectWindowIntoObject(const osg::Vec3& window,osg::Vec3& objec windows coordinates are calculated relative to the bottom left of the window.*/ bool SceneView::projectWindowXYIntoObject(int x,int y,osg::Vec3& near_point,osg::Vec3& far_point) const { - GLdouble nX,nY,nZ; - GLint result_near = gluUnProject((GLdouble)x,(GLdouble)y,(GLdouble)0.0, - _model,_proj,_view, - &nX,&nY,&nZ); - - - if (result_near==0) return false; - - GLdouble fX,fY,fZ; - GLint result_far = gluUnProject((GLdouble)x,(GLdouble)y,(GLdouble)1.0, - _model,_proj,_view, - &fX,&fY,&fZ); - - if (result_far==0) return false; - - near_point.set(nX,nY,nZ); - far_point.set(fX,fY,fZ); - - return true; + bool result_near = _camera->unproject(Vec3(x,y,0.0f),_view,near_point); + bool result_far = _camera->unproject(Vec3(x,y,1.0f),_view,far_point); + return result_near & result_far; } + /** Calculate, via glProject, the object coordinates of a window. Note, current implementation requires that SceneView::draw() has been previously called for projectWindowIntoObject to produce valid values. As per OpenGL windows coordinates are calculated relative to the bottom left of the window.*/ bool SceneView::projectObjectIntoWindow(const osg::Vec3& object,osg::Vec3& window) const { - GLdouble sX,sY,sZ; - GLint result_start = gluProject((GLdouble)object[0],(GLdouble)object[1],(GLdouble)object[2], - _model,_proj,_view, - &sX,&sY,&sZ); - if (result_start) - { - window.set(sX,sY,sZ); - return true; - } - else - { - return false; - } + return _camera->project(object,_view,window); } diff --git a/src/osgUtil/TrackballManipulator.cpp b/src/osgUtil/TrackballManipulator.cpp index aabd23ca4..919b21064 100644 --- a/src/osgUtil/TrackballManipulator.cpp +++ b/src/osgUtil/TrackballManipulator.cpp @@ -1,5 +1,6 @@ -#include "osgUtil/TrackballManipulator" -#include "osg/Notify" +#include +#include +#include using namespace osg; using namespace osgUtil; @@ -11,71 +12,79 @@ TrackballManipulator::TrackballManipulator() _thrown = false; } + TrackballManipulator::~TrackballManipulator() { } + void TrackballManipulator::setNode(osg::Node* node) { _node = node; if (_node.get()) { - const osg::BoundingSphere& boundingSphere=_node->getBound(); + const osg::BoundingSphere& boundingSphere=_node->getBound(); _modelScale = boundingSphere._radius; } } -osg::Node* TrackballManipulator::getNode() const + +const osg::Node* TrackballManipulator::getNode() const { return _node.get(); } -void TrackballManipulator::home(GUIEventAdapter& /*ea*/,GUIActionAdapter& us) + + /*ea*/ +void TrackballManipulator::home(const GUIEventAdapter& ,GUIActionAdapter& us) { if(_node.get() && _camera.get()) { - const osg::BoundingSphere& boundingSphere=_node->getBound(); + const osg::BoundingSphere& boundingSphere=_node->getBound(); - _camera->setView(boundingSphere._center+osg::Vec3( 0.0,-2.0f * boundingSphere._radius,0.0f), // eye - boundingSphere._center, // look - osg::Vec3(0.0f,0.0f,1.0f)); // up - - us.needRedraw(); + _camera->setView(boundingSphere._center+osg::Vec3( 0.0,-2.0f * boundingSphere._radius,0.0f), + boundingSphere._center, + osg::Vec3(0.0f,0.0f,1.0f)); + + us.requestRedraw(); } - + } -void TrackballManipulator::init(GUIEventAdapter& /*ea*/,GUIActionAdapter& /*us*/) + +void TrackballManipulator::init(const GUIEventAdapter& ,GUIActionAdapter& ) { flushMouseEventStack(); } -bool TrackballManipulator::update(GUIEventAdapter& ea,GUIActionAdapter& us) + +bool TrackballManipulator::handle(const GUIEventAdapter& ea,GUIActionAdapter& us) { if(!_camera.get()) return false; - + switch(ea.getEventType()) { - case(GUIEventAdapter::PUSH): + case(GUIEventAdapter::PUSH): { flushMouseEventStack(); addMouseEvent(ea); - if (calcMovement()) us.needRedraw(); - us.needContinuousUpdate(false); + if (calcMovement()) us.requestRedraw(); + us.requestContinuousUpdate(false); _thrown = false; } return true; - case(GUIEventAdapter::RELEASE): + case(GUIEventAdapter::RELEASE): { - if (ea.getButtonMask()==0) { + if (ea.getButtonMask()==0) + { if (isMouseMoving()) { if (calcMovement()) { - us.needRedraw(); - us.needContinuousUpdate(true); + us.requestRedraw(); + us.requestContinuousUpdate(true); _thrown = true; } } @@ -83,8 +92,8 @@ bool TrackballManipulator::update(GUIEventAdapter& ea,GUIActionAdapter& us) { flushMouseEventStack(); addMouseEvent(ea); - if (calcMovement()) us.needRedraw(); - us.needContinuousUpdate(false); + if (calcMovement()) us.requestRedraw(); + us.requestContinuousUpdate(false); _thrown = false; } @@ -93,47 +102,48 @@ bool TrackballManipulator::update(GUIEventAdapter& ea,GUIActionAdapter& us) { flushMouseEventStack(); addMouseEvent(ea); - if (calcMovement()) us.needRedraw(); - us.needContinuousUpdate(false); + if (calcMovement()) us.requestRedraw(); + us.requestContinuousUpdate(false); _thrown = false; } } return true; - case(GUIEventAdapter::DRAG): + case(GUIEventAdapter::DRAG): { addMouseEvent(ea); - if (calcMovement()) us.needRedraw(); - us.needContinuousUpdate(false); + if (calcMovement()) us.requestRedraw(); + us.requestContinuousUpdate(false); _thrown = false; } return true; - case(GUIEventAdapter::MOVE): + case(GUIEventAdapter::MOVE): { } return false; - case(GUIEventAdapter::KEYBOARD): - if (ea.getKey()==' ') - { - flushMouseEventStack(); - _thrown = false; - home(ea,us); - us.needRedraw(); - us.needContinuousUpdate(false); - return true; - } - return false; - case(GUIEventAdapter::FRAME): - if (_thrown) - { - if (calcMovement()) us.needRedraw(); - return true; - } - return false; - default: - return false; + case(GUIEventAdapter::KEYBOARD): + if (ea.getKey()==' ') + { + flushMouseEventStack(); + _thrown = false; + home(ea,us); + us.requestRedraw(); + us.requestContinuousUpdate(false); + return true; + } + return false; + case(GUIEventAdapter::FRAME): + if (_thrown) + { + if (calcMovement()) us.requestRedraw(); + return true; + } + return false; + default: + return false; } } + bool TrackballManipulator::isMouseMoving() { if (_ga_t0.get()==NULL || _ga_t1.get()==NULL) return false; @@ -142,24 +152,27 @@ bool TrackballManipulator::isMouseMoving() float dx = _ga_t0->getX()-_ga_t1->getX(); float dy = _ga_t0->getY()-_ga_t1->getY(); - float len = sqrtf(dx*dx+dy*dy); + float len = sqrtf(dx*dx+dy*dy); float dt = _ga_t0->time()-_ga_t1->time(); return (len>dt*velocity); } + void TrackballManipulator::flushMouseEventStack() { _ga_t1 = NULL; _ga_t0 = NULL; } -void TrackballManipulator::addMouseEvent(GUIEventAdapter& ea) + +void TrackballManipulator::addMouseEvent(const GUIEventAdapter& ea) { _ga_t1 = _ga_t0; _ga_t0 = &ea; } + bool TrackballManipulator::calcMovement() { // return if less then two events have been added. @@ -168,7 +181,6 @@ bool TrackballManipulator::calcMovement() float dx = dx = _ga_t0->getX()-_ga_t1->getX(); float dy = _ga_t0->getY()-_ga_t1->getY(); - // return if there is no movement. if (dx==0 && dy==0) return false; @@ -178,7 +190,7 @@ bool TrackballManipulator::calcMovement() // rotate camera. - osg::Vec3 center = _camera->getLookPoint(); + osg::Vec3 center = _camera->getCenterPoint(); osg::Vec3 axis; float angle; @@ -207,18 +219,18 @@ bool TrackballManipulator::calcMovement() mat.postRot(angle,axis.x(),axis.y(),axis.z()); mat.postTrans(center.x(),center.y(),center.z()); - _camera->mult(*_camera,mat); + _camera->transformLookAt(mat); return true; } - else if (buttonMask==GUIEventAdapter::MIDDLE_BUTTON || - buttonMask==(GUIEventAdapter::LEFT_BUTTON|GUIEventAdapter::RIGHT_BUTTON)) + else if (buttonMask==GUIEventAdapter::MIDDLE_BUTTON || + buttonMask==(GUIEventAdapter::LEFT_BUTTON|GUIEventAdapter::RIGHT_BUTTON)) { // pan model. - float scale = 0.0015f*_camera->getFocalDistance(); + float scale = 0.0015f*_camera->getFocalLength(); osg::Vec3 uv = _camera->getUpVector(); osg::Vec3 sv = _camera->getSideVector(); @@ -227,8 +239,8 @@ bool TrackballManipulator::calcMovement() osg::Matrix mat; mat.makeTrans(dv.x(),dv.y(),dv.z()); - _camera->mult(*_camera,mat); - + _camera->transformLookAt(mat); + return true; } @@ -237,43 +249,44 @@ bool TrackballManipulator::calcMovement() // zoom model. - float fd = _camera->getFocalDistance(); + float fd = _camera->getFocalLength(); float scale = 1.0f-dy*0.001f; if (fd*scale>_modelScale*_minimumZoomScale) { // zoom camera in. - osg::Vec3 center = _camera->getLookPoint(); + osg::Vec3 center = _camera->getCenterPoint(); osg::Matrix mat; mat.makeTrans(-center.x(),-center.y(),-center.z()); mat.postScale(scale,scale,scale); mat.postTrans(center.x(),center.y(),center.z()); - _camera->mult(*_camera,mat); + _camera->transformLookAt(mat); } - else + else { -// notify(DEBUG) << "Pushing forward"<getLookVector()*(dy*scale); - + osg::Matrix mat; mat.makeTrans(dv.x(),dv.y(),dv.z()); - _camera->mult(*_camera,mat); + _camera->transformLookAt(mat); } return true; } - + return false; } + /* * This size should really be based on the distance from the center of * rotation to the point on the object underneath the mouse. That @@ -329,6 +342,7 @@ void TrackballManipulator::trackball(osg::Vec3& axis,float& angle, float p1x, fl } + /* * Project an x,y pair onto a sphere of radius r OR a hyperbolic sheet * if we are away from the center of the sphere. @@ -338,9 +352,13 @@ float TrackballManipulator::tb_project_to_sphere(float r, float x, float y) float d, t, z; d = sqrt(x*x + y*y); - if (d < r * 0.70710678118654752440) { /* Inside sphere */ + /* Inside sphere */ + if (d < r * 0.70710678118654752440) + { z = sqrt(r*r - d*d); - } else { /* On hyperbola */ + } /* On hyperbola */ + else + { t = r / 1.41421356237309504880; z = t*t / d; } diff --git a/src/osgUtil/Version.cpp b/src/osgUtil/Version.cpp index eec61a493..0a107b95a 100644 --- a/src/osgUtil/Version.cpp +++ b/src/osgUtil/Version.cpp @@ -1,11 +1,11 @@ #include "osgUtil/Version" - const char* osgUtilGetVersion() { - return "0.8.34"; + return "0.8.42"; } + const char* osgUtilGetLibraryName() { return "Open Scene Graph Utility Library"; diff --git a/src/osgWX/Makedepend b/src/osgWX/Makedepend new file mode 100644 index 000000000..e69de29bb diff --git a/src/osgWX/Makefile b/src/osgWX/Makefile new file mode 100644 index 000000000..245922022 --- /dev/null +++ b/src/osgWX/Makefile @@ -0,0 +1,24 @@ +#!smake +include ../../Make/makedefs + +C++FILES = \ + WXEventAdapter.cpp\ + Version.cpp\ + +TARGET_BASENAME = osgWX + +LIBS = -L../../lib -losgDB -losgUtil -losg $(WXLIB) -lGLU -lGL -lm + +LIB = ../../lib/lib$(TARGET_BASENAME).so +#LIB = ../../lib/lib$(TARGET_BASENAME).a + +TARGET_LIB_FILES = lib$(TARGET_BASENAME).so +TARGET_INCLUDE_FILES = \ + osgWX/Export\ + osgWX/WXEventAdapter\ + osgWX/Version\ + +C++FLAGS += -I ../../include `wx-config --cflags` + +include ../../Make/makerules + diff --git a/src/osgWX/Version.cpp b/src/osgWX/Version.cpp new file mode 100644 index 000000000..8bfe7066e --- /dev/null +++ b/src/osgWX/Version.cpp @@ -0,0 +1,12 @@ +#include "osgWX/Version" + +const char* osgWXGetVersion() +{ + return "0.8.42"; +} + + +const char* osgWXGetLibraryName() +{ + return "Open Scene Graph WX Library"; +} diff --git a/src/osgWX/WXEventAdapter.cpp b/src/osgWX/WXEventAdapter.cpp new file mode 100644 index 000000000..888052587 --- /dev/null +++ b/src/osgWX/WXEventAdapter.cpp @@ -0,0 +1,173 @@ +// +// class WXEventAdapter +// + +// For compilers that support precompilation, includes "wx.h". +#include "wx/wxprec.h" + +#ifndef WX_PRECOMP +#include "wx/wx.h" +#endif + +#include "osgWX/WXEventAdapter" + +using namespace osgWX; + +// default to no mouse buttons being pressed. +unsigned int WXEventAdapter::_s_accumulatedButtonMask = 0; + +int WXEventAdapter::_s_Xmin = 0; +int WXEventAdapter::_s_Xmax = 1280; +int WXEventAdapter::_s_Ymin = 0; +int WXEventAdapter::_s_Ymax = 1024; +int WXEventAdapter::_s_mx = 0; +int WXEventAdapter::_s_my = 0; + +WXEventAdapter::WXEventAdapter() +{ + _eventType = NONE; // adaptor does not encapsulate any events. + _key = -1; // set to 'invalid' key value. + _button = -1; // set to 'invalid' button value. + _mx = -1; // set to 'invalid' position value. + _my = -1; // set to 'invalid' position value. + _buttonMask = 0; // default to no mouse buttons being pressed. + _time = 0.0f; // default to no time has been set. + + copyStaticVariables(); +} + + +void WXEventAdapter::copyStaticVariables() +{ + _buttonMask = _s_accumulatedButtonMask; + _Xmin = _s_Xmin; + _Xmax = _s_Xmax; + _Ymin = _s_Ymin; + _Ymax = _s_Ymax; + _mx = _s_mx; + _my = _s_my; +} + + +void WXEventAdapter::setWindowSize(int Xmin, int Ymin, int Xmax, int Ymax) +{ + _s_Xmin = Xmin; + _s_Xmax = Xmax; + _s_Ymin = Ymin; + _s_Ymax = Ymax; +} + + +void WXEventAdapter::setButtonMask(unsigned int buttonMask) +{ + _s_accumulatedButtonMask = buttonMask; +} + + +void WXEventAdapter::adaptResize(float time, int Xmin, int Ymin, int Xmax, int Ymax) +{ + setWindowSize(Xmin,Ymin,Xmax,Ymax); + _eventType = RESIZE; + _time = time; + copyStaticVariables(); +} + + +/** method for adapting mouse motion events whilst mouse buttons are pressed.*/ +void WXEventAdapter::adaptMouseMotion(float time, int x, int y) +{ + _eventType = DRAG; + _time = time; + _s_mx = x; + _s_my = y; + copyStaticVariables(); +} + + +/** method for adapting mouse motion events whilst no mouse button are pressed.*/ +void WXEventAdapter::adaptMousePassiveMotion(float time, int x, int y) +{ + _eventType = MOVE; + _time = time; + _s_mx = x; + _s_my = y; + copyStaticVariables(); +} + + +/** method for adapting mouse button pressed/released events.*/ +void WXEventAdapter::adaptMouse(float time, wxMouseEvent *event) +{ + _time = time; + + wxEventType type = event->GetEventType(); + + if ( type == wxEVT_LEFT_DOWN ) { + _eventType = PUSH; + _s_accumulatedButtonMask = _s_accumulatedButtonMask | LEFT_BUTTON; + } + else if ( type == wxEVT_LEFT_UP ) { + _eventType = RELEASE; + _s_accumulatedButtonMask = _s_accumulatedButtonMask & ~LEFT_BUTTON; + } + else if ( type == wxEVT_MIDDLE_DOWN ) { + _eventType = PUSH; + _s_accumulatedButtonMask = _s_accumulatedButtonMask | MIDDLE_BUTTON; + } + else if ( type == wxEVT_MIDDLE_UP ) { + _eventType = RELEASE; + _s_accumulatedButtonMask = _s_accumulatedButtonMask & ~MIDDLE_BUTTON; + } + else if ( type == wxEVT_RIGHT_DOWN ) { + _eventType = PUSH; + _s_accumulatedButtonMask = _s_accumulatedButtonMask | RIGHT_BUTTON; + } + else if ( type == wxEVT_RIGHT_UP ) { + _eventType = RELEASE; + _s_accumulatedButtonMask = _s_accumulatedButtonMask & ~RIGHT_BUTTON; + } + else if ( type == wxEVT_MOTION ) { + if (event->ButtonIsDown(-1)) + _eventType = DRAG; + else + _eventType = MOVE; + } + else { + // ignored mouse events, such as wxEVT_LEAVE_WINDOW + return; + } + +#if 0 + // not yet handled: modifiers + if (event.ControlDown()) ...; + if (event.ShiftDown()) ...; +#endif + + _s_mx = event->GetX(); + _s_my = event->GetY(); + + copyStaticVariables(); +} + + +/** method for adapting keyboard events.*/ +void WXEventAdapter::adaptKeyboard(float time, unsigned char key, int x, int y ) +{ + _eventType = KEYBOARD; + _time = time; + _key = key; + _s_mx = x; + _s_my = y; + + copyStaticVariables(); +} + + +/** method for adapting frame events, i.e. iddle/display callback.*/ +void WXEventAdapter::adaptFrame(float time) +{ + _eventType = FRAME; + _time = time; + + copyStaticVariables(); +}