OpenGL has become a standard for rendering 3D graphics for visualization systems. It is valuable for establishing a standard API for graphics device drivers, but has limited scope for applications wanting to do large-scale visualization. OpenGL treats the 3D world as a set of graphics primitivesand rendering state. Primtives include triangles, triangle strips, lines, points and other low-level geometric shapes. Rendering state includes attributes such as the "current color", the "current texture", the "current polygonmode",. This are attributges that are applied to primitives during rendering.
A scene graph, however, treats the 3D world as a set of spatially coherent objects with position, size and bound in the virutal world. This allows the visual system to cull those components that are not visible within the current viewing frustum and provides methods to utilize system resources in a highly optimized way, allowing for visual databases of infinite size. The graph itself is a tree datastructure, which arranges objects heirarchically according to their bound within the virtual world, then providcs traversals of the tree that do varous jobs (such as cullling) to prepare the scene for rendering.
OpenSceneGraph provides the functionality to render the virtual world as a scene graph. This includes the scene graph itself, traversers, Drawables, State management, Linear algebra functions and supporting components. Drawables wrap OpenGL primitive rendering into a C++ class, which also provides information about geometry bound to the scene graph. State management is carried out through StateSets, which contain attributes and modes which map directly to OpenGL attributes and modes. StateSets are managed in context of the scene graph, however, and only applied when needed and after optimization. Linear algebra functions provide control of matrices, vectors and quaternions.
Before exploring how the Real-Time Terrain Deformation Software fits into the OpenSceneGraph architecture, it is beneficial to explain this architecture. This section discusses the architecture of OpenSceneGraph, its high level components and provides the background information for understanding how the Real-Time Terrain Deformation Software will fit into the existing architectures.
OpenSceneGraph consists of three major core modules, implemented as dynamic libraries: osg, osgUtil and osgDB.
Figure 1 - The OSG architecture
Core OSG module
The core OSG module contains
- The scene graph (tree structure)
- StateSets (OpenGL state attributes and modes)
- Drawables (OpenGL geometry)
- Linear Algebra functions (Vectors, Matrices, Quaternions)
- Supporting functions
The core osg module is intended to be a collection of those software components directly related to the scene graph itself,. It is not the intended location for traversers, or other utilities that operate on the scene graph, and is, in effect, a passive set of software that allows for management of geometry and state, primarily, but does not effect that management.
Core osgUtil moduleThe core osgUtil module consists of:
- Traversers (Update and Cull traversals, for example)
- Misc. scene graph operators
OsgUtil is designed to be the operations that use the scene graph. Osgutil itself does not contain software components of the scene graph, or its supporting structures.
Core osgDB moduleThe osgDB module contains
- The Plug-in registry
- Plug-in ReaderWriter super-class
- File system utilities
- The asynchonous Database pager
While a scene graph can be created programatically through the API provide in the core osg library, the most common way is to read a published file format, which can be converted internally to a scene graph. This is done through OSG plug-ins. OSG plug-ins exist as dynamically loadable modules, which are loaded and used when a particular file format is requested by the application. The plug-in, containing a derived osgDB::ReaderWriter class, then is invoked to parse the incoming file and provide an intact scene graph back to the application.
Plug-ins, automatically register with the osgDB plug-in registry upon loading, and may use many of the utility functions provided by osgDB to read files, find files, etc.
The asynchronous database pager allows an application to use an asynchonous thread for loading and modifying the scene graph at run-time. The Database pager's internal functionality manages existing database tiles, loads newly requested tiles and cleans up stale tiles.
Plug-insOSG contains a large number of plug-ins that allow the importation of many different file formats. For the purposes of this document, it should be stated that a plug-in for the OpenFlight file format exists and is quite functional.
Plug-ins may provide readers and/or writers, but commonly only provide readers. OSG's file format writers include the .osg plug-in, an ASCII file format native to OSG, and .ive, a binary file format.
Plug-ins are also used for reading image file formats, including rgb, tiff, jpg, bmp, png, dds, and many more.
It is also important to note here, for the purposes of this design document, that plug-ins may invoke other plug-ins.
Node-KitsNode kits are a collection of software that extend the basic functionality of the scene graph, its drawables, and its state attributes. Further, node- kits may extend the .osg file format. An example of a node kit is osgText, which extends the concept of a Drawable to a set of attributes that are peculiar to rendering text.
The Terrain Deformation Module will be implemented as an OSG plug-in. The plug-in will read two types of file formats: OpenFlight, for which it will invoke the OpenFlight plug-in, and Shape files. Upon invokation, the Terrain Deformation plug-in wil receive a file, or stream, which contains the names of any OpenFlight file, intended to be a model of the terrain, and the name of one shape file. The shape file will contain all of the information needed to rehape the terrain itself.
It is necessary to implement these two components tugether for coherence of the terrain module and the Shape file. Because of the nature of OSG plug-ins being dynamically loadable modules, the mecahinism needed to tie Shape file information to a global terrain module is unecessarily complicated. By combining the two in the same plug-in, terrain deformation can occur on a single instance of an OpenFlight database, and one instance of a ShapeFile.
This also allows for a "tiling" of a database intended for asynchronous paging. If tiles are comprised of OpenFlight terrain/Shapefile pairs, the asynchronous database pager may simply invoke the Terrain Deformation plug-in to load both the OpenFlight file and Shape file, then carry out the deformation of the terrain in real-time at load time.
Figure 2 - Terrain Deformation Plug-in Diagram
Figure 2 shows a high-level block diagram of the major components of the Terrain Deformation plug-in. The components of the plug-in are shown in the gray box. Procedurally, then the application (light blue) requests the loading of a 'tdef' file through the osgDB plug-in registry, or through the osgDB Database Pager through the PagedLOD mechanism. At this time the Terrain Deformation Plug-in is invoked by the run time, registers itself with the osgDB plug-in registry and its readnodeFile() method is invoked, passing in the name of the 'tdef' file.
A 'tdef' file scanner scans the input file for name/value pairs, and produce the name of an OpenFlight file containing the TerrainDatabase, and the name of a ShapeFile containing the objects for the TargetDatabase.
The TerrainDatabase is then loaded through the osgDB regisry and the OSG OpenFlight plug-in.
A ShapeFileParser then opens and scans the ShapeFile, producing a TargetDatabase. The TerrainDeformer is then passed the TerrainDatabase and the TargetDatabase and proceeds to alter the terrain, placing targets within the database and deforming the terrain to match the targets. It produces AlteredTerrain which is returned to the application.
Identification of ComponentsThe following components within the Terrain Deformation plug-in module are identified here.
'tdef' file scannerThe 'tdef' file scanner is a simple parser, that reads name/value pairs from a simple ASCII file. Names being scanned for are TerrainDatabaseFile and ShapeFile. The values are extracted and kept in the local scope.
PDL: OpenFile( 'tdef' filename ); ScanFile( out terrainDatabaseFilename, out shapeFilename ) CloseFile
ShapeFileParserThe ShapeFileParser parses an ESRI Shape file and produces a set of geometric target objects. The parser adheres to a format specification for the ESRI Shape File.
TerrainDeformerThe Terrain Deformer component will take as input, the Terrain Databaes and the Target Database and traverse the graph, identifying geometry on the Terrain Database that is affected by each target and is periphery. This component is the work-horse of the Terrain Deformation plug-in module and has complex tasks including:The TerrainDeformer then produces an altered database including targets and the deformed terrain.
- Identification of terrain types for affected geometry
- Identification of exception situations
- Identification of accumulated affected geometry
(for example, alteration of geometry for one target changes the algorithm for alteration of geometry for another target)
- Reforming of terrain geometry.
- Addition of Targets into deformed terrain geometry.
- Optimization of deformed terrain