Inventor contains mostly 3-D objects and their associated attributes: geometric shapes, colors, lights and 3-D object manipulators. These are rendered with OpenGL or a similar API, such as Brian Paul's Mesa (see Resources).
The Inventor Xt Component and Utility Library provides widgets and utilities for event handling, rendering, viewers and editors that can manipulate the scene graph directly. These events include selection, picking and highlighting of nodes, keyboard and mouse handling, and processing Xt and Motif callback functions.
For standard GUI design, we can resort to Motif (MFC under Windows NT/95), or whatever happens to be our favorite 2-D GUI API. The standard components such as the predefined viewer classes have been set up to make use of Motif and Xt under UNIX/Linux using the SoXt classes. These classes have been emulated under Windows, so that we have a somewhat easier time of porting code between platforms.
I find Motif to be a little cumbersome to program, so I've been using Viewkit, available from http://www.ics.com/, in conjunction with RapidApp running on Irix to build the GUI and generate the C++ code stubs. Viewkit is freely available for SGI and Linux workstations, and the RapidApp code compiles cleanly under Linux. The GUI could have been built by hand, totally under Linux, but it helps the design process to be able to work interactively. Also, building on both platforms may help to make sure that portability issues spring up earlier in the design process.
Motif is not an absolute prerequisite under UNIX. Mark J. Kilgard, of SGI until recently, illustrates using Open Inventor without Motif in his book Open GL Programming for the X Window System (see Resources).
Let's look at a quick illustration of how easy it is to set up a scene graph and viewer. Example 2-4 of The Inventor Mentor presents “Hello Cone” using a standard scene viewer. (See Figure 1.) The figure shows three main areas of the SceneViewer: three thumbwheels, eight side buttons and a render area.
The eight buttons handle object selection/picking, viewpoint manipulation, help, returning to home viewpoint, setting a new home viewpoint, executing viewAll to see the whole scene, seeking to a point and toggling the camera type between orthographic and perspective.
The three thumbwheels handle manipulation of the scene's viewpoint by rotating the camera angle about the X and Y axes and traversing along the Z axis to obtain a zoom effect.
The render area is the most interesting. The mouse can be used to get the same effect as the thumbwheels. Mouse button one will allow the user to select the object, and if the mouse is moving when it is released, the object will continue spinning in the direction that the mouse cursor was moving. Mouse button two will allow the user to pan up/down and left/right, and if the control key is pressed, zoom in and out. Mouse button three causes a pop-up menu to appear that allows the user to set various attributes (such as rendering “as-is”, hidden-line, wire frame, points-only and bounding box), preferences and displays of the thumbwheels and side buttons (known as decorations).
Listing 1 shows how simple it is to create this program. The first seven lines are the minimum header files. Inventor has 553 different include files. This may seem like a lot; however, each is very specialized, and selecting only the needed ones will speed up compilation time. If I wanted to, I could have simply included Inventor/So.h and let the compiler process all of the “So” prefixed files.
The first two executing lines after main create the main window widget and invoke SoXt::init. This is an essential part of the program, because here, Inventor is bound to Xt event handling so that its sensors will work properly. SoXT::init is also where the licensing code is called. Failing to invoke init will result in a core dump.
To be visible, each scene graph must have a node to attach to a viewer. In the listing, I am using a SoSeparator which saves the traversal state before being entered and restores it afterwards. This serves to prevent the attributes of its child nodes from affecting other parts of the scene graph that follow. A separator can include lights, cameras, coordinates, normals, bindings and all other properties. Separators also provide caching and culling of their children based on bounding box calculations during picking and rendering.
Once you create a node and pass it to the scene graph, Inventor takes over. Inventor nodes are always created dynamically with the C++ new command—never on the stack. Each node has a reference count, starting with zero when created, and incrementing and decrementing as nodes are added and removed as children to other parent nodes. When this reference count drops from one to zero, Inventor automatically deletes the node.
During traversal, the node is referenced and then dereferenced as the scene graph is traveled over. If we had not done a ref, the first time we traversed the scene graph its reference count would have incremented as it was entered, moving its reference count to one, and then decremented it back to zero as it was left, automatically deleting the node and any children whose reference counts had also dropped to zero. We would have been left wondering where our node(s) went.
Next, we add a material property as a child to the root node. It has a diffuse color or (1.0,0.0,0.0), which corresponds to full red, with red, green and blue (RGB) quantities being expressed as floating-point values between 0.0 and 1.0.
A cone is now added to the root node. Its default values are one unit for base and one for the length. It is located at the origin 0,0,0, and when unrotated, points one unit up from the base along the Y axis. Since the cone comes after the material property specifying the color red mentioned above, the cone inherits its attributes and is also red.
Inventor traverses its scene graph by starting at the root node and traveling down and to the right. Since OpenGL is a state machine, once we set an attribute, it will retain that value until changed.
Now we create the SceneViewer, passing the widget of our parent window, hooking our scene graph to it and setting the window title.
The show and hide methods call XtManageChild and XtUnmanageChild if a sub-widget is passed to it. If the widget is a shell widget, show will call RealizeWidget and XMapWindow, and if it is iconised, it will raise and de-iconify it. The hide method will call XUnmapWindow.
|Dynamic DNS—an Object Lesson in Problem Solving||May 21, 2013|
|Using Salt Stack and Vagrant for Drupal Development||May 20, 2013|
|Making Linux and Android Get Along (It's Not as Hard as It Sounds)||May 16, 2013|
|Drupal Is a Framework: Why Everyone Needs to Understand This||May 15, 2013|
|Home, My Backup Data Center||May 13, 2013|
|Non-Linux FOSS: Seashore||May 10, 2013|
- Dynamic DNS—an Object Lesson in Problem Solving
- Making Linux and Android Get Along (It's Not as Hard as It Sounds)
- Using Salt Stack and Vagrant for Drupal Development
- New Products
- A Topic for Discussion - Open Source Feature-Richness?
- Drupal Is a Framework: Why Everyone Needs to Understand This
- Validate an E-Mail Address with PHP, the Right Way
- RSS Feeds
- Readers' Choice Awards
- Tech Tip: Really Simple HTTP Server with Python
3 hours 11 min ago
- Reply to comment | Linux Journal
3 hours 43 min ago
- All the articles you talked
6 hours 7 min ago
- All the articles you talked
6 hours 10 min ago
- All the articles you talked
6 hours 11 min ago
10 hours 36 min ago
- Keeping track of IP address
12 hours 27 min ago
- Roll your own dynamic dns
17 hours 41 min ago
- Please correct the URL for Salt Stack's web site
20 hours 52 min ago
- Android is Linux -- why no better inter-operation
23 hours 7 min ago
Enter to Win an Adafruit Pi Cobbler Breakout Kit for Raspberry Pi
It's Raspberry Pi month at Linux Journal. Each week in May, Adafruit will be giving away a Pi-related prize to a lucky, randomly drawn LJ reader. Winners will be announced weekly.
Fill out the fields below to enter to win this week's prize-- a Pi Cobbler Breakout Kit for Raspberry Pi.
Congratulations to our winners so far:
- 5-8-13, Pi Starter Pack: Jack Davis
- 5-15-13, Pi Model B 512MB RAM: Patrick Dunn
- 5-21-13, Prototyping Pi Plate Kit: Philip Kirby
- Next winner announced on 5-27-13!
Free Webinar: Hadoop
How to Build an Optimal Hadoop Cluster to Store and Maintain Unlimited Amounts of Data Using Microservers
Realizing the promise of Apache® Hadoop® requires the effective deployment of compute, memory, storage and networking to achieve optimal results. With its flexibility and multitude of options, it is easy to over or under provision the server infrastructure, resulting in poor performance and high TCO. Join us for an in depth, technical discussion with industry experts from leading Hadoop and server companies who will provide insights into the key considerations for designing and deploying an optimal Hadoop cluster.
Some of key questions to be discussed are:
- What is the “typical” Hadoop cluster and what should be installed on the different machine types?
- Why should you consider the typical workload patterns when making your hardware decisions?
- Are all microservers created equal for Hadoop deployments?
- How do I plan for expansion if I require more compute, memory, storage or networking?