OpenGL Porting Guide ® Document Number 007-1797-030

OpenGL Porting Guide ® Document Number 007-1797-030

OpenGL

®

Porting Guide

Document Number 007-1797-030

CONTRIBUTORS

Written by C J Silverio, Beth Fryer, and Jed Hartman. Revised by Renate Kempf.

Edited by Christina Cary

Production by Mike Dixon

Engineering contributions by Kurt Akeley, Allen Akin, Gavin Bell, Derrick Burns,

Dave Ciemiewicz, Tom Davis, Chris Frazier, Paul Ho, Phil Karlton, Reuel Nash,

Mark Segal, Dave Shreiner, Rolf van Widenfelt, and Mason Woo. Revised example programs by Paul Ho.

© 1994, 1997 Silicon Graphics, Inc.— All Rights Reserved

The contents of this document may not be copied or duplicated in any form, in whole or in part, without the prior written permission of Silicon Graphics, Inc.

RESTRICTED RIGHTS LEGEND

Use, duplication, or disclosure of the technical data contained in this document by the Government is subject to restrictions as set forth in subdivision (c) (1) (ii) of the

Rights in Technical Data and Computer Software clause at DFARS 52.227-7013 and/or in similar or successor clauses in the FAR, or in the DOD or NASA FAR

Supplement. Unpublished rights reserved under the Copyright Laws of the United

States. Contractor/manufacturer is Silicon Graphics, Inc., 2011 N. Shoreline Blvd.,

Mountain View, CA 94043-1389.

Silicon Graphics, the Silicon Graphics logo, IRIS, IRIS Indigo, and OpenGL are registered trademarks and IRIS InSight, GL, Graphics Library, IRIS GL, IRIX, Open

Inventor, Personal IRIS, and RealityEngine are trademarks of Silicon Graphics, Inc.

Ada is a trademark of the Ada Joint Program Office, U.S. Government. X Window

System is a trademark of Massachusetts Institute of Technology. OSF/Motif is a trademark of the Open Software Foundation, Inc.

OpenGL ® Porting Guide

Document Number 007-1797-030

Contents

1.

List of Figures

ix

List of Tables

xi

About This Guide

xiii

What This Guide Contains xiii

Where to Get More Information xiv

OpenGL Documentation xv

GLX and GLUT Documentation xvi

IRIS GL Documentation xvi

X Window System Documentation xvi

OSF/Motif Documentation xvii

Conventions Used in This Guide xvii

Typographical Conventions xvii

Function Naming Conventions xviii

Changes in This Version of the Document xviii

Introduction to Porting From IRIS GL to OpenGL

1

Differences Between IRIS GL and OpenGL 1

Tools and Libraries to Help Port Your Code 3

Porting IRIS GL Programs to OpenGL 4

Porting IRIS GL Programs That Use X Calls 4

Porting IRIS GL Programs With Simple Windowing 5

Porting IRIS GL Programs With Complex Windowing 5

If You’re Not Porting Your Code to OpenGL Yet 6

iii

Contents

2.

3.

Using the toogl Tool

7

Getting Started with toogl 7

Finding and Building toogl 8

Calling toogl 8

Using toogl in Batch Mode 9

What toogl Will and Won’t Do for You 9

Using xdiff or gdiff to Compare Files 9

Using toogl Effectively 10

Editing toogl Output: Areas that Need Special Attention 10

Windowing, Device, and Event Calls 11

Parentheses and Quotes 12

Defined Color Constants 12 clear() Calls 12

Get Calls 13 rotate() Calls 13 swaptmesh() Calls 13

Texturing Calls 13 def/bind Calls 14

Calls Without Direct Equivalents 14

Finding OpenGL Replacements for IRIS GL Calls 14

Performance 14

Editing toogl Output: An Example 15

After toogl: How to Finish Porting to OpenGL

17

Header Files 18

Porting greset() 19

Porting IRIS GL get* Commands 20

About glGet*() 21 glGet*() Conventions Used in This Book 22

Porting Commands That Required Current Graphics Positions 22

Porting Screen and Buffer Clearing Commands 23

iv

Porting Matrix and Transformation Calls 24

Porting MSINGLE Mode Code 28

Porting get* Calls for Matrices and Transformations 29

Porting Viewports, Screenmasks, and Scrboxes 30

Porting Clipping Planes 30

Porting Drawing Commands 31

Porting the IRIS GL Sphere Library 31

Porting v() Commands 33

Porting bgn/end Commands 33

Porting Points 35

Porting Lines 36

Porting Polygons and Quadrilaterals 37

Porting Tessellated Polygons 41

Porting Triangles 41

Porting Arcs and Circles 42

Porting Spheres 43

Porting Color, Shading, and Writemask Commands 44

Porting Color Calls 45

Porting Shading Models 46

Porting Pixel Operations 46

Porting Depth Cueing and Fog Commands 48

Porting Curve and Surface Commands 52

NURBS Objects 52

NURBS Curves 53

Trimming Curves 54

NURBS Surfaces 54

Porting Antialiasing Calls 58

Blending 59 afunction() Test Functions 60

Antialiasing Calls 60

Accumulation Buffer Calls 61

Stencil Plane Calls 63

Contents

v

Contents

4.

Porting Display Lists 63

Porting bbox2() Calls 65

Achieving Edited Display List Behavior 65

Sample Implementation of a Display List 66

Porting defs, binds, and sets: Replacing ‘Tables’ of Stored Definitions 67

Porting Lighting and Materials Calls 68

Porting Texture Calls 73

Translating tevdef() 75

Translating texdef() 76

Translating texgen() 78

Porting Picking Calls 79

Porting Feedback Calls 80

Porting RealityEngine Graphics Features 83

OpenGL Extensions 87

OpenGL in the X Window System

89

X Window System Background 90

Function Naming Conventions 90

Two Choices for Using OpenGL and X 91

Advice for OpenGL Programs using the X Window System 92

Dealing With Window Depth and Display Mode 92

Installing Color Maps 92

Fonts and Strings 92

Using Xt and a Widget Set 94

What You Need to Know About Xt and IRIS IM 95

IRIS IM and Other Widget Sets 96

Converting Your IRIS GL Program 96

Background Reading 102

Using Xlib and GLX Commands 103

Getting Started With Xlib and GLX 103

Opening a Window With GLX 104

Using X Color Maps 105

Using X Events 106

vi

D.

E.

F.

A.

B.

C.

OpenGL Commands and Their IRIS GL Equivalents

109

Differences Between OpenGL and IRIS GL

139

OpenGL Names, Types, and Error

153

OpenGL Command Names 153

OpenGL Defined Types 155

Error Handling 156

Example OpenGL Program With the GLUT Library

157

Example Program Using Xt and a WorkProc

161

Example Mixed-Model Programs With Xlib

171

Example One: iobounce.c 171

IRIS GL Version of iobounce.c 171

OpenGL Version of iobounce.c 174

Example Two: zrgb.c 181

IRIS GL Version of zrgb.c 181

OpenGL Version of zrgb.c 187

Index

197

Contents

vii

List of Figures

Figure 3-1

Figure 3-2

Figure 3-3

Figure 3-4

Generic IRIS GL Translation 25

Generic OpenGL Translation 25

OpenGL Matrix Example 26

Drawing Angles: Comparing IRIS GL and OpenGL 43

ix

List of Tables

Table 3-17

Table 3-18

Table 3-19

Table 3-20

Table 3-21

Table 3-22

Table 3-23

Table 3-24

Table 3-25

Table 3-26

Table 3-27

Table 3-1

Table 3-2

Table 3-3

Table 3-4

Table 3-5

Table 3-6

Table 3-7

Table 3-8

Table 3-9

Table 3-10

Table 3-11

Table 3-12

Table 3-13

Table 3-14

Table 3-15

Table 3-16

Include Lines in IRIS GL and OpenGL Programs 18

Include Lines for IRIS GL and OpenGL Motif Widgets 18

State Attribute Groups 19

Calls for Clearing the Screen 24

Matrix Operations 26

Matrix Modes 28

Arguments for Transformation Matrix Queries 29

Viewport Calls 30

Clipping Plane Calls 30

Calls for Drawing Quadrics 32

Calls for Drawing Primitives 34

Valid Commands Inside a Begin/End Structure 35

Calls for Drawing Points 35

Calls for Drawing Lines 36

Calls for Drawing Polygons 37

Polygon Modes 38

Polygon Stipple Calls 39

Tessellated Polygon Calls 41

Calls for Drawing Triangles 42

Calls for Drawing Arcs and Circles 42

Calls for Drawing Spheres 44

Color Calls 45

Shading and Dithering 46

Pixel Operations 47

Calls for Managing Fog 48

Fog Parameters 49

Fog Modes 50

xi

List of Tables

Table 3-44

Table 3-45

Table 3-46

Table 3-47

Table 3-48

Table 3-49

Table 3-50

Table 3-51

Table 3-52

Table 3-53

Table 3-54

Table A-1

Table C-1

Table C-2

Table C-3

Table 3-28

Table 3-29

Table 3-30

Table 3-31

Table 3-32

Table 3-33

Table 3-34

Table 3-35

Table 3-36

Table 3-37

Table 3-38

Table 3-39

Table 3-40

Table 3-41

Table 3-42

Table 3-43

Calls for Managing NURBS Objects 52

Calls for Drawing NURBS Curves 53

NURBS Curve Types 53

Calls for Drawing NURBS Trimming Curves 54

Calls for Drawing NURBS Surfaces 54

NURBS Surface Types 54

Blending Calls 59

Blending Factors 59

Alpha Test Functions 60

Calls to Draw Antialiased Primitives 60

Accumulation Buffer Calls 62

Accumulation Buffer Operations 62

Stencil Operations 63

Display List Commands 64

Lighting and Materials Commands 69

Material Definition Parameters 70

Lighting Model Parameters 70

Light Parameters 71

Texture Commands 74

Texture Environment Options 75

IRIS GL and OpenGL Texture Parameters 77

Values for IRIS GL and OpenGL Texture Parameters 77

Texture Coordinate Names 78

Texture Generation Modes and Planes 78

Calls for Picking 79

Feedback Calls 80

RealityEngine Calls 83

IRIS GL Commands and Their OpenGL Equivalents 109

Command Suffixes and Corresponding Argument Types 153

OpenGL Equivalents to C Data Types 155

glGetError()

Return Values 156

xii

About This Guide

This guide tells you how to port your existing IRIS GL code to OpenGL. It

• describes how to use the toogl automatic translation script

• lists OpenGL equivalents for IRIS GL calls

• describes how to reimplement IRIS GL windowing code using the X Window

System and IRIS IM APIs (IRIS IM is the Silicon Graphics port of the industry-standard OSF/Motif software)

• provides basic information for working with the X Window System

This guide is for developers who have been using IRIS GL. It is not an introduction to graphics programming and it is not comprehensive OpenGL documentation. For more complete OpenGL documentation, see “OpenGL Documentation” on page xv.

Note:

This guide is written for programmers who are working in C. It doesn’t discuss

OpenGL Fortran and Ada wrappers.

What This Guide Contains

This guide includes the following chapters:

• Chapter 1, “Introduction to Porting From IRIS GL to OpenGL,” describes some of the major differences between IRIS GL and OpenGL, lists the Silicon Graphics tools you can use to facilitate the transition, and provides some general porting instructions.

• Chapter 2, “Using the toogl Tool,” explains how to use the automatic translation tool, which can do much of the porting work for you.

• Chapter 3, “After toogl: How to Finish Porting to OpenGL,” discusses IRIS GL commands that might need some extra porting attention, giving command equivalents and providing porting tips for each.

xiii

About This Guide

• Chapter 4, “OpenGL in the X Window System,” describes two methods for using the X Window System™ to manage windows and events with OpenGL: using Xt and the Silicon Graphics IRIS IM widget or using Xlib.

• Appendix A, “OpenGL Commands and Their IRIS GL Equivalents,” is a complete alphabetical list of IRIS GL calls and their OpenGL equivalents (if an equivalent exists) along with cross-references to documentation, where available.

• Appendix B, “Differences Between OpenGL and IRIS GL,” provides a more complete list of the differences between OpenGL and IRIS GL than Chapter 1 offers.

• Appendix C, “OpenGL Names, Types, and Error,” explains OpenGL naming conventions, lists OpenGL defined types, and describes error handling in OpenGL.

• Appendix D, “Example OpenGL Program With the GLUT Library,” provides an example OpenGL program that uses the GLUT library for windowing and event handling.

• Appendix E, “Example Program Using Xt and a WorkProc,” provides an example

OpenGL program using Xt, IRIS IM, and the Silicon Graphics widget. The program demonstrates the use of a WorkProc for animation.

• Appendix F, “Example Mixed-Model Programs With Xlib,” provides two example mixed-model programs using Xlib. Each program is shown in both IRIS GL and

OpenGL form.

Where to Get More Information

As you use this guide, you will probably have to refer to the OpenGL reference pages, the IRIS GL reference pages, and the programming guides. You can read all the reference pages online using the man command, or you can buy the printed OpenGL reference pages. These are published in the OpenGL Reference Manual, available in bookstores (see

“OpenGL Documentation” on page xv).

Note:

If you’re viewing this manual online using IRIS InSight, click any red underlined reference page name to view the reference page.

xiv

About This Guide

In addition, you may find the OpenGL documentation, GLUT documentation, IRIS GL documentation, and window system documentation that’s listed in the following sections helpful:

• “OpenGL Documentation” on page xv

• “GLX and GLUT Documentation” on page xvi

• “X Window System Documentation” on page xvi

• “OSF/Motif Documentation” on page xvii

OpenGL Documentation

For more information on programming in OpenGL 1.1, refer to these manuals:

• OpenGL Architecture Review Board; Renate Kempf and Chris Frazier, editors.

OpenGL Reference Manual. The Official Reference Document for OpenGL, Version 1.1.

Reading, MA: Addison Wesley Longman Inc. 1996. ISBN 0-201-46140-4

• Woo, Mason, Jackie Neider, and Tom Davis. OpenGL Programming Guide: The Official

Guide to Learning OpenGL, Version 1.1. Reading, MA: Addison Wesley Longman Inc.

1997. ISBN 0-201-46138-2

OpenGL on Silicon Graphics Systems (Silicon Graphics manual; document number

007-2392-002)

For more information on programming in OpenGL 1.0, refer to these manuals:

• OpenGL Architecture Review Board. OpenGL Reference Manual. Reading, MA:

Addison-Wesley Publishing Company. 1992. ISBN 0-201-63276-4

• Neider, Jackie, Tom Davis, and Mason Woo. OpenGL Programming Guide. Reading,

MA: Addison-Wesley Publishing Company. ISBN 0-201-63274-8

OpenGL on Silicon Graphics Systems (Silicon Graphics manual; document number

007-2392-001)

xv

About This Guide

GLX and GLUT Documentation

• Kilgard, Mark J. OpenGL Programming for the X Window System. Menlo Park, CA:

Addison-Wesley Developer’s Press. 1996. ISBN 0-201-48369-9

• Pointers to the GLUT Library, to interesting technical papers, and to the comp.graphics.opengl mailing list are on the OpenGL home page: http://www.openGL.org/

IRIS GL Documentation

For more information on programming with IRIS GL, refer to these Silicon Graphics manuals:

Graphics Library Programming Guide, Volume 1 (document number 007-1210-060)

Graphics Library Programming Guide, Volume 2 (document number 007-1702-020)

Graphics Library Programming Tools and Techniques (document number 007-1489-030)

X Window System Documentation

For comprehensive information on the X Window System, Xlib, Xt, and X protocol, see the Digital Press X Series:

• Scheifler, Robert W., and James Gettys, et al. X Window System: The Complete

Reference to Xlib, X Protocol, ICCCM, XLFD. Third Edition, X Version 11, Release 5,

Burlington, MA. Digital Press—Digital Equipment Corporation, 1992. ISBN

1-55558-088-2

• Asente, Paul J., and Ralph R. Swick. X Window System Toolkit: The Complete

Programmer’s Guide and Specification. Burlington MA: Digital Press—Digital

Equipment Corporation. 1992. ISBN 1-55558-051-3

Or refer to the O’Reilly X Window System Series, Volumes 1, 4, and 5:

• Nye, Adrian. Volume One: Xlib Programming Manual. Sebastopol, CA. O’Reilly &

Associates. 3rd edition July 1992. ISBN 1-56592-002-3

• Nye, Adrian, and Tim O’Reilly. Volume Four: X Toolkit Intrinsics Programming

Manual. Sebastopol, CA: O’Reilly & Associates. Second edition, 1992. ISBN

1-56592-013-9

xvi

About This Guide

• Flanagen, David (editor). Volume Five: X Toolkit Intrinsics Reference Manual.

Sebastopol, CA: O’Reilly & Associates. Third edition, April 1992. ISBN

1-56592-007-4

OSF/Motif Documentation

For information on OSF/Motif, see the Prentice-Hall OSF/Motif series:

OSF/Motif Programmer’s Guide, Open Software Foundation, PTR Prentice-Hall, Inc.,

Englewood Cliffs, NJ.

OSF/Motif Programmer’s Reference, Open Software Foundation, PTR Prentice-Hall,

Inc., Englewood Cliffs, NJ.

OSF/Motif Style Guide, Open Software Foundation, PTR Prentice-Hall, Inc.,

Englewood Cliffs, NJ.

Conventions Used in This Guide

This section explains the typographical and function naming conventions used in this guide.

Typographical Conventions

This guide uses the following typographical conventions:

Italics

Filenames, IRIX command names, function parameters, and book titles.

Fixed-width

Bold

Code examples and system output.

Function names, with parentheses following the name—for example

glPolygonMode()

—and arguments to command-line options.

Note:

In all tables, regular font is used for function names. This avoids clutter in the table, which would make it difficult to read.

xvii

About This Guide

Function Naming Conventions

This guide refers to a group of similarly named OpenGL functions by a single name, using an asterisk to indicate all the functions whose names start the same way. For instance, glVertex*() refers to all functions whose names begin with “glVertex”:

glVertex2s()

, glVertex3dv(), glVertex4fv(), and so on.

Naming conventions for X-related functions can be confusing, because they depend largely on capitalization to differentiate between groups of functions. For systems on which both OpenGL and IRIS GL are available, the issue is further complicated by the similarity in function names. Here’s a quick guide to old and new function names:

GLX*()

Glx*()

IRIS GL mixed-model support

IRIS GL support for IRIS IM

glX*()

GLw*()

OpenGL support for X

OpenGL support for IRIS IM

Note that the (OpenGL) glX*() routines are collectively referred to as “GLX”; that term was previously used to refer to the (IRIS GL) GLX*() routines. Note, too, that

GLXgetconfig()

(an IRIS GL mixed-model routine) is not the same function as

glXGetConfig()

(a GLX routine). On systems with both IRIS GL and OpenGL, the command

IRIS% man glxgetconfig displays both reference pages, one following the other.

Changes in This Version of the Document

This version of the document has been updated in the following ways:

• All references to the aux library have been removed and replaced with references to the GLUT library where appropriate. The aux library was never intended for production-level code. Its removal from this document intends to discourage programmers from continuing to use it.

• All examples were updated to use the glut library instead of the aux library.

xviii

About This Guide

• This document is targeted at both OpenGL 1.0 and OpenGL 1.1 users. It refers to

OpenGL 1.1 functions where new functionality has been introduced (old references to extensions remain where appropriate).

• Most references to reference pages are now links when viewed with IRIS Insight.

• Chapter and section overviews with links to sections or subsections have been added.

• Appendix B, Differences Between OpenGL and IRIS GL, was updated to contain the most recent information supplied by Mark Kilgard.

xix

Chapter 1

1.

Introduction to Porting From IRIS GL to OpenGL

This chapter provides an overview to porting from IRIS GL to OpenGL. It discusses the following topics:

• “Differences Between IRIS GL and OpenGL” discusses window and event management, some fundamental implementation differences, and naming conventions.

• “Tools and Libraries to Help Port Your Code” on page 3 briefly explores the toogl tool, Motif drawing area widgets, and the glx library.

• “Porting IRIS GL Programs to OpenGL” on page 4 explains how to port both a mixed-model program (using IRIS GL and X) and an IRIS GL program that doesn’t use X.

• “If You’re Not Porting Your Code to OpenGL Yet” on page 6 provides some advice for programmers who don’t plan to port to OpenGL immediately.

Differences Between IRIS GL and OpenGL

One focus of OpenGL is portability. OpenGL and IRIS GL therefore differ in several major areas. This section lists a few important ways in which OpenGL is different from

IRIS GL. A more complete list of the differences between the two languages is provided in Appendix B, “Differences Between OpenGL and IRIS GL.”

Here are some key differences between OpenGL and IRIS GL:

Window Management

. OpenGL is window-system independent. It therefore contains no windowing, pop up menus, event handling, color-map loading, buffer allocation and management, font file formats, or cursor handling. These functions are delegated to the window or operating system. You can use the GLUT library for simple window handling under X. If you need more sophisticated windowing and event handling calls, you have to include the relevant X Window System calls in your program. Silicon Graphics provides some special GLX calls, where OpenGL rendering is made available as an extension to X in the formal X sense, and an

1

Chapter 1: Introduction to Porting From IRIS GL to OpenGL widget to help you replace your IRIS GL windowing, event, and colormap handling calls. See Chapter 4, “OpenGL in the X Window System,” for details.

Naming Conventions.

OpenGL establishes and adheres to a standard “name space.” OpenGL commands begin with the gl prefix (glEnable(), glTranslatef(), and so on). This convention prevents conflict with commands from other libraries.

“OpenGL Command Names” on page 153 explains the OpenGL naming conventions, and “OpenGL Defined Types” on page 155 lists the OpenGL defined types with their C data type equivalents.

State Variables

. Like IRIS GL, OpenGL maintains state variables for color, fog, texture, lighting, viewport, and so on. But OpenGL manages state variables more directly and consistently than IRIS GL does. With OpenGL there are no tables—you just load values directly.

Because OpenGL doesn’t keep tables of predefined lights and materials, it has no equivalent for “binds,” although you can use display lists to get a similar effect.

“Porting defs, binds, and sets: Replacing ‘Tables’ of Stored Definitions” on page 67 explores different approaches to replacing display lists. Refer also to “Porting

Lighting and Materials Calls” on page 68 and “Porting Texture Calls” on page 73 for more discussion and some examples.

Display Lists

. OpenGL display lists are not editable. In OpenGL, the sole purpose of display lists is to efficiently cache OpenGL commands. As a result, IRIS GL calls for editing display lists have no OpenGL equivalent. If your IRIS GL program edits display lists, you have to reimplement it to some extent. “Porting Display Lists” on page 63 lists the relevant IRIS GL calls, and “Achieving Edited Display List

Behavior” on page 65 provides some suggestions for porting code that edits display lists.

Fonts

. IRIS GL provides calls to handle fonts and text strings. Although OpenGL can render text, it doesn’t provide a file format for fonts. For fonts and text strings, you can use the GLX call glXUseXFont() in conjunction with the OpenGL calls

glCallLists()

and glListBase(). “Fonts and Strings” on page 92 provides suggestions for porting fonts and strings.

Utility Library.

OpenGL provides a utility library, called the GL Utility Library

(GLU), that contains additional routines (such as NURBS and quadric surfaces rendering routines). This library is discussed in the OpenGL Programming Guide.

Reference pages for all the routines the GLU consists of are included in the OpenGL

Reference Manual. These routines all begin with the “glu” prefix (gluDisk(),

gluErrorString()

, and so on).

2

Tools and Libraries to Help Port Your Code

Tools and Libraries to Help Port Your Code

Silicon Graphics provides tools and libraries to help you port your IRIS GL program:

• The toogl tool translates your program’s IRIS GL calls to OpenGL calls. toogl does do a lot of the translation work for you but it can’t translate everything (in particular, it can’t translate windowing and event calls). You therefore have to edit the output. Chapter 2, “Using the toogl Tool,” explains how to use toogl.

• The OpenGL extension to X (GLX) provides a variety of routines to help you replace your old IRIS GL windowing, event, and font calls. Chapter 4 explains how to use GLX. Reference pages for the GLX routines are included in the OpenGL

Reference Manual. Consider looking at the glXIntro reference page first for an overview.

• The GLwDrawingArea and GLwMDrawingArea widgets help you port your code to run in an X window. These widgets provide a window with the appropriate visual and color maps needed for OpenGL, based on supplied parameters. They also provide callbacks for redraw, resize, input, and initialization. For information on how to use these widgets, see Chapter 4.

• The GLUT Library is a programming interface with ANSI C and FORTRAN bindings for writing window system independent OpenGL programs. The toolkit supports the following functionality:

– Multiple windows for OpenGL rendering

– Callback-driven event processing

– Sophisticated input devices

– An “idle” routine and timers.

– A simple cascading pop-up menu facility

– Utility routines to generate various solid and wire frame objects

– Support for bitmap and stroke fonts

– Miscellaneous window management functions, including managing overlays

You can find the GLUT library (and the associated documentation) on the OpenGL home page http://www.opengl.org, or the Silicon Graphics OpenGL page, http://www.sgi.com/Technology/openGL/. It is also discussed in OpenGL

Programming for the X Window System; see “Where to Get More Information” on page xiv.

3

Chapter 1: Introduction to Porting From IRIS GL to OpenGL

Porting IRIS GL Programs to OpenGL

This section lists three porting scenarios. Select the one that best matches your situation and complete the porting tasks listed. More information is provided in subsequent chapters. This overview discusses the major porting tasks for different kinds of programs:

• “Porting IRIS GL Programs That Use X Calls” on page 4

• “Porting IRIS GL Programs With Simple Windowing” on page 5

• “Porting IRIS GL Programs With Complex Windowing” on page 5

In all cases, after you’ve finished the porting tasks listed, you probably have to iteratively compile, run, and debug your program. If necessary, run the toogl script again to catch any IRIS GL commands that you missed. You may find it useful to refer to “Error

Handling” on page 156 which gives some basic information on error handling in

OpenGL.

Porting IRIS GL Programs That Use X Calls

If your IRIS GL program uses X for all window system calls, including windowing and event handling, it will be relatively easy to port it to OpenGL. Here’s what you have to do:

1.

Run your program through a C beautifier (such as cb).

2. Run the toogl filter script on your code.

3. Edit toogl output. See Chapter 2 for a list of known trouble spots where you have to port your code explicitly. See Chapter 3, “After toogl: How to Finish Porting to

OpenGL,” for specific suggestions.

4. Convert your IRIS GL X Window System calls to GLX calls.

If you used one of the Motif widgets, GlxDraw or GlxMDraw, switch to the

OpenGL version: GLwDrawingArea or GLwMDrawingArea. Chapter 4 discusses mixed-model programming in OpenGL and provides information about the OpenGL version of the Silicon Graphics mixed-model widget.

If you didn’t use a widget, look at Appendix F, “Example Mixed-Model

Programs With Xlib.”

4

Porting IRIS GL Programs to OpenGL

The OpenGL Reference Manual contains an overview of the OpenGL Extension to the X Window System. It also includes a glXIntro reference page and reference pages for all the OpenGL/X routines.

OpenGL Programming for the X Window System by Mark Kilgard discusses all aspects of using OpenGL in the X Window System environment. See “Where to

Get More Information” on page xiv for complete bibliographical information.

Porting IRIS GL Programs With Simple Windowing

If your program doesn’t use X Window System calls but does use simple windowing, you can probably use the GLUT library to replace IRIS GL windowing, color map, and event handling calls. This is possible if your code meets the following conditions:

• Is reasonably simple

• Conforms to Silicon Graphics recommendations

• Doesn’t use unsupported calls,

Here’s what you have to do:

1.

Replace windowing and event handling calls with GLUT calls.

2. Run your program through a C beautifier (such as cb).

3. Run the toogl filter script on your code.

4. Edit toogl output. See Chapter 2 for a list of known trouble spots. You will probably have port some of the trickier commands explicitly; see Chapter 3 for specific suggestions.

Porting IRIS GL Programs With Complex Windowing

If your IRIS GL code doesn’t use X windowing calls and your windowing and event handling code uses unsupported calls, doesn’t conform to Silicon Graphics recommendations, or is complicated or unusual in scope, using the X Window System is the best solution.

Here’s what you have to do:

1.

Run your program through a C beautifier (such as cb),

2. Run the toogl filter script on your code.

5

Chapter 1: Introduction to Porting From IRIS GL to OpenGL

3. Edit toogl output. See Chapter 2 for a list of known trouble spots. You will probably have port some of the trickier commands explicitly; see Chapter 3 for specific suggestions.

4. Port your program to use OpenGL and X. You can do this either by using Xlib and directly replacing calls like winopen() and qread() with their GLX equivalents, or by using Xt along with a widget set and the OpenGL widget GLwDrawingArea. See

Chapter 4 for more information.

If You’re Not Porting Your Code to OpenGL Yet

If you’re not porting to OpenGL now, but know that you will be porting in the future, it’s a good idea to switch to mixed-model mode now.

• Replace all GL windowing calls with GLX and X calls.

• Replace GL event handling with X event handling. Refer to the Graphics Library

Programming Tools and Techniques manual for detailed instructions.

• Learn what IRIS GL features have no OpenGL equivalents. Avoid using them in new code, and reimplement code that does use them. Appendix A, “OpenGL

Commands and Their IRIS GL Equivalents,” lists IRIS GL commands and indicates which commands are not supported in OpenGL.

• Replace any obsolete or unsupported calls with newer IRIS GL equivalents as soon as possible.

6

Chapter 2

2.

Using the toogl Tool

toogl (which stands for To OpenGL and is pronounced TOO-guhl) is a script that takes

IRIS GL code as input and produces commented, nearly equivalent OpenGL code as output.

This chapter explores how to use and get the most from toogl. It explains where to find a copy of toogl and how to use toogl most effectively. It also mentions some areas of your

IRIS GL code that might give you problems.

The chapter discusses the following topics:

• “Getting Started with toogl” explains how you can get a copy of toogl and then explores calling toogl for one file and in batch mode.

• “Using xdiff or gdiff to Compare Files” on page 9 explains two tools that are helpful for comparing your original IRIS GL file with the OpenGL output produced by

toogl.

• “Using toogl Effectively” on page 10

• “Editing toogl Output: Areas that Need Special Attention” on page 10

• “Editing toogl Output: An Example” on page 15

Getting Started with toogl

You can use toogl to do much of the work of translating your IRIS GL code to OpenGL code. While toogl can’t do everything, it can do all the tedious work of changing command names, and it can call your attention to code you have to port explicitly.

This section first explains “Finding and Building toogl,” then provides the syntax in

“Calling toogl,” and explores “Using toogl in Batch Mode.” The last section briefly discusses “What toogl Will and Won’t Do for You.”

7

Chapter 2: Using the toogl Tool

Finding and Building toogl

A copy of toogl is in the /usr/share directory. The exact location depends on the operating system version you are using. If you want to look at the source (it’s in C++), you can get a copy from the OpenGL directory.

You can also get a copy of the tool from the “Contributed Tools” area of the Silicon

Graphics OpenGL home page (http://www.sgi.com/Technology/openGL/)

To build the tool, enter:

# setenv OBJECT_STYLE 32

# make

Warning:

If you build toogl with OBJECT_STYLE set to n32 (the default on current systems), the tool does not work!

Calling toogl

toogl syntax: toogl [-cwq] < infile > outfile

You can use any of these options with toogl:

-c

Don’t clutter up the output with comments

-w

-q

Don’t remove window manager calls like winopen(), mapcolor()

Don’t remove event queue calls like qread(), setvaluator()

Note:

toogl doesn’t attempt to translate event queue and windowing calls. It simply removes them, and replaces them with warning comments. The -w and -q flags merely suppress the comments.

Keep your original source! Accidents happen.

8

Using xdiff or gdiff to Compare Files

Using toogl in Batch Mode

To process a directory full of source files automatically, you could use a shell script like the following:

#!/bin/sh mkdir OpenGL for i in *.c

do

echo "Converting " $i " ..."

toogl < $i > OpenGL/$i

done

What toogl Will and Won’t Do for You

toogl is a filter that scans each line of an input file, looking for IRIS GL calls. When toogl finds an IRIS GL function, it replaces the function with the corresponding OpenGL function(s).

Because toogl can’t translate everything, you have to edit its output. Any time toogl translates code that you may have to look at, check, or change, it marks the potential problem with a comment starting with “OGLXXX”. (You can use the -c option to suppress the comments.)

Using xdiff or gdiff to Compare Files

After you’ve converted your program using toogl, you have to edit the toogl output. You’ll probably want to examine the differences between the toogl output and your original program—or any other version of the program. To do so, use either gdiff or xdiff.

To use gdiff, enter: gdiff -b

file1 file2

where file1 and file2 are the names of the files you want to compare. The -b option tells

gdiff to ignore trailing blanks on lines when comparing files. You might also want to use the -w option, which tells gdiff to ignore white space.

9

Chapter 2: Using the toogl Tool

To use xdiff, enter: xdiff

file1 file2

See the xdiff reference page for more information.

Using toogl Effectively

Here are a few suggestions for getting the most out of toogl:

• For best results, use a C beautifier (such as cb) on your code before running toogl.

• Use gdiff (or xdiff) to browse through the source and the translation simultaneously.

toogl expects to find the matching parentheses or quotes on the same line as the

IRIS GL function.

toogl expects to find only spaces and tabs between a function name and the opening parenthesis. For example, the code v3f

(foo); will be left unchanged, as will v3f /* comment */ (foo);

Running a C beautifier on your program before using toogl can prevent problems like this.

toogl expects that C comments inside the argument list of a function don’t contain parentheses or quote characters. Faced with the following code, toogl will generate a warning and will not do a translation: v3f ( foo /* I really mean bar “-) */ );

Editing toogl Output: Areas that Need Special Attention

After you’ve run toogl on your code, you have to edit the output. Some areas are more problematic than others—for example, v() calls usually translate quite neatly into

glVertex()

calls, but texture calls often don’t translate well. This section lists some of the general areas that are likely to need special attention. Chapter 3, “After toogl: How to

Finish Porting to OpenGL,” provides more detailed information on problem areas.

10

Editing toogl Output: Areas that Need Special Attention

This section briefly addresses the following issues:

• “Windowing, Device, and Event Calls”

• “Parentheses and Quotes”

• “Defined Color Constants”

• “clear() Calls”

• “Get Calls”

• “rotate() Calls”

• “swaptmesh() Calls”

• “Texturing Calls”

• “def/bind Calls”

• “Calls Without Direct Equivalents”

• “Finding OpenGL Replacements for IRIS GL Calls”

• “Performance”

Windowing, Device, and Event Calls

toogl can’t translate sections of code that make window manager, window configuration, device, or event calls, or that load a color map. You have to rewrite these code sections yourself. You can use the -w and -q options to make toogl leave this code untouched, so you can still read it to translate it manually. If your windowing and event handling calls are simple and straightforward, you can replace them with calls from the GLUT library.

For more information on GLUT, see the OpenGL home page http://www.OpenGL.org

or the Silicon Graphics OpenGL page http://www.sgi.com/Technology/openGL/. See also “GLX and GLUT Documentation” on page xvi.

If your windowing and event handling calls are fairly sophisticated, you have to incorporate the OpenGL code into X Windows directly, either using the OpenGL widget or using Xlib. This is explained in Chapter 4, “OpenGL in the X Window System.”

11

Chapter 2: Using the toogl Tool

Parentheses and Quotes

toogl understands a little about matching parentheses and quotes. It translates v3f( v[strlen(strcat(foo, "foo("))] ); into glVertex3fv( v[strlen(strcat(foo, "foo("))] );

Defined Color Constants

IRIS GL provides defined color constants: BLACK, BLUE, RED, GREEN, MAGENTA,

CYAN, YELLOW, and WHITE. OpenGL does not provide these constants and toogl does not translate them, so you have to port them explicitly.

clear() Calls

Make sure clear() calls are correctly translated. For example, assume your program clears the window as follows: color(BLACK); clear();

toogl translates those two lines as follows: glIndex(BLACK); glClear(GL_COLOR_BUFFER_BIT);

The above code fragment is incorrect for these reasons:

• OpenGL does not provide the color constant BLACK

• OpenGL maintains a clear color that’s distinct from the drawing color.

A better translation is the following: glIndex(0); glClearIndex(0); glClear(GL_COLOR_BUFFER_BIT);

12

Editing toogl Output: Areas that Need Special Attention

Get Calls

toogl does not always translate IRIS GL “get” calls (such as getdepth(), getcolor(), and so on) correctly. toogl translates i = getcolor(); getdepth(&near, &far); into

/* OGLXXX replace value with your variable */ i = glGetIntegerv(GL_CURRENT_INDEX, &value);

/* OGLXXX You can probably do better than this. */

{

int get_depth_tmp[2];

glGetIntegerv(GL_DEPTH_RANGE, get_depth_tmp);

*(&near)=get_depth_tmp[0];

*( &far)=get_depth_tmp[1];

};

This guide lists the glGet*() calls related to a particular topic in the section on that topic.

For general information on replacing get calls, see “Porting IRIS GL get* Commands” on page 20.

rotate() Calls

The OpenGL rotation call glRotate() is different from rotate(). You will probably have to modify the code after translating the program with toogl. See “Porting Matrix and

Transformation Calls” on page 24 for details.

swaptmesh() Calls

OpenGL has no equivalent for swaptmesh(); toogl flags occurrences of the function and leaves it up to you to restructure your triangles.

Texturing Calls

toogl correctly translates texture coordinate calls. You have to do additional work, as explained in “Porting Texture Calls” on page 73.

13

Chapter 2: Using the toogl Tool

Note:

If you’re using OpenGL 1.1, you can take advantage of subtextures. Because toogl was developed for OpenGL 1.0, you have to implement the use of OpenGL subtextures yourself.

def/bind Calls

OpenGL does not keep tables of predefined lights and materials, so it has no equivalent for “binds.” You can use display lists to mimic the behavior. See “Porting defs, binds, and sets: Replacing ‘Tables’ of Stored Definitions” on page 67 for more information. See also

“Porting Lighting and Materials Calls” on page 68 and “Porting Texture Calls” on page 73 for more discussion and some examples.

Calls Without Direct Equivalents

There are some IRIS GL calls that toogl cannot directly translate into OpenGL calls. arcf() is one example. You have to port such calls explicitly. “Editing toogl Output: An

Example” on page 15 gives an example for porting a call like arcf().

Finding OpenGL Replacements for IRIS GL Calls

Appendix A, “OpenGL Commands and Their IRIS GL Equivalents,” contains a table listing IRIS GL commands and the corresponding OpenGL commands, and tells you where to go for more information. This table also indicates which IRIS GL calls are not supported in OpenGL.

Performance

toogl doesn’t necessarily produce fast OpenGL code; in fact, such an automatic port usually results in loss of performance. Details of improving OpenGL performance are beyond the scope of the current edition of this guide; however, you can find some specific tips in “Porting Screen and Buffer Clearing Commands” on page 23 and “Porting

Lighting and Materials Calls” on page 68.

Note:

The performance chapters of OpenGL on Silicon Graphics Systems provide additional information.

14

Editing toogl Output: An Example

Two features of OpenGL that can drastically improve performance are display lists and direct rendering. Use these features whenever possible in OpenGL programs. For information on display lists, see “Porting Display Lists” in Chapter 3. For information on direct rendering, see the glXCreateContext reference page. If you aren’t careful, you may set up indirect rendering without noticing that it’s indirect; specify direct rendering explicitly where possible.

Here are few more tips:

• If you’re drawing independent triangles, there’s no need to put glBegin() and

glEnd()

around each set of three vertices. Instead, call glBegin(GL_TRIANGLES) and then list as many individual triangles as you need before the glEnd(). This optimization alone can noticeably improve performance.

• If you aren’t using the depth buffer, disable it. This is particularly important when you call glDrawPixels() or other non-3D drawing functions.

• Disable texturing when you call glDrawPixels() or any other function that shouldn’t use textures. Otherwise, the texture overhead slows down drawing even if you’re only drawing a bitmap.

Editing toogl Output: An Example

This section provides an example for working with toogl output.

toogl translates the call arcf(1.0, 1.0, 0.9, 1200, 2200); as

/* OGLXXX see gluPartialDisk man page */ gluPartialDisk( *gobj, innerRad, outerRad, slices, loops, startAng, endAng);

The IRIS GL call arcf() can’t be directly translated into an OpenGL call. The GL Utility

Library call gluPartialDisk() is the nearest equivalent, but you have to fill in its arguments explicitly. Compare the reference pages for the two commands, or refer to the section in this guide that discusses porting that command (in this case, “Porting Arcs and

Circles” on page 42).

15

Chapter 2: Using the toogl Tool

Those materials explain that you have to account for the following changes:

• Arcs are now quadrics and are drawn using quadric objects.

• Angles are now measured in degrees instead of tenths of degrees.

• Instead of specifying a center for your arc in the call, you now do a translation first.

• Angles are now measured on different coordinate axes. The second angle is now a sweep angle instead of an end angle.

Your completed arcf() translation might look like this: gluQuadricObj *arcObj; arcObj = gluNewQuadric(void); glTranslatef( 1.0, 1.0, 0.0 ); gluPartialDisk( *arcObj, 0.0, 0.9, 100, 2, -30, -100);

16

Chapter 3

3.

After toogl: How to Finish Porting to OpenGL

After you run your IRIS GL program through toogl, you can use this chapter to find out how to replace IRIS GL calls that toogl didn’t translate completely or correctly. To get the most out of this discussion, refer to the reference pages as necessary.

The chapter discusses these topics:

• “Header Files” on page 18

• “Porting greset()” on page 19

• “Porting IRIS GL get* Commands” on page 20

• “Porting Commands That Required Current Graphics Positions” on page 22

• “Porting Screen and Buffer Clearing Commands” on page 23

• “Porting Matrix and Transformation Calls” on page 24

• “Porting Drawing Commands” on page 31

• “Porting Color, Shading, and Writemask Commands” on page 44

• “Porting Pixel Operations” on page 46

• “Porting Depth Cueing and Fog Commands” on page 48

• “Porting Curve and Surface Commands” on page 52

• “Porting Antialiasing Calls” on page 58

• “Porting Display Lists” on page 63

• “Porting defs, binds, and sets: Replacing ‘Tables’ of Stored Definitions” on page 67

• “Porting Texture Calls” on page 73

• “Porting Picking Calls” on page 79

• “Porting Feedback Calls” on page 80

• “Porting RealityEngine Graphics Features” on page 83

• “OpenGL Extensions” on page 87

17

Chapter 3: After toogl: How to Finish Porting to OpenGL

Header Files

toogl doesn’t replace header files for you, so you have to replace them yourself. This section lists the files your IRIS GL program probably used and the OpenGL files to replace them with.

Table 3-1

Include Lines in IRIS GL and OpenGL Programs

IRIS GL Include Lines

#include <gl/gl.h>

#include <gl/device.h>

#include <gl/get.h>

OpenGL Include Lines

#include <GL/gl.h>

#include <GL/glu.h>

/* X header files start here*/

#include <Xm/Xm.h>

#include <Xm/Frame.h>

#include <Xm/Form.h>

#include <X11/StringDefs.h>

#include <X11/keysym.h>

If you use the GLUT library, you also have to include the GLUT header file:

#include <GL/glut.h>

If you use the Motif widget, replace the include lines as indicated in Table 3-2.

Table 3-2

Include Lines for IRIS GL and OpenGL Motif Widgets

IRIS GL Motif Widget Include Lines

For the IRIS IM version of the widget:

#include <X11/Xirisw/GlxMDraw.h>

For the generic version of the widget:

#include <X11/Xirisw/GLxDraw.h>

OpenGL Motif Widget Include Lines

For the IRIS IM version of the widget:

#include <GL/GLwMDrawA.h>

For the generic version of the widget:

#include <GL/GLwDrawA.h>

If you’re using Xlib and OpenGL/X calls, add

#include <GL/glx.h>

18

Porting greset()

Porting greset()

OpenGL replaces the functionality of greset() with the commands glPushAttrib() and

glPopAttrib()

. Use these commands to save and restore groups of state variables.

Call glPushAttrib() to indicate which groups of state variables to push onto an attribute stack by taking a bitwise OR of symbolic constants, as follows: void glPushAttrib( GLbitfield mask );

The attribute stack has a finite depth of at least 16.

The glPushAttrib() and glPopAttrib() calls push and pop the server attribute stacks. In

OpenGL 1.1, you can also use the functions glPushClientAttrib() and

glPopClientAttrib()

to push and pop the client attribute stack.

Each constant refers to a group of state variables. Table 3-3 shows the attribute groups with their corresponding symbolic constant names. For a complete list of the OpenGL state variables associated with each constant, see the glPushAttrib reference page.

Table 3-3

State Attribute Groups

Attribute

accumulation buffer clear value color buffer current depth buffer enable evaluators fog

GL_LIST_BASE setting hint variables lighting variables line drawing mode

Constant

GL_ACCUM_BUFFER_BIT

GL_COLOR_BUFFER_BIT

GL_CURRENT_BIT

GL_DEPTH_BUFFER_BIT

GL_ENABLE_BIT

EGL_VAL_BIT

GL_FOG_BIT

GL_LIST_BIT

GL_HINT_BIT

GL_LIGHTING_BIT

GL_LINE_BIT

19

Chapter 3: After toogl: How to Finish Porting to OpenGL

Table 3-3 (continued)

Attribute

pixel mode variables point variables polygon polygon stipple scissor stencil buffer texture transform viewport

— pixel storage modes vertex arrays and enables

State Attribute Groups

Constant

GL_PIXEL_MODE_BIT

GL_POINT_BIT

GL_POLYGON_BIT

GL_POLYGON_STIPPLE_BIT

GL_SCISSOR_BIT

GL_STENCIL_BUFFER_BIT

GL_TEXTURE_BIT

GL_TRANSFORM_BIT

GL_VIEWPORT_BIT

GL_ALL_ATTRIB_BITS

GL_CLIENT_PIXEL_STORE_BITS (1.1 only)

GL_CLIENT_VERTEX_ARRAY_BIT (1.1 only)

To restore the values of the state variables to those saved with the last glPushAttrib(), call

glPopAttrib()

. The variables you didn’t save remain unchanged.

Porting IRIS GL get* Commands

IRIS GL get* calls are of this form: int get

thing

(); int get

things

( int *a, int *b);

Your IRIS GL program probably includes calls that look like the following: thing = get

thing

(); if(get

thing

() == THING) { /* stuff */ } get

things

(&a, &b);

20

Porting IRIS GL get* Commands

OpenGL uses glGet*() calls for equivalent functionality; they look like this: void glGetIntegerfv(NAME_OF_THING, &thing);

Table A-1 on page 109 lists the IRIS GL get functions with their OpenGL equivalents.

In general, this guide lists various parameters for glGet*() calls in the sections that discuss topics related to those parameters. To see the parameter values related to matrices, for example, see “Porting Matrix and Transformation Calls” on page 24.

There are other functions to query the OpenGL state, such as glGetClipPlane() and

glGetLight()

. These commands are discussed in the sections on related calls, and also in the reference pages.

About glGet*()

There are four types of glGet*() functions:

glGetBooleanv()

glGetIntegerv()

glGetFloatv()

glGetDoublev()

The functions have this syntax: glGet<

Datatype

>v(

value

, *

data

)

value is of type GLenum and data of type GLdatatype. If you issue a glGet*() call that returns types different from the expected types, each type is converted appropriately. For a complete list of parameters, see the glGet reference page.

In addition to the basic glGet*() function, there are a number of special purpose information retrieval functions: glGetClipPlane, glGetError, glGetLight, glGetMap, glGetMaterial, glGetPixelMap, glGetPointerv, glGetPolygonStipple, glGetString, glGetTexEnv, glGetTexGen, glGetTexImage, glGetTexlevelParameter, glGetTexParameter.

21

Chapter 3: After toogl: How to Finish Porting to OpenGL

glGet*() Conventions Used in This Book

For the sake of brevity, this guide usually shortens the reference to the form glGet*(

GL_GET_TYPE

)

For example, glGetIntegerv(GL_VIEWPORT, *

params

); is abbreviated as glGet*(GL_VIEWPORT); in tables and text (but not in code examples).

Porting Commands That Required Current Graphics Positions

OpenGL doesn’t maintain a current graphics position. IRIS GL commands that depend on the current graphics position, such as move(), draw(), and rmv(), have no equivalents in OpenGL.

Older versions of IRIS GL included drawing commands that relied upon the current graphics position, though their use was discouraged in more recent versions. You have to reimplement parts of your program if you relied on the current graphics position in any way, or used any of the following routines:

draw()

and move()

pmv()

, pdr(), and pclos()

rdr()

, rmv(), rpdr(), and rpmv()

getgpos()

OpenGL has a concept of raster position that corresponds to the IRIS GL current character position. See “Porting Pixel Operations” on page 46 for more information.

22

Porting Screen and Buffer Clearing Commands

Porting Screen and Buffer Clearing Commands

OpenGL replaces a variety of IRIS GL clear() calls (such as zclear(), aclear(), sclear(), and so on) with one: glClear(). Specify exactly what you want to clear by passing masks to

glClear()

.

When porting screen and buffer clearing commands, consider the following issues:

• OpenGL maintains clear colors separately from drawing colors, with calls like

glClearColor()

and glClearIndex(). Be sure to set the clear color for each buffer before making a clear call.

• Since toogl has no concept of context, it cannot correctly translate color calls immediately preceding clear calls into glClearColor() calls. You have to translate these calls explicitly. For example, suppose your program clears the viewport as follows: color(BLACK); clear();

toogl translates those two lines as follows: glIndex(BLACK); glClear(GL_COLOR_BUFFER_BIT);

A better translation of this fragment the following: glClearIndex(0); glClear(GL_COLOR_BUFFER_BIT);

Remember that IRIS GL color constants, such as BLACK, are not defined in

OpenGL.

• Instead of using one of several differently named clear calls, you now clear several buffers with one call, glClear(), by ORing together buffer masks. For example,

czclear()

is replaced by glClear( GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT )

• IRIS GL respects the polygon stipple and the color write mask. OpenGL ignores the polygon stipple but respects the write mask. czclear() ignored both the polygon stipple and the write mask.

23

Chapter 3: After toogl: How to Finish Porting to OpenGL

Table 3-4 lists the various clear calls with their IRIS GL equivalents.

Table 3-4

Calls for Clearing the Screen

IRIS GL Call OpenGL Call Meaning

acbuf(AC_CLEAR) glClear(GL_ACCUM_BUFFER_BIT) Clear the accumulation buffer.

— glClearColor() glClearIndex()

Set the RGBA clear color.

Set the clear color index.

clear()

— zclear() czclear()

— sclear() glClear(GL_COLOR_BUFFER_BIT) glClearDepth() glClear(GL_DEPTH_BUFFER_BIT)

Clear the color buffer.

Specify the clear value for the depth buffer.

Clear the depth buffer.

glClear(GL_COLOR_BUFFER_BIT |

GL_DEPTH_BUFFER_BIT)

Clear the color buffer and the depth buffer.

glClearAccum() glClearStencil()

Specify clear values for the accumulation buffer.

Specify the clear value for the stencil buffer.

glClear(GL_STENCIL_BUFFER_BIT) Clear the stencil buffer.

If your IRIS GL code used both gclear() and sclear(), you can instead use a single

glClear()

call. As a result, your program’s performance may improve.

Porting Matrix and Transformation Calls

When porting matrix and transformation calls, consider the following issues:

• There is no single-matrix mode. OpenGL is always in double-matrix mode.

• Angles are now measured in degrees, instead of tenths of degrees.

• Projection matrix calls, like glFrustum() and glOrtho(), now multiply with the current matrix, instead of being loaded onto the current matrix.

24

Porting Matrix and Transformation Calls

• The OpenGL call glRotate() is different from rotate(). glRotate() lets you rotate around any arbitrary axis, instead of being confined to the x, y, and z axes. But you probably have to port rotate() calls explicitly, because toogl often doesn’t translate them correctly. For example, toogl might translate rotate(200*(i+1), ’z’); into glRotate(.1*(200*(i+1)), ( ’z’)==’x’, ( ’z’)==’y’,

( ’z’)==’z’);

toogl correctly switched to degrees from tenths of degrees, but didn’t correctly handle the replacement of z

with a vector for the z-axis. A better translation is glRotate(.1*(200*(i+1), 0.0, 0.0, 1.0);

• OpenGL documentation presents matrices in a manner more consistent with standard usage in linear algebra than did IRIS GL documentation. Specifically, in

IRIS GL documentation, vectors are treated as rows, and a matrix is applied to a vector on the right of the vector. multmatrix() replaces the current matrix C with

C’ = MC. In OpenGL documentation, vectors are treated as columns, and a matrix applies to a vector on the left of the vector. glMultMatrix() computes C’ = CM.

A generic IRIS GL translation is shown in the equation in Figure 3-1.

[

xyz1

]

1 0 0 0

0 1 0 0

0 0 1 0

Tx Ty Tz 1

=

[ (

x

+

Tx

) (

y

+

Ty

) (

z

+

Tz

)

1

]

Figure 3-1

Generic IRIS GL Translation

A generic OpenGL translation is shown in the equation in Figure 3-2.

1 0 0

Tx

0 1 0

Ty

0 0 1

Tz

0 0 0 1

z

1

x y

=

x

+

Tx y

+

Ty z

+

Tz

1

Figure 3-2

Generic OpenGL Translation

25

Chapter 3: After toogl: How to Finish Porting to OpenGL

The important thing is that this is a change in documentation only—OpenGL matrices are completely compatible with the ones in IRIS GL except that they are stored in column-major order. So, if you want the matrix shown in the equation in Figure 3-3 in your OpenGL application, you would declare it as follows: float mat[16] = {a, e, i, m, b, f, j, n, c, g, k, o, d, h, l, p}

a b c d a f g h i j k l m n o p

Figure 3-3

OpenGL Matrix Example

• OpenGL has no equivalent to the polarview() call. You can replace such a call with a translation and three rotations. For example, the IRIS GL call polarview(distance, azimuth, incidence, twist); translates to glTranslatef( 0.0, 0.0, -distance); glRotatef( -twist * 10.0, 0.0, 0.0, 1.0); glRotatef( -incidence * 10.0, 1.0, 0.0, 0.0); glRotatef( -azimuth * 10.0, 0.0, 0.0, 1.0);

• The replacement for the lookat() call, gluLookAt(), takes an up vector instead of a twist angle. toogl doesn’t translate this call correctly, so you have to port explicitly.

See the gluLookAt reference page for more information.

Table 3-5 lists the OpenGL matrix calls and their IRIS GL equivalents.

Table 3-5

IRIS GL Call

mmode()

— loadmatrix()

Matrix Operations

OpenGL Call

glMatrixMode() glLoadIdentity() glLoadMatrixf(), glLoadMatrixd()

Meaning

Set current matrix mode.

Replace current matrix with the identity matrix.

Replace current matrix with the specified matrix.

26

Porting Matrix and Transformation Calls

Table 3-5 (continued)

IRIS GL Call

multmatrix() mapw(), mapw2() ortho() ortho2() perspective() picksize() popmatrix() pushmatrix() rotate(), rot() scale() translate() window()

Matrix Operations

OpenGL Call Meaning

glMultMatrixf(), glMultMatrixd() gluUnProject() glOrtho() gluOrtho2D() gluPerspective() gluPickMatrix() glPopMatrix() glPushMatrix() glRotated(), glRotatef()

Post-multiply current matrix with the specified matrix

(note that multmatrix() pre-multiplied).

Project world space coordinates to object space (see also gluProject()).

Multiply current matrix by an orthographic projection matrix.

Define a two-dimensional orthographic projection matrix.

Define a perspective projection matrix.

Define a picking region.

Pop current matrix stack, replacing the current matrix with the one below it.

Push current matrix stack down by one, duplicating the current matrix.

Rotate current coordinate system by the given angle about the vector from the origin through the given point.

Note that rotate() rotated only about the x, y, and z axes.

glScaled(),glScalef() Multiply current matrix by a scaling matrix.

glTranslatef(), glTranslated() glFrustum()

Move coordinate system origin to the specified point by multiplying the current matrix by a translation matrix.

Given coordinates for clipping planes, multiply the current matrix by a perspective matrix.

OpenGL has three matrix modes, which are set with glMatrixMode(). Table 3-6 lists the

IRIS GL mmode() arguments in the first column and the corresponding arguments to

glMatrixMode()

in the second column.

27

Chapter 3: After toogl: How to Finish Porting to OpenGL

Table 3-6

Matrix Modes

IRIS GL Matrix Mode OpenGL Mode

MTEXTURE

MVIEWING

MPROJECTION

GL_TEXTURE

Meaning Min. Stack Depth

Operate on the texture matrix stack. 2

GL_MODELVIEW Operate on the modelview matrix stack.

GL_PROJECTION Operate on the projection matrix stack.

32

2

Porting MSINGLE Mode Code

OpenGL has no equivalent for MSINGLE, single-matrix mode. Though use of this mode has been discouraged, it was the default for IRIS GL and your program may have used it. If it did, you have to reimplement part of it. OpenGL is always in double-matrix mode, and is initially in GL_MODELVIEW mode.

Most IRIS GL code in MSINGLE mode looks as follows:

...

projectionmatrix();

...

projectionmatrix()

is one of the following: ortho(), ortho2(), perspective(), window().

To port to OpenGL, replace the MSINGLE mode projectionmatrix() call by the following pseudo-code:

...

glMatrixMode( GL_PROJECTION ); glLoadMatrix( identity matrix );

[one of these calls: glFrustrum(), glOrtho(), glOrtho2(), gluPerspective()]; glMatrixMode( GL_MODELVIEW ); glLoadMatrix( identity matrix );

28

Porting Matrix and Transformation Calls

Porting get* Calls for Matrices and Transformations

Table 3-7 maps IRIS GL matrix queries to OpenGL matrix queries.

Table 3-7

Arguments for Transformation Matrix Queries

IRIS GL Matrix

Query

getmmode()

OpenGL glGet*() Matrix Query

GL_MODELVIEW_STACK_DEPTH

GL_PROJECTION_STACK_DEPTH

GL_TEXTURE_STACK_DEPTH

Meaning

GL_MATRIX_MODE getmatrix() in

MVIEWING mode

GL_MODELVIEW_MATRIX getmatrix() in

MPROJECTION mode

GL_PROJECTION_MATRIX

Return the current matrix mode.

Return a copy of the current modelview matrix.

Return a copy of the current projection matrix.

getmatrix() in

MTEXTURE mode

GL_TEXTURE_MATRIX

Return a copy of the current texture matrix.

GL_MAX_MODELVIEW_STACK_DEPTH Return maximum supported depth of modelview matrix stack.

GL_MAX_PROJECTION_STACK_DEPTH Return maximum supported depth of projection matrix stack.

— GL_MAX_TEXTURE_STACK_DEPTH Return maximum supported depth of texture matrix stack.

Return number of matrices on modelview stack.

Return number of matrices on projection stack.

Return number of matrices on texture stack.

29

Chapter 3: After toogl: How to Finish Porting to OpenGL

Porting Viewports, Screenmasks, and Scrboxes

The following IRIS GL calls have no direct OpenGL equivalent:

reshapeviewport()

scrbox()

, getscrbox()

The IRIS GL viewport() call had as parameters the x coordinates (in pixels) for the left and right of the viewport rectangle and the y coordinates for the top and bottom. The

OpenGL glViewport() call has as parameters the x and y coordinates (in pixels) of the lower left corner of the viewport rectangle, as well as the rectangle’s width and height.

Table 3-8 lists the OpenGL equivalents for viewport commands.

Table 3-8

IRIS GL Call

viewport(left, right, bottom, top) popviewport() pushviewport() getviewport()

Viewport Calls

OpenGL Call

glViewport(x, y, width, height) glPopAttrib() glPushAttrib(GL_VIEWPORT_BIT) glGet*(GL_VIEWPORT)

Meaning

Set the viewport.

Push and pop the stack.

Return viewport dimensions.

Porting Clipping Planes

OpenGL implements clipping planes the way IRIS GL did, though you can now also query clipping planes. Table 3-9 lists the OpenGL equivalents to IRIS GL calls.

Table 3-9

Clipping Plane Calls

IRIS GL Call OpenGL Call Meaning

clipplane(i, CP_ON, params) clipplane(i, CP_DEFINE, plane) glEnable(GL_CLIP_PLANEi) Enable clipping on plane i. glClipPlane(

GL_CLIP_PLANEi, plane)

Define clipping plane.

— glGetClipPlane() Return clipping plane equation.

30

Porting Drawing Commands

Table 3-9 (continued)

IRIS GL Call

— scrmask() getscrmask()

Clipping Plane Calls

OpenGL Call

glIsEnabled(

GL_CLIP_PLANEi) glScissor() glGet*(GL_SCISSOR_BOX)

Meaning

Return true if clip plane i is enabled.

Define the scissor box.

Return the current scissor box.

To turn on the scissor test, call glEnable() with GL_SCISSOR_BOX as the parameter.

Porting Drawing Commands

The following sections discuss how to port IRIS GL drawing primitives, discussing the following topics:

• “Porting the IRIS GL Sphere Library”

• “Porting v() Commands” on page 33

• “Porting bgn/end Commands” on page 33

• “Porting Points” on page 35

• “Porting Lines” on page 36

• “Porting Polygons and Quadrilaterals” on page 37

• “Porting Tessellated Polygons” on page 41

• “Porting Triangles” on page 41

• “Porting Arcs and Circles” on page 42

• “Porting Spheres” on page 43

Porting the IRIS GL Sphere Library

The sphere library that worked with IRIS GL isn’t available for OpenGL. You can replace sphere library calls with quadrics routines from the GLU library or with the GLUT functions for geometric object rendering. Refer to the OpenGL Programming Guide and the

31

Chapter 3: After toogl: How to Finish Porting to OpenGL

GLU reference pages in the OpenGL Reference Manual for details on using the GLU library.

Table 3-10 summarizes OpenGL quadrics calls.

Table 3-10

Calls for Drawing Quadrics

OpenGL Call Meaning

gluNewQuadric() gluDeleteQuadric() gluQuadricCallback()

Create a new quadric object.

Delete a quadric object.

Associate a callback with a quadric object, for error handling.

gluQuadricNormals() Specify normals: no normals, one per face, or one per vertex.

gluQuadricOrientation() Specify direction of normals: outward or inward.

gluQuadricTexture() Turn texture coordinate generation on or off.

gluQuadricDrawstyle() Specify drawing style: polygons, lines, points, and so on.

gluSphere() gluCylinder() gluPartialDisk() gluDisk()

Draw a sphere.

Draw a cylinder or cone.

Draw an arc.

Draw a circle or disk.

You can use one quadric object for all quadrics you’d like to render in similar ways. The code fragment in Example 3-1 uses two quadrics objects to draw four quadrics, two of them textured.

Example 3-1

Drawing Quadrics Objects

GLUquadricObj *texturedQuad, *plainQuad; texturedQuad = gluNewQuadric(void); gluQuadricTexture(texturedQuad, GL_TRUE); gluQuadricOrientation(texturedQuad, GLU_OUTSIDE); gluQuadricDrawStyle(texturedQuad, GLU_FILL); plainQuad = gluNewQuadric(void); gluQuadricDrawStyle(plainQuad, GLU_LINE); glColor3f (1.0, 1.0, 1.0);

32

Porting Drawing Commands gluSphere(texturedQuad, 5.0, 20, 20); glTranslatef(10.0, 10.0, 0.0); gluCylinder(texturedQuad, 2.5, 5, 5, 10, 10); glTranslatef(10.0, 10.0, 0.0); gluDisk(plainQuad, 2.0, 5.0, 10, 10); glTranslatef(10.0, 10.0, 0.0); gluSphere(plainQuad, 5.0, 20, 20);

Porting v() Commands

In IRIS GL, you use variations on the v() call to specify vertices. The OpenGL glVertex() call is a direct successor of this call: glVertex2[d|f|i|s][v]( x, y ); glVertex3[d|f|i|s][v]( x, y, z); glVertex4[d|f|i|s][v]( x, y, z, w);

glVertex()

takes suffixes the same way other OpenGL calls do. The vector versions of the call take arrays of the proper size as arguments. In the 2D version, z = 0 and w = 1. In the

3D version, w = 1.

Porting bgn/end Commands

IRIS GL uses the begin/end paradigm but has a different call for each graphics primitive.

For example, bgnpolygon() and endpolygon() draw polygons, and bgnline() and

endline()

draw lines. In OpenGL, you use the glBegin()/glEnd() structure. OpenGL draws most geometric objects by enclosing a series of calls that specify vertices, normals, textures, and colors between pairs of glBegin() and glEnd() calls.

void glBegin( GLenum mode) ;

/* vertex list, colors, normals, textures, materials */ void glEnd( void );

glBegin()

takes a single argument that specifies the drawing mode, and thus the primitive. Here’s an OpenGL code fragment that draws a polygon and then a line: glBegin( GL_POLYGON) ;

glVertex2f(20.0, 10.0);

glVertex2f(10.0, 30.0);

glVertex2f(20.0, 50.0);

glVertex2f(40.0, 50.0);

glVertex2f(50.0, 30.0);

33

Chapter 3: After toogl: How to Finish Porting to OpenGL

glVertex2f(40.0, 10.0); glEnd(); glBegin( GL_LINES ) ;

glVertex2i(100,100);

glVertex2i(500,500); glEnd();

In OpenGL, you draw different geometric objects by specifying different arguments to

glBegin()

. These arguments are listed in Table 3-11 below, along with the IRIS GL calls they replace (if any). There is no limit to the number of vertices you can specify between a glBegin()/glEnd() pair.

Table 3-11

Calls for Drawing Primitives

IRIS GL Call Value of glBegin() Mode Meaning

bgnpoint() bgnline()

GL_POINTS

GL_LINE_STRIP bgnclosedline() GL_LINE_LOOP

— GL_LINES

Individual points

Series of connected line segments

Series of connected line segments, with a segment added between first and last vertices

Pairs of vertices interpreted as individual line segments bgnpolygon() GL_POLYGON

— GL_TRIANGLES bgntmesh()

GL_TRIANGLE_STRIP

GL_TRIANGLE_FAN

Boundary of a simple convex polygon

Triples of vertices interpreted as triangles

Linked strips of triangles

Linked fans of triangles

— bgnqstrip()

GL_QUADS

GL_QUAD_STRIP

Quadruples of vertices interpreted as quadrilaterals

Linked strips of quadrilaterals

For a detailed discussion of the differences between triangle meshes, strips, and fans, see

“Porting Triangles” on page 41.

34

Porting Drawing Commands

In addition to specifying vertices inside a glBegin()/glEnd() pair, you can also specify a current normal, current texture coordinates, and a current color. Table 3-12 lists the commands valid inside a glBegin()/glEnd() pair.

Table 3-12

Valid Commands Inside a Begin/End Structure

IRIS GL Call

v2*(), v3*(), v4*()

RGBcolor(), cpack() color(), colorf() n3f()

OpenGL Equivalent

glVertex*() glColor*() glIndex*() glNormal*() glEvalCoord() callobj()

Meaning

Set vertex coordinates.

Set current color.

Set current color index.

Set normal vector coordinates.

Evaluate enabled one- and two-dimensional maps.

Execute display list(s).

t2()

— lmbind() glCallList(), glCallLists() glTexCoord() glEdgeFlag() glMaterial()

Set texture coordinates.

Control drawing edges.

Set material properties.

If you use any other OpenGL command inside a glBegin()/glEnd() pair, results are unpredictable and an error may result.

Porting Points

OpenGL has no command to draw a single point. Otherwise, porting point calls is straightforward. Table 3-13 lists commands for drawing points.

Table 3-13

IRIS GL Call

pnt() bgnpoint(), endpoint()

Calls for Drawing Points

OpenGL Equivalent

— glBegin(GL_POINTS), glEnd()

Meaning

Draw a single point.

Interpret vertices as points.

35

Chapter 3: After toogl: How to Finish Porting to OpenGL

Table 3-13 (continued)

IRIS GL Call

pntsize() pntsmooth()

Calls for Drawing Points

OpenGL Equivalent Meaning

glPointSize() Set point size in pixels.

glEnable(GL_POINT_SMOOTH) Turn on point antialiasing (see “Porting

Antialiasing Calls” on page 58).

See the glPointSize reference page for information about related glGet*() commands.

Porting Lines

Porting code that draws lines is fairly straightforward, though you should note the differences in the way OpenGL does stipples.

Table 3-14

Calls for Drawing Lines

IRIS GL Call OpenGL Call Meaning

bgnclosedline(), endclosedline() glBegin(GL_LINE_LOOP) glEnd() bgnline() glBegin(GL_LINE_STRIP) linewidth() getlwidth() deflinestyle() setlinestyle() lsrepeat() glLineWidth() glGet*(GL_LINE_WIDTH) glLineStipple(factor, pattern) getlstyle() getlsrepeat() linesmooth(), smoothline()

Draw a closed line.

Draw line segments.

Set line width.

Return current line width.

Specify a line stipple pattern.

factor argument of glLineStipple() Set a repeat factor for the line style.

glGet*(GL_LINE_STIPPLE_PATTERN) Return line stipple pattern.

glGet*(GL_LINE_STIPPLE_REPEAT) Return repeat factor.

glEnable(GL_LINE_SMOOTH) Turn on line antialiasing (see “Porting

Antialiasing Calls” on page 58).

There are no tables for line stipples. OpenGL maintains only one line stipple pattern. You can use glPushAttrib() and glPopAttrib() to switch between different stipple patterns.

36

Porting Drawing Commands

Old-style line style routines are not supported by OpenGL. If you used the calls: draw(),

lsbackup()

, getlsbackup(), resetls(), getresetls(), reimplement that part of your program.

For information on drawing antialiased lines, see “Porting Antialiasing Calls” on page 58.

Porting Polygons and Quadrilaterals

When porting polygons and quadrilaterals, consider the following issues:

• There is no direct equivalent for concave(TRUE)

. Consider using the GLU tessellation routines described in “Porting Tessellated Polygons” on page 41.

• Polygon modes are now set differently.

• These older polygon drawing calls have no direct equivalents in OpenGL:

– the poly() family of routines

– the polf() family of routines

pmv()

, pdr(), and pclos()

rpmv()

and rpdr()

splf()

spclos()

If you used these calls, reimplement that part of the program using glBegin(GL_POLYGON)

.

Table 3-15 lists the OpenGL equivalents to IRIS GL polygon drawing calls.

Table 3-15

IRIS GL Call

bgnpolygon(), endpolygon()

— bgnqstrip(), endqstrip()

Calls for Drawing Polygons

OpenGL Equivalent Meaning

glBegin(GL_POLYGON), glEnd()

Vertices define boundary of a simple convex polygon.

glBegin(GL_QUADS), glEnd() Interpret quadruples of vertices as quadrilaterals.

glBegin(GL_QUAD_STRIP), glEnd()

Interpret vertices as linked strips of quadrilaterals.

37

Chapter 3: After toogl: How to Finish Porting to OpenGL

Table 3-15

IRIS GL Call

— polymode() rect(), rectf() sbox(), sboxf()

Calls for Drawing Polygons

OpenGL Equivalent

glEdgeFlag() glPolygonMode() glRect()

Meaning

Set polygon drawing mode.

Draw a rectangle.

Draw a screen-aligned rectangle.

Setting Polygon Modes

The call for setting the polygon mode has changed slightly. The OpenGL call

glPolygonMode()

allows you to specify which side of a polygon (front or back) the mode applies to. Its syntax is void glPolygonMode( GLenum

face

, GLenum

mode

)

face is one of the following:

GL_FRONT Mode applies to front-facing polygons.

GL_BACK Mode applies to back-facing polygons.

GL_FRONT_AND_BACK Mode applies to both front- and back-facing polygons.

The equivalents to IRIS GL polymode() calls would use GL_FRONT_AND_BACK.

Table 3-16 lists IRIS GL polygon modes and the corresponding OpenGL modes.

Table 3-16

IRIS GL Mode

PYM_POINT

PYM_LINE

PYM_FILL

PYM_HOLLOW

Polygon Modes

OpenGL Mode

GL_POINT

GL_LINE

GL_FILL

Meaning

Draw vertices as points.

Draw boundary edges as line segments.

Draw polygon interior filled.

Fill only interior pixels at the boundaries.

38

Porting Drawing Commands

Setting Polygon Stipples

When porting polygon stipples, consider the following issues:

• There are no tables for polygon stipples. OpenGL keeps only one stipple pattern.

You can use display lists to store different stipple patterns.

• The polygon stipple bitmap size is always a 32 x 32 bit pattern.

• Stipple encoding is affected by glPixelStore(). See “Porting Pixel Operations” on page 46 for more information.

Table 3-17 lists polygon stipple calls.

Table 3-17

IRIS GL Call

defpattern() setpattern() getpattern()

Polygon Stipple Calls

OpenGL Call

glPolygonStipple()

Meaning

Set the stipple pattern.

— OpenGL keeps only one polygon stipple pattern.

glGetPolygonStipple() Return the stipple bitmap (used to return an index).

Enable and disable polygon stippling by passing GL_POLYGON_STIPPLE as an argument to glEnable() and glDisable().

Example 3-2 shows an OpenGL code fragment that demonstrates polygon stippling.

Example 3-2

OpenGL Polygon Stippling

/* polys.c */

#include <GL/gl.h>

#include <GL/glu.h> void display(void)

{

GLubyte fly[] = {

0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00, 0x00,

0x03, 0x80, 0x01, 0xC0, 0x06, 0xC0, 0x03, 0x60,

0x04, 0x60, 0x06, 0x20, 0x04, 0x30, 0x0C, 0x20,

0x04, 0x18, 0x18, 0x20, 0x04, 0x0C, 0x30, 0x20,

0x04, 0x06, 0x60, 0x20, 0x44, 0x03, 0xC0, 0x22,

0x44, 0x01, 0x80, 0x22, 0x44, 0x01, 0x80, 0x22,

0x44, 0x01, 0x80, 0x22, 0x44, 0x01, 0x80, 0x22,

39

Chapter 3: After toogl: How to Finish Porting to OpenGL

0x44, 0x01, 0x80, 0x22, 0x44, 0x01, 0x80, 0x22,

0x66, 0x01, 0x80, 0x66, 0x33, 0x01, 0x80, 0xCC,

0x19, 0x81, 0x81, 0x98, 0x0C, 0xC1, 0x83, 0x30,

0x07, 0xe1, 0x87, 0xe0, 0x03, 0x3f, 0xfc, 0xc0,

0x03, 0x31, 0x8c, 0xc0, 0x03, 0x33, 0xcc, 0xc0,

0x06, 0x64, 0x26, 0x60, 0x0c, 0xcc, 0x33, 0x30,

0x18, 0xcc, 0x33, 0x18, 0x10, 0xc4, 0x23, 0x08,

0x10, 0x63, 0xC6, 0x08, 0x10, 0x30, 0x0c, 0x08,

0x10, 0x18, 0x18, 0x08, 0x10, 0x00, 0x00, 0x08

};

GLubyte halftone[] = {

0xAA, 0xAA, 0xAA, 0xAA, 0x55, 0x55, 0x55, 0x55,

0xAA, 0xAA, 0xAA, 0xAA, 0x55, 0x55, 0x55, 0x55,

0xAA, 0xAA, 0xAA, 0xAA, 0x55, 0x55, 0x55, 0x55,

0xAA, 0xAA, 0xAA, 0xAA, 0x55, 0x55, 0x55, 0x55,

0xAA, 0xAA, 0xAA, 0xAA, 0x55, 0x55, 0x55, 0x55,

0xAA, 0xAA, 0xAA, 0xAA, 0x55, 0x55, 0x55, 0x55,

0xAA, 0xAA, 0xAA, 0xAA, 0x55, 0x55, 0x55, 0x55,

0xAA, 0xAA, 0xAA, 0xAA, 0x55, 0x55, 0x55, 0x55,

0xAA, 0xAA, 0xAA, 0xAA, 0x55, 0x55, 0x55, 0x55,

0xAA, 0xAA, 0xAA, 0xAA, 0x55, 0x55, 0x55, 0x55,

0xAA, 0xAA, 0xAA, 0xAA, 0x55, 0x55, 0x55, 0x55,

0xAA, 0xAA, 0xAA, 0xAA, 0x55, 0x55, 0x55, 0x55,

0xAA, 0xAA, 0xAA, 0xAA, 0x55, 0x55, 0x55, 0x55,

0xAA, 0xAA, 0xAA, 0xAA, 0x55, 0x55, 0x55, 0x55,

0xAA, 0xAA, 0xAA, 0xAA, 0x55, 0x55, 0x55, 0x55,

0xAA, 0xAA, 0xAA, 0xAA, 0x55, 0x55, 0x55, 0x55

};

glClear (GL_COLOR_BUFFER_BIT);

glColor3f (1.0, 1.0, 1.0); /* draw all polys in white */

/* draw 1 solid unstippled rectangle, then 2 stippled ones*/

glRectf (25.0, 25.0, 125.0, 125.0);

glEnable (GL_POLYGON_STIPPLE);

glPolygonStipple (fly);

glRectf (125.0, 25.0, 225.0, 125.0);

glPolygonStipple (halftone);

glRectf (225.0, 25.0, 325.0, 125.0);

glDisable (GL_POLYGON_STIPPLE);

glFlush ();

}

40

Porting Drawing Commands

Porting Tessellated Polygons

The GLU has routines you can use to draw concave polygons. You no longer just use

concave(TRUE)

and then bgnpolygon().

To draw a concave polygon with OpenGL, follow these steps:

1.

Create a tesselation object.

2. Define callbacks that will be used to process the triangles generated by the tessellator.

3. Specify the concave polygon to be tessellated.

Table 3-18 lists the calls for drawing tessellated polygons.

Table 3-18

Tessellated Polygon Calls

GLU Call

gluNewTess() gluDeleteTess() gluTessCallback() gluBeginPolygon() gluTessVertex() gluNextContour() gluEndPolygon()

Meaning

Create a new tessellation object.

Delete a tessellation object.

Begin the polygon specification.

Specify a polygon vertex. Successive gluTessVertex() calls describe a closed contour.

Indicate that the next series of vertices describe a new contour.

End the polygon specification.

For details, see the reference pages for the commands in Table 3-18.

Porting Triangles

OpenGL provides three ways to draw triangles: separate triangles, triangle strips, and triangle fans.

41

Chapter 3: After toogl: How to Finish Porting to OpenGL

When porting triangles, consider the following issues:

• There’s no OpenGL equivalent for swaptmesh(). Instead, use a combination of triangles, triangle strips, and triangle fans.

• If your IRIS GL program draws individual triangles by surrounding each triangle with a bgntmesh() / endtmesh() pair, surround the entire group of individual triangles with just one glBegin(GL_TRIANGLES) / glEnd()

pair in your OpenGL program, for a noticeable performance increase.

Table 3-19 lists the commands for drawing triangles.

Table 3-19

IRIS GL Call

— bgntmesh(), endtmesh()

Calls for Drawing Triangles

Equivalent glBegin() Argument

GL_TRIANGLES

GL_TRIANGLE_STRIP

GL_TRIANGLE_FAN

Meaning

Triples of vertices interpreted as triangles.

Linked strips of triangles.

Linked fans of triangles.

Porting Arcs and Circles

In OpenGL, filled arcs and circles are drawn with the same calls as unfilled arcs and circles. See the reference pages for specifics. Table 3-20 lists the IRIS GL arc and circle commands and the corresponding OpenGL (GLU) commands.

Table 3-20

IRIS GL Call

arc(), arcf() circ(), circf()

Calls for Drawing Arcs and Circles

OpenGL Call

gluPartialDisk() gluDisk()

Meaning

Draw an arc.

Draw a circle or disk.

The gluPartialDisk() call is different from the arc() call. See the gluPartialDisk reference page for complete information.

IRIS GL arcs and circles are called disks and partial disks in OpenGL. You can do some things with OpenGL disks and partial disks that you could not do with IRIS GL. See the

42

.

Porting Drawing Commands

OpenGL Programming Guide and the reference pages in the OpenGL Reference Manual for detailed information.

When porting arcs and circles, consider these issues:

• Angles are no longer measured in tenths of degrees, but simply in degrees.

• The start angle is measured from the positive y axis, and not from the x axis.

• The sweep angle is now clockwise instead of counterclockwise, as shown in

Figure 3-4.

y axis

900 y axis

0

1800 0 x axis

270 90 x axis

2700 180

Figure 3-4

IRIS GL angles in degrees

OpenGL angles in degrees

Drawing Angles: Comparing IRIS GL and OpenGL

Porting Spheres

When porting spheres, consider these issues:

• In OpenGL, you cannot control the type of primitives used to draw the sphere.

Instead, you can control drawing precision by using the slices and stacks parameters.

Slices are longitudinal; stacks are latitudinal.

• Spheres are now drawn centered at the origin. Instead of specifying the location, as you used to in sphdraw() calls, precede a gluSphere() call with a translation.

• The sphere library isn’t yet available for OpenGL—see “Porting the IRIS GL Sphere

Library” on page 31 for more information about replacing sphere library calls.

43

Chapter 3: After toogl: How to Finish Porting to OpenGL

Table 3-21 lists the IRIS GL calls for drawing spheres along with the corresponding GLU calls where available.

Table 3-21

IRIS GL Call

sphobj() sphfree() sphdraw() sphmode() sphrotmatrix() sphgnpolys()

Calls for Drawing Spheres

GLU Call Notes

— gluNewQuadric() Create a new sphere object.

gluDeleteQuadric() Delete sphere object and free memory used.

gluSphere() Draw a sphere.

Set sphere attributes.

Control sphere orientation.

Return number of polygons in current sphere.

Porting Color, Shading, and Writemask Commands

When porting color, shading, and writemask calls, note that color map implementation differs between OpenGL and IRIS GL and consider these issues:

• Although you can set color map indices with the OpenGL glIndex() call, OpenGL doesn’t provide a routine for loading color map indices. See “Using X Color Maps” on page 105 for an example code fragment that sets up a color map.

• Color values are normalized to their data type. See the glColor reference page for details.

• There is no simple equivalent for cpack(). You can use glColor() instead, but you have to port explicitly.

• Some calls to c() or color() may have to be translated to glClearColor() or

glClearIndex()

and not glColor() or glIndex(). See “Porting Screen and Buffer

Clearing Commands” on page 23 for details.

• The RGBA writemask is not for each bit, just for each component.

• IRIS GL provided defined color constants: BLACK, BLUE, RED, GREEN,

MAGENTA, CYAN, YELLOW, and WHITE. OpenGL doesn’t provide these constants and toogl doesn’t translate them, so you have to port them explicitly.

44

Porting Color, Shading, and Writemask Commands

Porting Color Calls

Table 3-22 lists IRIS GL color calls and their OpenGL equivalents.

Table 3-22

Color Calls

IRIS GL Call

c3*(), c4*()

OpenGL Call

glColor*() color(), colorf() glIndex*() getcolor() glGet*(GL_CURRENT_INDEX) getmcolor() XQueryColor()

Meaning

Sets RGB color.

Sets the color index.

Returns the current color index.

Gets a copy of a colormap entry’s RGB values.

gRGBcolor() mapcolor()

RGBcolor() writemask() glGet*(GL_CURRENT_COLOR)

XStoreColor() glColor() glIndexMask()

Gets the current RGB color values.

See “Using X Color Maps” on page 105.

Sets RGB color.

Sets the color index mode color mask.

wmpack()

RGBwritemask() glColorMask() Sets the RGB color mode mask.

getwritemask() glGet*(GL_COLOR_WRITEMASK) glGet*(GL_INDEX_WRITEMASK)

Gets the color mask.

gRGBmask() zwritemask() glGet*(GL_COLOR_WRITEMASK) Gets the color mask.

glDepthMask() —

Note:

Be careful when replacing zwritemask() with glDepthMask(): glDepthMask() takes a boolean argument; zwritemask() takes a bitfield.

If you want to use multiple color maps, use the X colormap facilities. The functions

multimap()

, onemap(), getcmmode(), setmap(), and getmap() have no OpenGL equivalents.

45

Chapter 3: After toogl: How to Finish Porting to OpenGL

Porting Shading Models

Just like IRIS GL, OpenGL lets you switch between smooth (Gouraud) shading and flat shading. Table 3-23 lists the calls.

Table 3-23

Shading and Dithering

IRIS GL Call

shademodel(FLAT)

OpenGL Call

glShadeModel(GL_FLAT)

Meaning

Do flat shading.

shademodel(GOURAUD) glShadeModel(GL_SMOOTH) Do smooth shading.

getsm() glGet*(GL_SHADE_MODEL) Return current shade model.

dither(DT_ON) dither(DT_OFF) glEnable(GL_DITHER) glDisable(GL_DITHER)

Turn dithering on/off.

Smooth shading and dithering are on by default, as in IRIS GL.

Porting Pixel Operations

When porting pixel operations, consider the following issues:

• Logical pixel operations are not applied to RGBA color buffers. See the glLogicOp reference page for more information.

• In general, IRIS GL used the ABGR format for pixels (that is, with color components in the order Alpha, Blue, Green, Red), while OpenGL uses the RGBA format.

Although glPixelStore() can reverse the order of bytes within a color component, it can’t reverse the order of the components within a pixel; thus, it can’t be used to convert IRIS GL pixels to OpenGL pixels. Instead, you must reverse the order of the components yourself.

• When porting lrectwrite() calls, be careful to note where lrectwrite() is writing (for instance, it could be writing to the depth buffer).

• If you wanted to read from the z-buffer in IRIS GL, you specified that buffer with

readsource()

and then used lrectread() or rectread() to do the reading. If you want to read from the z-buffer in OpenGL, you simply specify that buffer as a parameter to glReadPixels().

46

Porting Pixel Operations

OpenGL provides some additional flexibility in pixel operations. Table 3-24 lists calls for pixel operations.

Table 3-24

Pixel Operations

IRIS GL Call OpenGL Call Meaning

lrectread(), rectread(), readRGB() cmov() readsource() pixmode() pixmode() logicop()

— glReadPixels() lrectwrite(), rectwrite() glDrawPixels() rectcopy() rectzoom() glCopyPixels() glPixelZoom()

Read a block of pixels from the frame buffer.

Write a block of pixels to the frame buffer.

Copy pixels in the frame buffer.

Specify pixel zoom factors for glDrawPixels() and glCopyPixels().

glRasterPos() glReadBuffer() glPixelStore() glPixelTransfer()

Specify raster position for pixel operations.

Select a color buffer source for pixels.

Set pixel storage modes.

Set pixel transfer modes.

glLogicOp() Specify a logical operation for pixel writes.

glEnable(GL_LOGIC_OP) Turn on pixel logic operations.

See the reference page for glLogicOp for a list of possible logical operations.

Here’s a code fragment that shows a typical pixel write operation: unsigned long *packedRaster;

...

packedRaster[k] = 0x00000000;

...

lrectwrite(0, 0, xSize, ySize, packedRaster);

Here is how toogl translates the call to lrectwrite():

/* OGLXXX lrectwrite: see man page for glDrawPixels */ glRasterPos2i(0, 0); glDrawPixels(( xSize)-(0)+1, ( ySize)-( 0)+1, GL_RGBA,

GL_UNSIGNED_BYTE, packedRaster);

47

Chapter 3: After toogl: How to Finish Porting to OpenGL

After some tweaking, the finished code might look like this: glRasterPos2i(0, 0); glDrawPixels(xSize + 1, ySize + 1, GL_RGBA,

GL_UNSIGNED_BYTE, packedRaster);

Porting Depth Cueing and Fog Commands

When porting depth cueing and fog commands, consider these issues:

• The fog calls have been restructured, so you have to rewrite them explicitly in most cases. The IRIS GL call fogvertex() set a mode and parameters affecting that mode.

In OpenGL, you call glFog() once to set the mode, then again twice or more to set various parameters.

• Depth cueing is no longer a separate feature. Use linear fog instead of depth cueing.

(This section provides an example of how to do this.) The following calls therefore have no direct OpenGL equivalent:

depthcue()

lRGBrange()

lshaderange()

getdcm()

• To adjust fog quality, call glHint(GL_FOG_HINT)

.

Table 3-25 lists the IRIS GL calls for managing fog along with the corresponding OpenGL calls.

Table 3-25

Calls for Managing Fog

IRIS GL Call

fogvertex() fogvertex(FG_ON) fogvertex(FG_OFF) depthcue()

OpenGL Call

glFog() glEnable(GL_FOG) glDisable(GL_FOG) glFog(GL_FOG_MODE,

GL_LINEAR)

Meaning

Set various fog parameters.

Turn fog on.

Turn fog off.

Use linear fog for depth cueing.

48

Porting Depth Cueing and Fog Commands

Table 3-26 lists the arguments you can pass to glFog().

Table 3-26

Fog Parameters

Fog Parameter

GL_FOG_DENSITY

GL_FOG_START

GL_FOG_END

GL_FOG_INDEX

GL_FOG_COLOR

GL_FOG_MODE

Meaning

Fog density.

Near distance for linear fog.

Far distance for linear fog.

Fog color index.

Fog RGBA color.

Fog mode.

Default

1.0

0.0

1.0

0.0

(0, 0, 0, 0) see Table 3-27

The OpenGL fog density argument differs from the IRIS GL fog density argument. They are related as follows:

• If fogMode is EXP2: openGLfogDensity = (IRISGLfogDensity) (sqrt( - log( 1 / 255 ) ))

• If fogMode is EXP: openGLfogDensity = (IRISGLfogDensity) (- log( 1 / 255 ) ) where

sqrt log

IRISGLfogDensity openGLfogDensity

Is the square root operation.

Is the natural logarithm.

Is the IRIS GL fog density.

Is the OpenGL fog density.

To switch between calculating fog in per-pixel mode and per-vertex mode, use glHint(GL_FOG_HINT

,

hintMode). Two hint modes are available:

GL_NICEST per-pixel fog calculation

GL_FASTEST per-vertex fog calculation

49

Chapter 3: After toogl: How to Finish Porting to OpenGL

Table 3-27 lists the OpenGL equivalents for IRIS GL fog modes.

Table 3-27

Fog Modes

IRIS GL Fog Mode OpenGL Fog Mode Hint Mode

FG_VTX_EXP,

FG_PIX_EXP

FG_VTX_EXP2,

FG_PIX_EXP2

FG_VTX_LIN,

FG_PIX_LIN

GL_EXP

GL_EXP2

GL_LINEAR

GL_FASTEST,

GL_NICEST

GL_FASTEST,

GL_NICEST

GL_FASTEST,

GL_NICEST

Meaning

Heavy fog mode (default)

Haze mode

Linear fog mode (use for depthcueing)

Example 3-3 shows a code fragment that demonstrates depth cueing in OpenGL.

Example 3-3

Depth Cueing in OpenGL

/*

* depthcue.c

* This program draws a wireframe model, which uses

* intensity (brightness) to give clues to distance.

* Fog is used to achieve this effect.

*/

#include <stdlib.h>

#include <GL/glut.h>

/* Initialize linear fog for depth cueing.

*/ void myinit(void)

{

GLfloat fogColor[4] = {0.0, 0.0, 0.0, 1.0};

glEnable(GL_FOG);

glFogi(GL_FOG_MODE, GL_LINEAR);

glHint(GL_FOG_HINT, GL_NICEST); /* per pixel */

glFogf(GL_FOG_START, 3.0);

glFogf(GL_FOG_END, 5.0);

glFogfv(GL_FOG_COLOR, fogColor);

glClearColor(0.0, 0.0, 0.0, 1.0);

glDepthFunc(GL_LESS);

glEnable(GL_DEPTH_TEST);

50

Porting Depth Cueing and Fog Commands

glShadeModel(GL_FLAT);

}

/* display() draws an icosahedron.

*/ void display(void)

{

glClear(GL_COLOR_BUFFER_BIT|GL_DEPTH_BUFFER_BIT);

glColor3f(1.0, 1.0, 1.0);

glutWireIcosahedron();

glFlush();

} void myReshape(int w, int h)

{

glViewport(0, 0, w, h);

glMatrixMode(GL_PROJECTION);

glLoadIdentity();

gluPerspective(45.0, (GLfloat)w/(GLfloat)h, 3.0, 5.0);

glMatrixMode(GL_MODELVIEW);

glLoadIdentity();

glTranslatef(0.0, 0.0, -4.0); /* move object into view */

}

/* Main Loop

*/ int main(int argc, char** argv)

{

glutInit(&argc, argv);

glutInitDisplayMode (GLUT_SINGLE|GLUT_RGB|GLUT_DEPTH);

glutCreateWindow(argv[0]);

myinit();

glutReshapeFunc(myReshape);

glutDisplayFunc(display);

glutMainLoop();

return 0; /* ANSI C requires main to return int. */

}

51

Chapter 3: After toogl: How to Finish Porting to OpenGL

Porting Curve and Surface Commands

OpenGL doesn’t support equivalents to the old-style curves and surface patches. You have to reimplement your code if it uses any of these calls:

defbasis()

curvebasis()

, curveprecision(), crv(), crvn(), rcrv(), rcrvn(), and curveit()

patchbasis()

, patchcurves(), patchprecision(), patch(), and rpatch()

Silicon Graphics recommends that you reimplement these calls using evaluators, rather than trying to replace them with NURBS. Refer to the OpenGL Reference Manual and to the section “Evaluators” on page 440 of the OpenGL Programming Guide, Second Edition, for more information on using evaluators.

NURBS Objects

OpenGL treats NURBS as objects, similar to the way it treats quadrics: you create a

NURBS object and then specify how it should be rendered. Table 3-28 lists the NURBS object commands.

Table 3-28

Calls for Managing NURBS Objects

OpenGL Call Meaning

gluNewNurbsRenderer() Create a new NURBS object.

gluDeleteNurbsRenderer() Delete a NURBS object.

gluNurbsCallback() Associate a callback for error handling with a NURBS object.

When using NURBS objects, consider the following issues:

• NURBS control points are now floats, not doubles.

• The stride parameter is now counted in floats, not bytes.

• If you’re using lighting and you’re not specifying normals, call glEnable() with

GL_AUTO_NORMAL as the parameter to generate normals automatically.

52

Porting Curve and Surface Commands

NURBS Curves

The OpenGL calls for drawing NURBS are similar to the IRIS GL calls. You specify knot sequences and control points using a gluNurbsCurve() call, which must be contained within a glBeginCurve()/glEndCurve() pair.

Table 3-29 summarizes the calls for drawing NURBS curves.

Table 3-29

IRIS GL Call

bgncurve() nurbscurve() endcurve()

Calls for Drawing NURBS Curves

OpenGL Call

gluBeginCurve() gluNurbsCurve() gluEndCurve()

Meaning

Begin a curve definition.

Specify curve attributes.

End a curve definition.

Position, texture, and color coordinates are associated by presenting each as a separate

gluNurbsCurve()

inside the begin/end pair. You can make no more than one call to

gluNurbsCurve()

for each piece of color, position, and texture data within a single

gluBeginCurve()

/gluEndCurve() pair. You must make exactly one call to describe the position of the curve (a GL_MAP1_VERTEX_3 or GL_MAP1_VERTEX_4 description).

When you call gluEndCurve(), the curve will be tessellated into line segments and then rendered.

Table 3-30 lists NURBS curve types.

Table 3-30

IRIS GL Type

N_V3D

N_V3DR

NURBS Curve Types

OpenGL Type Meaning

GL_MAP1_VERTEX_3

GL_MAP1_VERTEX_4

Polynomial curve.

Rational curve.

GL_MAP1_TEXTURE_COORD_* Control points are texture coordinates.

GL_MAP1_NORMAL Control points are normals.

For more information on available evaluator types, see the glMap1 reference page.

53

Chapter 3: After toogl: How to Finish Porting to OpenGL

Trimming Curves

OpenGL trimming curves are similar to IRIS GL trimming curves. Table 3-31 lists the calls for defining trimming curves.

Table 3-31

IRIS GL Call

bgntrim() pwlcurve() nurbscurve() endtrim()

Calls for Drawing NURBS Trimming Curves

OpenGL Call

gluBeginTrim() gluPwlCurve() gluNurbsCurve() gluEndTrim()

Meaning

Begin trimming curve definition.

Define a piecewise linear curve.

Specify trimming curve attributes.

End trimming curve definition.

NURBS Surfaces

Table 3-32 summarizes the calls for drawing NURBS surfaces.

Table 3-32

IRIS GL Call

bgnsurface() nurbssurface() endsurface()

Calls for Drawing NURBS Surfaces

OpenGL Call

gluBeginSurface() gluNurbsSurface() gluEndSurface()

Meaning

Begin a surface definition.

Specify surface attributes.

End a surface definition.

Table 3-33 lists parameters for surface types.

Table 3-33

NURBS Surface Types

IRIS GL Type OpenGL Type

N_V3D

N_V3DR

N_C4D

GL_MAP2_VERTEX_3

GL_MAP2_VERTEX_4

GL_MAP2_COLOR_4

Meaning

Polynomial curve

Rational curve

Control points define color surface in

(R,G,B,A) form

54

Porting Curve and Surface Commands

Table 3-33 (continued)

NURBS Surface Types

IRIS GL Type OpenGL Type

N_C4DR

N_T2D

N_T2DR

Meaning

GL_MAP2_TEXTURE_COORD_2 Control points are texture coordinates.

GL_MAP2_TEXTURE_COORD_3 Control points are texture coordinates.

GL_MAP2_NORMAL Control points are normals.

For more information on available evaluator types, see the glMap2 reference page.

Example 3-4 draws a trimmed NURBS surface.

Example 3-4

Drawing an OpenGL NURBS surface

/*

* trim.c

* This program draws a NURBS surface in the shape of a

* symmetrical hill, using both a NURBS curve and pwl

* (piecewise linear) curve to trim part of the surface.

*/

#include <stdlib.h>

#include <GL/glut.h>

#include <stdio.h>

GLfloat ctlpoints[4][4][3];

GLUnurbsObj *theNurb;

/*

* Initializes the control points of the surface to a small hill.

* The control points range from -3 to +3 in x, y, and z

*/ void init_surface(void)

{

int u, v;

for (u = 0; u < 4; u++) {

for (v = 0; v < 4; v++) {

ctlpoints[u][v][0] = 2.0 * ((GLfloat)u - 1.5);

ctlpoints[u][v][1] = 2.0 * ((GLfloat)v - 1.5);

if ((u == 1 || u == 2) && (v == 1 || v == 2))

55

Chapter 3: After toogl: How to Finish Porting to OpenGL

ctlpoints[u][v][2] = 3.0;

else

ctlpoints[u][v][2] = -3.0;

}

}

} void nurbsError(GLenum errorCode)

{

const GLubyte *estring;

estring = gluErrorString(errorCode);

fprintf (stderr, "Nurbs Error: %s\n", estring);

exit (0);

}

/* Initialize material property and depth buffer.

*/ void init(void)

{

GLfloat mat_diffuse[] = { 0.7, 0.7, 0.7, 1.0 };

GLfloat mat_specular[] = { 1.0, 1.0, 1.0, 1.0 };

GLfloat mat_shininess[] = { 100.0 };

glClearColor(0.0, 0.0, 0.0, 0.0);

glMaterialfv(GL_FRONT, GL_DIFFUSE, mat_diffuse);

glMaterialfv(GL_FRONT, GL_SPECULAR, mat_specular);

glMaterialfv(GL_FRONT, GL_SHININESS, mat_shininess);

glEnable(GL_LIGHTING);

glEnable(GL_LIGHT0);

glEnable(GL_DEPTH_TEST);

glEnable(GL_AUTO_NORMAL);

glEnable(GL_NORMALIZE);

init_surface();

theNurb = gluNewNurbsRenderer();

gluNurbsProperty(theNurb, GLU_SAMPLING_TOLERANCE, 25.0);

gluNurbsProperty(theNurb, GLU_DISPLAY_MODE, GLU_FILL);

gluNurbsCallback(theNurb, GLU_ERROR, (GLvoid

(CALLBACK*)())nurbsError);

} void display(void)

56

Porting Curve and Surface Commands

{

GLfloat knots[8] = {0.0, 0.0, 0.0, 0.0, 1.0, 1.0, 1.0, 1.0};

GLfloat edgePt[5][2] = /* counter clockwise */

{{0.0, 0.0}, {1.0, 0.0}, {1.0, 1.0}, {0.0, 1.0}, {0.0, 0.0}};

GLfloat curvePt[4][2] = /* clockwise */

{{0.25, 0.5}, {0.25, 0.75}, {0.75, 0.75}, {0.75, 0.5}};

GLfloat curveKnots[8] =

{0.0, 0.0, 0.0, 0.0, 1.0, 1.0, 1.0, 1.0};

GLfloat pwlPt[4][2] = /* clockwise */

{{0.75, 0.5}, {0.5, 0.25}, {0.25, 0.5}};

glClear(GL_COLOR_BUFFER_BIT|GL_DEPTH_BUFFER_BIT);

glPushMatrix();

glRotatef(330.0, 1.,0.,0.);

glScalef(0.5, 0.5, 0.5);

gluBeginSurface(theNurb);

gluNurbsSurface(theNurb, 8, knots, 8, knots,

4*3, 3, &ctlpoints[0][0][0],

4, 4, GL_MAP2_VERTEX_3);

gluBeginTrim(theNurb);

gluPwlCurve(theNurb, 5, &edgePt[0][0], 2, GLU_MAP1_TRIM_2);

gluEndTrim(theNurb);

gluBeginTrim(theNurb);

gluNurbsCurve(theNurb, 8, curveKnots, 2,

&curvePt[0][0], 4, GLU_MAP1_TRIM_2);

gluPwlCurve(theNurb, 3, &pwlPt[0][0], 2, GLU_MAP1_TRIM_2);

gluEndTrim(theNurb);

gluEndSurface(theNurb);

glPopMatrix();

glFlush();

} void reshape(int w, int h)

{

glViewport(0, 0, (GLsizei)w, (GLsizei)h);

glMatrixMode(GL_PROJECTION);

glLoadIdentity();

gluPerspective(45.0, (GLdouble)w/(GLdouble)h, 3.0, 8.0);

glMatrixMode(GL_MODELVIEW);

glLoadIdentity();

glTranslatef(0.0, 0.0, -5.0);

}

57

Chapter 3: After toogl: How to Finish Porting to OpenGL

/* ARGSUSED1 */ void keyboard(unsigned char key, int x, int y)

{

switch (key) {

case 27:

exit(0);

break;

}

}

/* Main Loop

*/ int main(int argc, char **argv)

{

glutInit(&argc, argv);

glutInitDisplayMode(GLUT_SINGLE|GLUT_RGB|GLUT_DEPTH);

glutInitWindowSize(500, 500);

glutInitWindowPosition(100, 100);

glutCreateWindow(argv[0]);

init();

glutReshapeFunc(reshape);

glutDisplayFunc(display);

glutKeyboardFunc(keyboard);

glutMainLoop();

return 0;

}

Porting Antialiasing Calls

This section discusses topics related to antialiasing:

• “Blending”

• “afunction() Test Functions” on page 60

• “Antialiasing Calls” on page 60

In OpenGL, subpixel mode is always on, so the IRIS GL call subpixel(TRUE)

is not necessary and has no OpenGL equivalent.

58

Porting Antialiasing Calls

Blending

Blending is off by default. If you use _DA or _MDA blend functions, you have to allocate destination alpha bits when you choose a visual. You have to use X to choose the visual, so refer to Chapter 4.

Tip:

In IRIS GL, when drawing to both front and back buffers, blending is done by reading one of the buffers, blending with that color, and then writing the result to both buffers. In OpenGL, however, each buffer is read in turn, blended, and then written.

Table 3-34 lists IRIS GL and OpenGL blending calls.

Table 3-34

IRIS GL

— blendfunction()

Blending Calls

OpenGL

glEnable(GL_BLEND) glBlendFunc()

Meaning

Turn on blending.

Specify a blend function.

Table 3-35

IRIS GL

BF_ZERO

BF_ONE

BF_SA

BF_MSA

BF_DA

BF_MDA

BF_SC

BF_MSC

BF_DC

The calls glBlendFunc() and blendfunction() are almost identical. Table 3-35 lists the

OpenGL equivalents to the IRIS GL blend factors.

Blending Factors

OpenGL

GL_ZERO

GL_ONE

GL_SRC_ALPHA

GL_ONE_MINUS_SRC_ALPHA

GL_DST_ALPHA

GL_ONE_MINUS_DST_ALPHA

GL_SRC_COLOR

GL_ONE_MINUS_SRC_COLOR

GL_DST_COLOR

Notes

Destination only

Source only

59

Chapter 3: After toogl: How to Finish Porting to OpenGL

Table 3-35 (continued)

Blending Factors

IRIS GL OpenGL

BF_MDC GL_ONE_MINUS_DST_COLOR

BF_MIN_SA_MDA GL_SRC_ALPHA_SATURATE

afunction() Test Functions

Table 3-36 lists the available alpha test functions.

Table 3-36

Alpha Test Functions

afunction()

AF_NOTEQUAL

AF_ALWAYS

AF_NEVER

AF_LESS

AF_EQUAL

AF_LEQUAL

AF_GREATER

AF_GEQUAL

glAlphaFunc()

GL_NOTEQUAL

GL_ALWAYS

GL_NEVER

GL_LESS

GL_EQUAL

GL_LEQUAL

GL_GREATER

GL_GEQUAL

Notes

Source only

Antialiasing Calls

OpenGL has direct equivalents to the IRIS GL antialiasing calls. Table 3-37 lists them.

Table 3-37

Calls to Draw Antialiased Primitives

IRIS GL Call OpenGL Call

pntsmooth() glEnable(GL_POINT_SMOOTH) linesmooth() glEnable(GL_LINE_SMOOTH) polysmooth() glEnable(GL_POLYGON_SMOOTH)

Meaning

Enable antialiasing of points.

Enable antialiasing of lines.

Enable antialiasing of polygons.

60

Porting Antialiasing Calls

Use the corresponding glDisable() calls to turn off antialiasing.

In IRIS GL, you can control the quality of the antialiasing by calling linesmooth(SML_ON + SML_SMOOTHER);

OpenGL provides similar control—use glHint(): glHint(GL_POINT_SMOOTH_HINT,

hintMode

); glHint(GL_LINE_SMOOTH_HINT,

hintMode

); glHint(GL_POLYGON_SMOOTH_HINT,

hintMode

);

hintMode is one of the following:

GL_NICEST Use the highest quality smoothing.

GL_FASTEST Use the most efficient smoothing.

GL_DONT_CARE You don’t care which smoothing method is used.

You could perform end correction in IRIS GL by calling linesmooth(SML_ON + SML_END_CORRECT);

OpenGL doesn’t provide an equivalent for this call.

Accumulation Buffer Calls

You must allocate your accumulation buffer by requesting the appropriate visual with

glXChooseVisual()

. For information on glXChooseVisual(), see the glXIntro and glXChooseVisual reference pages and refer to Chapter 4.

IRIS GL allows you to draw colors in the depth buffer, so acbuf() can use that buffer as a color source for accumulation. Some developers have used this depth-buffer reading capability to put depth data into accumulation buffers as well. OpenGL, on the other hand, doesn’t put color information in the depth buffer; glAccum() thus can’t read any information from the depth buffer.

To emulate accumulation from the depth buffer (using a configuration that supports auxiliary buffers) use the following procedure:

1.

Use glReadPixels() to read from the depth buffer.

2. Massage the results as necessary.

61

Chapter 3: After toogl: How to Finish Porting to OpenGL

3. Draw the resulting data to an auxiliary buffer.

4. Select this auxiliary buffer with glReadBuffer(), and use glAccum() to accumulate from that buffer.

This procedure requires caution in converting among data types.

Except as noted above, porting accumulation buffer calls is straightforward. Table 3-38 lists calls that affect the accumulation buffer.

Table 3-38

Accumulation Buffer Calls

IRIS GL Call OpenGL Call Meaning

acbuf()

— glAccum() glClearAccum()

Operate on the accumulation buffer.

Set clear values for accumulation buffer.

acbuf(AC_CLEAR) glClear(GL_ACCUM_BUFFER_BIT) Clear the accumulation buffer.

acsize() glXChooseVisual() Specify number of bitplanes per color component in accumulation buffer.

Table 3-39 lists the IRIS GL acbuf() arguments along with the corresponding arguments to the OpenGL glAccum() call.

Table 3-39

Accumulation Buffer Operations

IRIS GL Argument

AC_ACCUMULATE

AC_CLEAR_ACCUMULATE

AC_RETURN

AC_MULT

AC_ADD

OpenGL Argument

GL_ACCUM

GL_LOAD

GL_RETURN

GL_MULT

GL_ADD

62

Porting Display Lists

Stencil Plane Calls

In OpenGL, you allocate stencil planes by requesting the appropriate visual with

glXChooseVisual()

. (For information on glXChooseVisual(), see the glXIntro and glXChooseVisual reference pages and refer to Chapter 4.) Otherwise, porting should be straightforward. Table 3-40 lists calls that affect the stencil planes.

Table 3-40

Stencil Operations

IRIS GL Call

stensize()

OpenGL Call

glXChooseVisual() stencil(TRUE, ...) glEnable(GL_STENCIL_TEST) stencil() glStencilOp() stencil(... func, ...) glStencilFunc() swritemask()

— sclear()

Meaning

Enable stencil tests.

Set stencil test actions.

glStencilMask()

Set function & reference value for stencil testing.

Specify which stencil bits can be written.

glClearStencil() Specify the clear value for the stencil buffer.

glClear(GL_STENCIL_BUFFER_BIT) —

Stencil comparison functions and stencil pass/fail operations are almost equivalent in

OpenGL and IRIS GL. The IRIS GL stencil function flags are prefaced with SF, the

OpenGL flags with GL. IRIS GL pass/fail operation flags are prefaced with ST, the

OpenGL flags with GL. Compare the IRIS GL and OpenGL reference pages for further details.

Porting Display Lists

The OpenGL implementation of display lists is similar to the IRIS GL implementation, with two exceptions: you can’t edit display lists once you’ve created them and you can’t call functions from within display lists.

63

Chapter 3: After toogl: How to Finish Porting to OpenGL

Because you can’t edit or call functions from within display lists, these IRIS GL commands have no equivalents in OpenGL:

editobj()

objdelete()

, objinsert(), and objreplace()

maketag()

, gentag(), istag(), and deltag()

callfunc()

In IRIS GL, you used the commands makeobj() and closeobj() to create display lists. In

OpenGL, you use glNewList() and glEndList(). For details on using glNewList()

(including a description of the two list modes and a list of commands that are not compiled into the display list but are executed immediately), see the glNewList reference page and the OpenGL Programming Guide.

Table 3-41 lists the IRIS GL display list commands with the corresponding OpenGL commands.

Table 3-41

IRIS GL Call

makeobj() closeobj() callobj() isobj() delobj() genobj()

Display List Commands

OpenGL Call Meaning

glNewList() Create a new display list.

glEndList() Signal end of display list.

glCallList(), glCallLists() Execute display list(s).

glIsList() glDeleteLists() glGenLists() glListBase()

Test for display list existence.

Delete contiguous group of display lists.

Generate the given number of contiguous empty display lists.

Get the display list base for glCallLists().

64

Porting Display Lists

Porting bbox2() Calls

The command bbox2() has no OpenGL equivalent. To port bbox2() calls, first create a new (OpenGL) display list that has everything that was in the corresponding IRIS GL display list except the bbox2() call. Then, in feedback mode, draw a rectangle the same size as the IRIS GL bounding box: if nothing comes back, the box was completely clipped and you shouldn’t draw the display list.

Achieving Edited Display List Behavior

Although you can’t actually edit OpenGL display lists, you can get a similar result by nesting display lists, then destroying and creating new versions of the sublists. The following OpenGL code fragment illustrates how to do this: glNewList (1, GL_COMPILE);

glIndexi (MY_RED); glEndList ();

glNewList (2, GL_COMPILE);

glScalef (1.2, 1.2, 1.0); glEndList (); glNewList (3, GL_COMPILE);

glCallList (1);

glCallList (2); glEndList ();

.

.

glDeleteLists (1, 2); glNewList (1, GL_COMPILE);

glIndexi (MY_CYAN); glEndList (); glNewList (2, GL_COMPILE);

glScalef (0.5, 0.5, 1.0); glEndList ();

65

Chapter 3: After toogl: How to Finish Porting to OpenGL

Sample Implementation of a Display List

Example 3-5 defines three IRIS GL display lists. One display list refers to the others in its definition.

Example 3-5

IRIS GL Display Lists makeobj (10);

cpack (0x0000FF);

recti (164, 33, 364, 600); closeobj ();

/* 10 object */

/* hollow rectangle */

/*20 object--various things*/

/* draw an unfilled circle */

/* draw filled rect */ makeobj (20);

cpack (0xFFFF00);

circi(0,0,25);

rectfi (100, 100, 200, 200); closeobj (); makeobj (30);

callobj (10);

cpack (0xFFFFFF);

rectfi (400, 100, 500, 300);

callobj (20); closeobj (); callobj(30);

/* 30 -- THE MAIN OBJECT */

/* draw filled rect */

/* now draw by calling the lists */

Translated to OpenGL, the code from Example 3-5 might look Example 3-6.

Example 3-6

OpenGL Display Lists glNewList( 10, GL_COMPILE );

glColor3f( 1, 0, 0 );

glRecti( 164, 33, 364, 600 ); glEndList(); glNewList( 20, GL_COMPILE );

glColor3f( 1, 1, 0 );

glPolygonMode(GL_BOTH, GL_LINE);

glBegin(GL_POLYGON);

for(i=0;i<100;i++) {

/* set color to YELLOW */

/* unfilled mode */

/*use polygon to approximate circle*/

cosine = 25 * cos(i*2*PI/100.0);

sine = 25 * sin(i*2*PI/100.0);

glVertex2f(cosine,sine);

}

66

Porting defs, binds, and sets: Replacing ‘Tables’ of Stored Definitions

glEnd();

glBegin(GL_QUADS);

glColorf( 0, 1, 1 );

glVertex2i(100,100);

glVertex2i(100,200);

glVertex2i(200,200);

glVertex2i(100,200);

glEnd(); glEndList(); glNewList(30, GL_COMPILE);

glCallList( 10 );

glColorf( 1, 1, 1 );

glRecti(400, 100, 500, 300);

glCallList( 20 ); glEndList(); glCallList( 30 );

/* set color to CYAN */

/* List #30 */

/* set color to WHITE */

/* execute the display lists */

Porting defs, binds, and sets: Replacing ‘Tables’ of Stored Definitions

OpenGL doesn’t have tables of stored definitions—you cannot define lighting models, materials, textures, line styles, or patterns as separate objects as you could in IRIS GL.

Thus, there are no direct equivalents to these IRIS GL calls:

lmdef()

and lmbind()

tevdef()

and tevbind()

texdef()

and texbind()

deflinestyle()

and setlinestyle()

defpattern()

and setpattern()

However, you can use display lists to mimic the def/bind behavior. (It’s often best to optimize by writing display lists that contain just a single material definition.)

67

Chapter 3: After toogl: How to Finish Porting to OpenGL

For example, here is a material definition in IRIS GL: float mat[] = {

AMBIENT, .1, .1, .1,

DIFFUSE, 0, .369, .165,

SPECULAR, .5, .5, .5,

SHININESS, 10,

LMNULL

}; lmdef(DEFMATERIAL, 1, 0, mat); lmbind(MATERIAL, 1);

In the following code fragment, the same material is defined in a display list, referred to by the list number in MYMATERIAL:

#define MYMATERIAL 10

/* you would probably use glGenLists() to get list numbers */

GLfloat mat_amb[] = {.1, .1, .1, 1.0};

GLfloat mat_dif[] = {0, .369, .165, 1.0};

GLfloat mat_spec[] = { .5, .5, .5, 1.0}; glNewList( MYMATERIAL, GL_COMPILE );

glMaterialfv( GL_FRONT, GL_AMBIENT, mat_amb);

glMaterialfv( GL_FRONT, GL_DIFFUSE, mat_dif);

glMaterialfv( GL_FRONT, GL_SPECULAR, mat_spec);

glMateriali( GL_FRONT, GL_SHININESS, 10); glEndList(); glCallList( MYMATERIAL );

Porting Lighting and Materials Calls

You probably have to port lighting and materials code explicitly, because the OpenGL calls differ substantially from the IRIS GL calls. The OpenGL API has separate calls for setting lights, light models, and materials.

When porting lighting and materials calls, consider the following issues:

• OpenGL has no table of stored definitions. It has no separate lmdef() and lmbind() calls. You can use display lists to mimic the def/bind behavior. See “Porting defs, binds, and sets: Replacing ‘Tables’ of Stored Definitions” on page 67 for an example.

Using display lists can have the added benefit of improving your program’s performance.

68

Porting Lighting and Materials Calls

• Attenuation is now associated with each light source, rather than with the overall lighting model.

• Diffuse and specular components are separated out in OpenGL light sources.

• OpenGL light sources have an alpha component. When porting your code, it’s best to set the alpha component to 1.0, indicating 100% fully opaque. That way, alpha values will be determined solely by the alpha component of your materials and the objects in your scene will look just as they did in IRIS GL.

• In IRIS GL, you could call lmcolor() between a call to bgnprimitive() and the corresponding endprimitive() call. In OpenGL, you can’t call glColorMaterial() between a glBegin() and its corresponding glEnd().

Table 3-42 lists IRIS GL lighting and materials commands and the corresponding

OpenGL commands.

Table 3-42

Lighting and Materials Commands

IRIS GL Call OpenGL Call Meaning

lmdef(DEFLIGHT,...) lmdef(DEFLMODEL, ...) lmbind() glLight() glLightModel() glEnable(GL_LIGHT

i)

Define a light source.

Define a lighting model.

Enable light

i.

lmbind()

— lmdef(DEFMATERIAL, ...) glMaterial() lmcolor() glColorMaterial()

— glEnable(GL_LIGHTING) Enable lighting.

glGetLight() Get light source parameters.

glGetMaterial()

Define a material.

Change effect of color commands while lighting is active.

Get material parameters.

69

Chapter 3: After toogl: How to Finish Porting to OpenGL

When the first argument for lmbind() is DEFMATERIAL, the equivalent command is

glMaterial()

. Table 3-43 lists the various materials parameters you can set.

Table 3-43

Material Definition Parameters

lmdef() index

ALPHA

AMBIENT

DIFFUSE

SPECULAR

EMISSION

glMaterial() parameter

GL_DIFFUSE a

GL_AMBIENT

GL_DIFFUSE

GL_SPECULAR

GL_EMISSION b

Default Meaning

(0.2, 0.2, 0.2, 1.0) Ambient color

(0.8, 0.8, 0.8, 1.0) Diffuse color

(0.0, 0.0, 0.0, 1.0) Specular color

(0.0, 0.0, 0.0, 1.0) Emissive color

SHININESS

GL_SHININESS

GL_AMBIENT_AND_

DIFFUSE

0.0

(see above)

COLORINDEXES GL_COLOR_INDEXES —

Specular exponent

Equivalent to calling glMaterial() twice with same values

Color indices for ambient, diffuse, and specular lighting a. The fourth value in the GL_DIFFUSE parameter specifies the alpha value.

b. In IRIS GL, if the specular exponent (i.e. SHININESS) is zero, then the specular component of the light is not added in. In OpenGL, the specular component is added in anyway.

When the first argument of lmdef() is DEFLMODEL, the equivalent OpenGL call is

glLightModel()

. The exception is the case when the first argument of lmdef() is

DEFLMODEL, ATTENUATION—in this case, you have to replace lmdef() with several

glLight()

calls. Table 3-44 lists equivalent lighting model parameters.

Table 3-44

Lighting Model Parameters

lmdef() index glLightModel() Parameter Default Meaning

AMBIENT GL_LIGHT_MODEL_AMBIENT (0.2, 0.2, 0.2, 1.0) Ambient color of scene.

ATTENUATION —

LOCALVIEWER GL_LIGHT_MODEL_

LOCAL_VIEWER

TWOSIDE

GL_FALSE

GL_LIGHT_MODEL_TWO_SIDE GL_FALSE

See glLight().

Viewer local (TRUE) or infinite (FALSE).

Use two-sided lighting when TRUE.

70

Porting Lighting and Materials Calls

When the first argument of lmdef() is DEFLIGHT, the equivalent OpenGL call is

glLight()

. Table 3-45 lists equivalent lighting parameters.

Table 3-45

Light Parameters

lmdef() index glLight() Parameter

AMBIENT GL_AMBIENT

GL_DIFFUSE

GL_SPECULAR

LCOLOR

POSITION GL_POSITION

SPOTDIRECTION GL_SPOT_DIRECTION

SPOTLIGHT --

GL_SPOT_EXPONENT

GL_SPOT_CUTOFF

Default Meaning

(0.0, 0.0, 0.0, 1.0) Ambient intensity.

(1.0, 1.0, 1.0, 1.0) Diffuse intensity.

(1.0, 1.0, 1.0, 1.0) Specular intensity.

(0.0, 0.0, 1.0, 0.0) Position of light.

(0, 0, -1) Spot direction.

0

180

DEFLMODEL,

ATTENUATION,

...

GL_CONSTANT_ATTENUATION

GL_LINEAR_ATTENUATION

GL_QUADRATIC_ATTENUATION

(1,0,0)

Intensity distribution.

Maximum spread angle of light source.

Attenuation factors.

Example 3-7 is an OpenGL code fragment that demonstrates some OpenGL lighting and material calls, including two-sided lighting.

Example 3-7

OpenGL Lighting and Material Calls

/* Initialize lighting */ void myinit(void)

{

GLfloat light_ambient[] = { 0.0, 0.0, 0.0, 1.0 };

GLfloat light_diffuse[] = { 1.0, 1.0, 1.0, 1.0 };

GLfloat light_specular[] = { 1.0, 1.0, 1.0, 1.0 };

/* light_position is NOT default value */

GLfloat light_position[] = { 1.0, 1.0, 1.0, 0.0 };

71

Chapter 3: After toogl: How to Finish Porting to OpenGL

glLightfv(GL_LIGHT0, GL_AMBIENT, light_ambient);

glLightfv(GL_LIGHT0, GL_DIFFUSE, light_diffuse);

glLightfv(GL_LIGHT0, GL_SPECULAR, light_specular);

glLightfv(GL_LIGHT0, GL_POSITION, light_position);

glFrontFace (GL_CW);

glEnable(GL_LIGHTING);

glEnable(GL_LIGHT0);

glEnable(GL_AUTO_NORMAL);

glEnable(GL_NORMALIZE);

glDepthFunc(GL_LEQUAL);

glEnable(GL_DEPTH_TEST);

} void display(void)

{

GLdouble eqn[4] = {1.0, 0.0, -1.0, 1.0};

GLfloat mat_diffuse[] = { 0.8, 0.8, 0.8, 1.0 };

GLfloat back_diffuse[] = { 0.8, 0.2, 0.8, 1.0 };

glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);

glPushMatrix ();

glClipPlane (GL_CLIP_PLANE0, eqn); /* slice objects */

glEnable (GL_CLIP_PLANE0);

glPushMatrix ();

glTranslatef (0.0, 2.0, 0.0);

auxSolidTeapot(1.0); /* one-sided lighting */

glPopMatrix ();

/* two-sided lighting, but same material */

glLightModelf (GL_LIGHT_MODEL_TWO_SIDE, GL_TRUE);

glMaterialfv (GL_FRONT_AND_BACK, GL_DIFFUSE,

mat_diffuse);

glPushMatrix ();

glTranslatef (0.0, 0.0, 0.0);

auxSolidTeapot(1.0);

glPopMatrix ();

/* two-sided lighting, two different materials */

glMaterialfv (GL_FRONT, GL_DIFFUSE, mat_diffuse);

glMaterialfv (GL_BACK, GL_DIFFUSE, back_diffuse);

glPushMatrix ();

glTranslatef (0.0, -2.0, 0.0);

72

Porting Texture Calls

auxSolidTeapot(1.0);

glPopMatrix ();

glLightModelf (GL_LIGHT_MODEL_TWO_SIDE, GL_FALSE);

glDisable (GL_CLIP_PLANE0);

glPopMatrix ();

glFlush();

}

Porting Texture Calls

When porting texture calls, consider these issues:

• At times, a single IRIS GL texturing call has to be replaced with two or more

OpenGL calls. For those cases, edit the toogl output to use more variables than it did before or restructure the program.

• Use glEnable() and glDisable() to turn texturing capabilities on and off. See the reference page for details.

• OpenGL doesn’t automatically generate mipmaps for you—if you’re using mipmaps, call gluBuild2DMipmaps() first.

• Texture size in OpenGL is more strictly regulated than in IRIS GL. An OpenGL texture must be

2

n

+ 2b where n is an integer and b is

– 0, if there’s no border

– 1, if there’s a border pixel (textures in OpenGL can have 1 pixel borders)

• OpenGL 1.0 keeps no tables of textures, just a single 1D texture and a single 2D texture. If you want to reuse your textures, put them in a display list, as described in

“Porting defs, binds, and sets: Replacing ‘Tables’ of Stored Definitions” on page 67.

• In OpenGL 1.1, you can use named textures. Use the functions glBindTexture(),

glGenTexture()

, and glDeleteTextures() to work with named texture object. You can also call glPrioritizeTextures() to have certain textures preferentially be assigned to texture memory, and glAreTexturesResident() to determine whether a named texture is currently in texture memory.

• In OpenGL 1.1, you can use the subtexture mechanism for more efficient texture loading.

73

Chapter 3: After toogl: How to Finish Porting to OpenGL

• OpenGL 1.1 offers the proxy texture mechanism to let you test whether a texture will fit into texture memory on a certain system.

Table 3-46 lists the general OpenGL equivalents to IRIS GL texture calls.

Table 3-46

IRIS GL Call

texdef2d() texbind() tevdef() tevbind()

— t2*(), t3*(), t4*() texgen()

Texture Commands

OpenGL Call Meaning

glTexImage2D() glTexParameter() gluBuild2DMipmaps()

Specify a 2D texture image.

glTexParameter() glTexImage2D() gluBuild2DMipmaps()

Select a texture function.

glTexEnv() Define a texture mapping environment.

glTexEnv() glTexImage1D() glTexCoord*() glTexGen()

Select a texture environment.

Set the current texture coordinates.

Control generation of texture coordinates.

glGetTexParameter() — gluBuild1DMipmaps() — gluBuild2DMipmaps() — gluScaleImage() Scale an image to arbitrary size.

The OpenGL Programming Guide describes in detail how textures work in OpenGL. Here are a few general tips:

• Remember to call gluBuild2DMipmaps() or gluBuild1DMipmaps() before trying to use mipmaps.

• Use glTexParameter() to specify wrapping and filters.

• Use glTexEnv() to set up texturing environment.

• Use glTexImage2D() or glTexImage1D() to load each image.

74

Porting Texture Calls

• Use glEnable() and glDisable() to turn texturing capabilities on and off.

See the reference page for each call for detailed information.

Translating tevdef()

Here’s an example of an IRIS GL texture environment definition that specifies the

TV_DECAL texture environment option: float tevprops[] = {TV_DECAL, TV_NULL}; tevdef(1, 0, tevprops);

Here’s how you could translate that code to OpenGL: glTexEnvfv(GL_TEXTURE_ENV, GL_TEXTURE_ENV_MODE, GL_DECAL);

Table 3-47 lists the IRIS GL texture environment options and their OpenGL equivalents.

Table 3-47

Texture Environment Options

IRIS GL Option

TV_MODULATE

TV_DECAL

TV_BLEND

TV_COLOR

TV_ALPHA

TV_COMPONENT_SELECT

OpenGL Option

GL_MODULATE

GL_DECAL

GL_BLEND

GL_TEXTURE_ENV_COLOR no direct OpenGL equivalent no direct OpenGL equivalent

For more detailed information on how to use these options, see the glTexEnv reference page.

75

Chapter 3: After toogl: How to Finish Porting to OpenGL

Translating texdef()

Here’s an example of an IRIS GL texture definition: float texprops[] = { TX_MINFILTER, TX_POINT,

TX_MAGFILTER, TX_POINT,

TX_WRAP_S, TX_REPEAT,

TX_WRAP_T, TX_REPEAT,

TX_NULL }; texdef2d(1, 1, 6, 6, granite_texture, 7, texprops)

In the above code example, texdef() specifies the TX_POINT filter as both the magnification and the minification filter, and TX_REPEAT as the wrapping behavior. It also specifies the texture image, in this case an image called granite_texture.

In OpenGL, the image specification is handled by the glTexImage*() functions and property-setting is handled by glTexParameter(). To translate to OpenGL, you’d replace a texdef() call with a call to a glTexImage*() routine and one or more calls to

glTexParameter()

.

Here’s an example of one way you could translate the IRIS GL code fragment above:

GLfloat nearest [] = {GL_NEAREST};

GLfloat repeat [] = {GL_REPEAT}; glTexParameterfv( GL_TEXTURE_1D, GL_TEXTURE_MIN_FILTER,

nearest); glTexParameterfv( GL_TEXTURE_1D, GL_TEXTURE_MAG_FILTER,

nearest); glTexParameterfv( GL_TEXTURE_1D, GL_TEXTURE_WRAP_S,

repeat); glTexParameterfv( GL_TEXTURE_1D, GL_TEXTURE_WRAP_T,

repeat); glTexImage1D(GL_TEXTURE_1D, 0, 1, 6, 0, GL_RGB,

GL_UNSIGNED_SHORT,granite_tex);

76

Porting Texture Calls

Table 3-48 lists the IRIS GL texture parameters with their OpenGL equivalents. For more detailed information on OpenGL texture parameters, see the glTexParameter reference page.

Table 3-48

IRIS GL and OpenGL Texture Parameters

texdef(... np, ...) Option

TX_MINFILTER

TX_MAGFILTER

TX_WRAP, TX_WRAP_S

TX_WRAP, TX_WRAP_T

glTexParameter() Parameter Name

GL_TEXTURE_MIN_FILTER

GL_TEXTURE_MAG_FILTER

GL_TEXTURE_WRAP_S

GL_TEXTURE_WRAP_T

GL_TEXTURE_BORDER_COLOR

Table 3-49 lists the possible values of the IRIS GL texture parameters along with their

OpenGL equivalents. If you used special values available only on systems with

RealityEngine™ graphics, you may have to wait for RealityEngine extensions to

OpenGL before you can translate these values exactly (see “Porting RealityEngine

Graphics Features” for further discussion). For more information on possible values of

OpenGL texture parameters, see the glTexParameter reference page.

Table 3-49

Values for IRIS GL and OpenGL Texture Parameters

IRIS GL

TX_POINT

TX_BILINEAR

TX_MIPMAP_POINT

TX_MIPMAP_BILINEAR

TX_MIPMAP_LINEAR

TX_TRILINEAR

OpenGL

GL_NEAREST

GL_LINEAR

GL_NEAREST_MIPMAP_NEAREST

GL_LINEAR_MIPMAP_NEAREST

GL_NEAREST_MIPMAP_LINEAR

GL_LINEAR_MIPMAP_LINEAR

77

Chapter 3: After toogl: How to Finish Porting to OpenGL

Translating texgen()

The functionality of texgen() is replaced by glTexGen() almost entirely, though you have to call glEnable() and glDisable() to turn coordinate generation on and off. Table 3-50 lists the equivalents for texture coordinate names.

Table 3-50

Texture Coordinate Names

IRIS GL Texture Coordinate

TX_S

TX_T

TX_R

TX_Q

OpenGL Texture Coordinate

GL_S

GL_T

GL_R

GL_Q

glEnable() Argument

GL_TEXTURE_GEN_S

GL_TEXTURE_GEN_T

GL_TEXTURE_GEN_R

GL_TEXTURE_GEN_Q

Table 3-51 lists texture generation mode and plane names.

Table 3-51

Texture Generation Modes and Planes

IRIS GL Texture Mode

TG_LINEAR

TG_CONTOUR

TG_SPHEREMAP

OpenGL Texture Mode

GL_OBJECT_LINEAR

GL_EYE_LINEAR

GL_SPHERE_MAP

Corresponding Plane Name

GL_OBJECT_PLANE

GL_EYE_PLANE

With IRIS GL, you call texgen() twice: once to simultaneously set the mode and a plane equation, and once more to enable texture coordinate generation. In OpenGL, you make three calls: two to glTexGen() (once to set the mode, and again to set the plane equation), and one to glEnable(). For example, if you called texgen() like this: texgen(TX_S, TG_LINEAR,

planeParams

); texgen(TX_S, TG_ON, NULL); the equivalent OpenGL code is: glTexGen(GL_S, GL_TEXTURE_GEN_MODE,

modeName

); glTexGen(GL_S, GL_OBJECT_PLANE,

planeParams

); glEnable(GL_TEXTURE_GEN_S);

78

Porting Picking Calls

Porting Picking Calls

All the IRIS GL picking calls have OpenGL equivalents, with the exception of

clearhitcode()

. Table 3-52 lists the IRIS GL picking calls and their OpenGL counterparts.

Table 3-52

Calls for Picking

IRIS GL Call OpenGL Call Notes

clearhitcode() pick(),

select() not supported glRenderMode(GL_SELECT)

Clears global variable, hitcode.

Switch to selection/picking mode.

endpick(), endselect() picksize() glRenderMode(GL_RENDER) Switch back to rendering mode.

— initnames() gluPickMatrix() glSelectBuffer() glInitNames()

Set the return array.

— pushname(), popname() glPushName(), glPopName() — loadname() glLoadName() —

For more information on picking, refer to the gluPickMatrix reference page and the

OpenGL Programming Guide. You can find a complete example and additional explanation in “OpenGL Programming for the X Window System,” page 438-441. See

“GLX and GLUT Documentation” on page xvi.

79

Chapter 3: After toogl: How to Finish Porting to OpenGL

Porting Feedback Calls

Feedback under IRIS GL differed from machine to machine. OpenGL standardizes feedback, so you can now rely on consistent feedback from machine to machine, and from implementation to implementation. Table 3-53 lists IRIS GL and OpenGL feedback calls.

Table 3-53

Feedback Calls

IRIS GL Call OpenGL Call Notes

feedback() glRenderMode(GL_FEEDBACK) Switch to feedback mode.

endfeedback() glRenderMode(GL_RENDER) Switch back to rendering mode.

— glFeedbackBuffer() passthrough() glPassThrough()

Place a token marker in the feedback buffer.

For more information, see the reference pages or the OpenGL Programming Guide.

Example 3-8 demonstrates OpenGL feedback.

Example 3-8

Feedback in OpenGL

/*

* feedback.c

* This program demonstrates use of OpenGL feedback. First,

* a lighting environment is set up and a few lines are drawn.

* Then feedback mode is entered, and the same lines are

* drawn. The results in the feedback buffer are printed.

*/

#include <GL/glut.h>

#include <stdlib.h>

#include <stdio.h>

/* Initialize lighting.

*/ void init(void)

{

glEnable(GL_LIGHTING);

glEnable(GL_LIGHT0);

}

/* Draw a few lines and two points, one of which will

80

Porting Feedback Calls

* be clipped. If in feedback mode, a passthrough token

* is issued between the each primitive.

*/ void drawGeometry(GLenum mode)

{

glBegin(GL_LINE_STRIP);

glNormal3f(0.0, 0.0, 1.0);

glVertex3f(30.0, 30.0, 0.0);

glVertex3f(50.0, 60.0, 0.0);

glVertex3f(70.0, 40.0, 0.0);

glEnd();

if (mode == GL_FEEDBACK)

glPassThrough(1.0);

glBegin(GL_POINTS);

glVertex3f(-100.0, -100.0, -100.0); /* will be clipped */

glEnd();

if (mode == GL_FEEDBACK)

glPassThrough(2.0);

glBegin(GL_POINTS);

glNormal3f(0.0, 0.0, 1.0);

glVertex3f(50.0, 50.0, 0.0);

glEnd();

}

/* Write contents of one vertex to stdout.

*/ void print3DcolorVertex(GLint size, GLint *count, GLfloat *buffer)

{

int i;

printf(" ");

for (i = 0; i < 7; i++) {

printf("%4.2f ", buffer[size-(*count)]);

*count = *count - 1;

}

printf ("\n");

}

/* Write contents of entire buffer. (Parse tokens!)

*/ void printBuffer(GLint size, GLfloat *buffer)

{

GLint count;

GLfloat token;

81

Chapter 3: After toogl: How to Finish Porting to OpenGL

count = size;

while (count) {

token = buffer[size-count];

count--;

if (token == GL_PASS_THROUGH_TOKEN) {

printf("GL_PASS_THROUGH_TOKEN\n");

printf(" %4.2f\n", buffer[size-count]);

count--;

} else if (token == GL_POINT_TOKEN) {

printf("GL_POINT_TOKEN\n");

print3DcolorVertex (size, &count, buffer);

} else if (token == GL_LINE_TOKEN) {

printf("GL_LINE_TOKEN\n");

print3DcolorVertex(size, &count, buffer);

print3DcolorVertex(size, &count, buffer);

} else if (token == GL_LINE_RESET_TOKEN) {

printf("GL_LINE_RESET_TOKEN\n");

print3DcolorVertex(size, &count, buffer);

print3DcolorVertex(size, &count, buffer);

}

}

} void display(void)

{

GLfloat feedBuffer[1024];

GLint size;

glMatrixMode(GL_PROJECTION);

glLoadIdentity();

glOrtho(0.0, 100.0, 0.0, 100.0, 0.0, 1.0);

glClearColor(0.0, 0.0, 0.0, 0.0);

glClear(GL_COLOR_BUFFER_BIT);

drawGeometry(GL_RENDER);

glFeedbackBuffer(1024, GL_3D_COLOR, feedBuffer);

glRenderMode(GL_FEEDBACK);

drawGeometry(GL_FEEDBACK);

size = glRenderMode(GL_RENDER);

printBuffer(size, feedBuffer);

}

/* ARGSUSED1 */

82

Porting RealityEngine Graphics Features void keyboard(unsigned char key, int x, int y)

{

switch (key) {

case 27:

exit(0);

break;

}

} int main(int argc, char **argv)

{

glutInit(&argc, argv);

glutInitDisplayMode(GLUT_SINGLE|GLUT_RGB);

glutInitWindowSize(100, 100);

glutInitWindowPosition(100, 100);

glutCreateWindow(argv[0]);

init();

glutDisplayFunc(display);

glutKeyboardFunc(keyboard);

glutMainLoop();

return 0;

}

Porting RealityEngine Graphics Features

Some IRIS GL features that were available only on systems with RealityEngine graphics are unavailable in OpenGL; though several of them are supported either by OpenGL 1.1

or by an extension.

Table 3-54 lists the IRIS GL RealityEngine calls and their OpenGL counterparts.

Table 3-54

IRIS GL Call

blendcolor() convolve()

RealityEngine Calls

OpenGL Call

glBlendColorEXT() glConvolutionFilter2DEXT(), glSeparableFilter2DEXT(), glConvolutionParameterEXT(), glPixelTransfer()

Notes

Specify a color to blend.

Convolve an input image with a kernel image.

83

Chapter 3: After toogl: How to Finish Porting to OpenGL

Table 3-54 (continued)

RealityEngine Calls

IRIS GL Call OpenGL Call Notes

displacepolygon() glPolygonOffsetEXT() (OpenGL 1.0) glPolygonOffset() (OpenGL 1.1) fbsubtexload() gethgram() getminmax()

Not supported glGetHistogramEXT() hgram() ilbuffer()

Specify z displacement for rendered polygons.

Load part or all of a texture.

Get histogram data.

glGetMinmaxEXT() Get minimum and maximum graphics values.

glHistogramEXT(), glResetHistogramEXT() Compute histogram of pixel-transfer information.

Not supported Allocate space for temporary image-processing results.

ildraw() istexloaded() leftbuffer() minmax() monobuffer()

Not supported glAreTexturesResidentEXT (OpenGL 1.0) glAreTexturesResident (OpenGL 1.1) glDrawBuffer(GL_LEFT) glMinmaxEXT()

Select an ilbuffer to draw into.

Find out whether a given texture is resident in texture memory.

Enable left-buffer drawing.

Compute minimum and maximum pixel values.

Select monoscopic viewing.

msalpha() msmask() mspattern()

Superseded by selection of an appropriate

GLX visual glEnable(

GL_SAMPLE_ALPHA_TO_MASK_SGIS), glEnable(

GL_SAMPLE_ALPHA_TO_ONE_SGIS) glSampleMaskSGIS() glSamplePatternSGIS()

Specify treatment of alpha values during multisampling.

mssize() multisample() glXChooseVisual() with attribute

GLX_SAMPLE_BUFFERS_SGIS glEnable(GL_MULTISAMPLE_SGIS)

Specify a multisample mask.

Specify a sample pattern for multisampling.

Configure multisample buffer.

Enable or disable multisampling.

84

Porting RealityEngine Graphics Features

Table 3-54 (continued)

RealityEngine Calls

IRIS GL Call OpenGL Call Notes

pixelmap() pixeltransfer() glPixelMap() glPixelTransfer() readcomponent() glReadPixels() gives partial support; some readcomponent() features aren’t yet supported rightbuffer() glDrawBuffer(GL_RIGHT) stereobuffer() subtexload()

Choose a component source.

Enable drawing in right buffer.

Select stereoscopic viewing.

Superseded by selection of an appropriate

GLX visual.

OpenGL 1.1 function glTexSubImage2D() gives partial support (the flags parameter to subtexload() isn’t supported)

Load part or all of a texture.

texdef3d() glTexImage3DEXT()

Define pixel transfer lookup tables.

Set transfer modes.

tlutbind() tlutdef() zbsize()

Not supported

Not supported

Superseded by selection of an appropriate

GLX visual

Convert 3D image into a texture.

Select a texture lookup table.

Define a texture lookup table.

Specify number of bitplanes to use for the depth buffer.

Some RealityEngine features (mostly involving texturing) don’t correspond to specific

IRIS GL functions, and thus don’t fit nicely into Table 3-54. Some such features are supported by extensions to OpenGL; you should check at runtime to see if the relevant extension is supported by calling glGetString(GL_EXTENSIONS)

(see the glGetString reference page for more information). Some other non-function-specific IRIS GL

RealityEngine features aren’t supported at all.

Each of the following features is supported on a given machine if the corresponding

OpenGL extension is supported. (“OpenGL Extensions” on page 87 points you to additional information):

• The internal texture storage format (TX_INTERNAL_FORMAT in IRIS GL) is supported by the texture extension (GL_EXT_texture). OpenGL without extensions

85

Chapter 3: After toogl: How to Finish Porting to OpenGL supports a superset of the formats previously specified by

TX_EXTERNAL_FORMAT; see the glTexImage2D reference page for more information.

• Sharpen texture is supported by the GL_SGIS_sharpen_texture extension. This was done in IRIS GL by passing TX_SHARPEN to texdef().

• Detail texture is supported by the GL_SGIS_detail_texture extension. This was done in IRIS GL by using the tokens TX_DETAIL, TX_ADD_DETAIL, and

TX_MODULATE_DETAIL in texdef() calls.

• The detail texture and sharpen texture extension both support control points (pairs of level-of-detail and scale values) to control the rate at which the relevant filters are applied (see TX_CONTROL_CLAMP and TX_CONTROL_POINT in the texdef() reference page). However, unlike IRIS GL, OpenGL uses a separate set of control points for each of the two filters.

• The IRIS GL ABGR pixel format is supported by the GL_EXT_abgr extension.

• Texture and texture environment definition and binding (formerly done by using

texdef()

, texbind(), tevdef(), and tevbind()) are currently handled in OpenGL by creating a display list containing a glTexImage2D() call. (No OpenGL extension is required.)

• The texture object extension supports named textures and allows you to prioritize textures using glPrioritizeTexturesEXT(). This functionality is also part of OpenGL

1.1.

These features are not supported in OpenGL or its extensions:

• Automatic mipmap generation is supported in the GLU library by

gluBuild2DMipmaps()

, but you can’t change the default filtering used to generate mipmap levels (see TX_MIPMAP_FILTER_KERNEL in the texdef reference page).

• Bicubic texture filtering (see the descriptions of TX_BICUBIC and

TX_BICUBIC_FILTER in the texdef reference page).

• shadows (see the descriptions of TX_BILINEAR_LEQUAL and

TX_BILINEAR_GEQUAL in the texdef() reference page, and of TV_ALPHA in the

tevdef()

reference page).

• Component selection (see TV_COMPONENT_SELECT in the tevdef() reference page).

• Texture definition from a live video stream (available in IRIS GL using the flags argument to subtexload()).

86

OpenGL Extensions

On some platforms, the video source extension, SGIX_video_source, lets you source pixel data from a video stream to the OpenGL renderer. The video source extension is available only for system configurations that have direct hardware paths from the video hardware to the graphics accelerator. On other systems, you need to transfer video data to host memory and then call glDrawPixels() or glTex{Sub}Image() to transfer data to the framebuffer or to texture memory.

• Fast texture definition, as performed in IRIS GL with TX_FAST_DEFINE.

• Quadlinear mipmap filtering (see TX_MIPMAP_QUADLINEAR in the texdef reference page).

• Specifying separate alpha and non-alpha functions for texture magnification filtering (see TX_MAGFILTER_COLOR and TX_MAGFILTER_ALPHA in the texdef reference page).

OpenGL Extensions

For information on extensions to OpenGL, see the glintro and glxintro reference pages, as well as the reference pages for individual functions. (For a partial list of extension-related functions, see “Porting RealityEngine Graphics Features.”)

The manual OpenGL on Silicon Graphics Systems discusses each extension and explains how to use it.

87

Chapter 4

4.

OpenGL in the X Window System

This chapter provides some information about OpenGL programming in the X environment. The chapter focuses on information relevant to translating IRIS GL programs into programs using OpenGL and X—it doesn’t provide a tutorial on Xt and

IRIS IM.

This chapter discusses the following topics:

• “X Window System Background” on page 90 provides some basic information about the X Window system and also briefly discusses porting issue, naming conventions, and the two porting options (widget or Xlib).

• “Advice for OpenGL Programs using the X Window System” on page 92 discusses window depth, display mode, and X colormaps.

• “Fonts and Strings” on page 92 explores using fonts in an OpenGL program.

• “Using Xt and a Widget Set” on page 94 discusses using a widget set in more detail.

• “Using Xlib and GLX Commands” on page 103 discusses using straight OpenGL in more detail.

Several documents can help you with more detailed information (see “Where to Get

More Information” on page xiv):

• For a detailed discussion of all issues involving OpenGL and X, see “OpenGL

Programming for the X Window System” discussed under “GLX and GLUT

Documentation” on page xvi.

• For more information on the relevant features of Xt and IRIS IM, consult the

OSF/Motif series, and Digital’s X Window System Toolkit: The Complete Programmer’s

Guide and Specification, or O’Reilly’s Volumes 4 and 5 on X Toolkit Intrinsics.

• For information on OpenGL in the X Window System within a Silicon Graphics environment, see OpenGL on Silicon Graphics Systems.

89

Chapter 4: OpenGL in the X Window System

X Window System Background

An X program can create one or more subwindows that use OpenGL for rendering. Such a program allows full access to the capabilities of X by completely removing OpenGL from any feature governed by the X server. You have direct control of all the areas governed by the X server: the event handling, window control, and menus. You also use

X to handle color maps and fonts.

You can find examples of programs that use either OpenGL or IRIS GL in the usr/share directory and through the SGI home page.

In IRIS GL, you could use IRIS GL event and window management routines, such as

winopen()

or qread()—which would access the X Window System for you. In OpenGL, you can use the GLUT library for all basic windowing and event handling routines. If the

GLUT library isn’t sufficient for your purposes, you can modify your IRIS GL code to be an OpenGL program using GLX.

Function Naming Conventions

IRIS GL can draw in X11 windows with routines such as GLXgetconfig(), GLXlink(),

GLXunlink()

, and GLXwinset(). These functions don’t have exact equivalents in

OpenGL; see Appendix A for approximate equivalents.

The naming conventions for X-related functions may be confusing, as they depend largely on capitalization to differentiate between groups of functions:

GLX*()

Glx*()

IRIS GL mixed-model support

IRIS GL support for IRIS IM

glX*()

GLw*()

OpenGL support for X

OpenGL support for IRIS IM

Note that the glX*() routines are, collectively referred to as “GLX.” Note, too, that

GLXgetconfig()

(an IRIS GL mixed-model routine) isn’t at all the same function as

glXGetConfig()

(an OpenGL GLX routine). The command

IRIS% man glxgetconfig on a system with both IRIS GL and OpenGL lists both reference pages, one following the other.

90

X Window System Background

Two Choices for Using OpenGL and X

When integrating your OpenGL program with the X Window System, you have two choices:

• Use the Xt toolkit and a widget set, such as IRIS IM (see “Using Xt and a Widget

Set”)

• Write your program in Xlib and OpenGL using special GLX commands (see “Using

Xlib”).

The first method, using Xt and a widget set, is easier and is commonly used by developers. It’s recommended particularly for programmers with little or no previous experience with X.

Note:

detail.

The manual OpenGL on Silicon Graphics Systems explores both approaches in some

Whichever method you choose, you’ll find more information on programming with Xlib and Xt in the X Window System series from O’Reilly & Associates. The material in this chapter is intended as a supplement to the O’Reilly guides, detailing X development features available on Silicon Graphics workstations.

Using Xt and a Widget Set

Silicon Graphics provides a widget library that simplifies programming with Xt. “Using

Xt and a Widget Set” on page 94 explains how to convert your IRIS GL program to an

OpenGL program using Xt, the IRIS Widget Library, and the GL widget,

GLwDrawingArea (Silicon Graphics also provides an IRIS IM—Motif—version of

GLwDrawingArea, called GLwMDrawingArea.)

Using Xlib

If you prefer to use Xlib without using Xt (in effect working at a lower level), refer to the recommended references on X programming, and use the GLX routines described in the

OpenGL Reference Manual (start with the glXIntro reference page). “Using Xlib and GLX

Commands” on page 103 provides more information and contains some code examples.

Several complete programs using this method are included in Appendix F, “Example

Mixed-Model Programs With Xlib,” along with IRIS GL versions of the same programs.

91

Chapter 4: OpenGL in the X Window System

Advice for OpenGL Programs using the X Window System

This section briefly discusses two important issues:

• “Dealing With Window Depth and Display Mode”

• “Installing Color Maps”

Dealing With Window Depth and Display Mode

In OpenGL programs that use the X Window System, window depth and display mode are window attributes that are defined when the window is created, and they cannot be changed. To change these attributes, you must create a new window. If you need multiple display modes in your application, you can create multiple windows, then map and unmap them, or raise one above the others.

Installing Color Maps

It’s a good idea to call XSetWMColormapWindows(); this ensures that its color maps are installed. If you don’t call XSetWMColormapWindows(), the default X color map is used. Even if your program uses RGB mode, you should still call

XSetWMColormapWindows()

because some hardware (such as IRIS Indigo) simulates

RGB with a color map.

Fonts and Strings

OpenGL contains no equivalents for the IRIS GL text-handling calls and Font Manager calls. To obtain full text- and font-handling facilities, call glXUseXFont() with display lists to get some text-display capabilities. You can also use the GLUT font rendering calls for some more limited text- and font-handling facilities.

This section gives you an example; to use display lists to do X bitmap fonts, your program should do the following:

1.

Use X calls to load information about the font you want to use.

2. Using glXUseXFont(), generate a series of display lists, one for each character in the font.

92

Fonts and Strings

3. Put the bitmap for one character into each display list, in the order the characters appear in the font.

4. To print out a string, use glListBase() to set the display list base to the base for your character series. Then pass the string as an argument to glCallLists().

The following code fragment gives you an example, using Adobe Times Medium to print out the string “The quick brown fox jumps over a lazy dog.” It also prints out the entire character set, from ASCII 32 to 127.

Example 4-1

OpenGL Character Rendering

#include <GL/gl.h>

#include <GL/glu.h>

#include <GL/glx.h>

#include <X11/Xlib.h>

#include <X11/Xutil.h>

GLuint base; void makeRasterFont(Display *dpy)

{

XFontStruct *fontInfo;

Font id;

unsigned int first, last;

fontInfo = XLoadQueryFont(dpy,

"-adobe-times-medium-r-normal--17-120-100-100-p-88-iso8859-1"); if (fontInfo == NULL) {

printf ("no font found\n");

exit (0);

}

id = fontInfo->fid;

first = fontInfo->min_char_or_byte2;

last = fontInfo->max_char_or_byte2;

base = glGenLists(last+1);

if (base == 0) {

printf ("out of display lists\n");

exit (0);

}

glXUseXFont(id, first, last-first+1, base+first);

}

93

Chapter 4: OpenGL in the X Window System void printString(char *s)

{

glListBase(base);

glCallLists(strlen(s), GL_UNSIGNED_BYTE, (unsigned char *)s);

} void display(void)

{

GLfloat white[3] = { 1.0, 1.0, 1.0 };

long i, j;

char teststring[33];

glClear(GL_COLOR_BUFFER_BIT);

glColor3fv(white);

for (i = 32; i < 127; i += 32) {

glRasterPos2i(20, 200 - 18*i/32);

for (j = 0; j < 32; j++)

teststring[j] = i+j;

teststring[32] = 0;

printString(teststring);

}

glRasterPos2i(20, 100);

printString("The quick brown fox jumps");

glRasterPos2i(20, 82);

printString("over a lazy dog.");

glFlush ();

}

Note:

You can also use the OpenGL character renderer (glc) to render characters. See the glcintro reference page for more information.

Using Xt and a Widget Set

In general, you can bypass many of the complexities of X by using the Xt toolkit and a widget set such as IRIS IM.

When mixing OpenGL with Xt, IRIS IM, or Athena widgets, you can use the Silicon

Graphics GLwDrawingArea widget, which simplifies programming with IRIS IM or any other widget set. The GLwDrawingArea widget is also compatible with User Interface

Language (UIL). This section explains how to use the GLwMDrawingArea widget for embedding GL in an Xt or IRIS IM program. It discusses these topics:

94

Using Xt and a Widget Set

• “What You Need to Know About Xt and IRIS IM” on page 95

• “IRIS IM and Other Widget Sets” on page 96

• “Converting Your IRIS GL Program” on page 96

• “Background Reading” on page 102

What You Need to Know About Xt and IRIS IM

The examples shown in this chapter use Xt and IRIS IM. Although knowing Xt and

IRIS IM isn’t required to read this chapter, understanding the details of the examples does require some Xt and IRIS IM knowledge. This chapter points out a few areas of the

Xt and IRIS IM toolkits relevant for OpenGL programmers; it doesn’t provide a tutorial on Xt and IRIS IM.

For more information on the relevant features of Xt and IRIS IM, consult the OSF/Motif series, and Digital’s X Window System Toolkit: The Complete Programmer’s Guide and

Specification, or O’Reilly’s Volumes 4 and 5 on the X Toolkit Intrinsics, or refer to the

OpenGL on Silicon Graphics Systems manual.

About Xt

Xt, also known as the X Toolkit Intrinsics, is a C library that provides routines for creating and using user interface components called widgets. It’s usually easier to convert your

IRIS GL program using Xt than it is to use the low-level Xlib programming library.

Since Xt doesn’t dictate the “look and feel” of the GUI, you must use it in conjunction with a widget set (a library of pre-built widgets), such as the Athena widget set or IRIS

IM.

About IRIS IM

IRIS IM is the Silicon Graphics port of OSF/Motif. Motif is an extensible widget set of user interface objects, such as buttons, scroll bars, menu systems, and dialog boxes. These widgets are accessible via a library of C routines. These widgets are supported by Xt.

Ultimately, the X Window System is the foundation for both the Motif and Athena widget sets.

Motif is also a style guide, which describes the “look and feel” of a Motif compliant user interface.

95

Chapter 4: OpenGL in the X Window System

IRIS IM and Other Widget Sets

This section refers frequently to IRIS IM because it is commonly used with OpenGL programs; however, unless otherwise specified, you can use the features discussed here with other widget sets, such as the Athena widget set. The features discussed in this chapter exist either within the widget itself or are based on the X toolkit. You therefore have a choice:

• Use the generic GLwDrawingArea widget.

• Use the IRIS IM (Motif) widget GLwMDrawingArea.

Combining OpenGL and Motif is made easier by a specially supplied OpenGL drawing area widget, GLwDrawingArea. Use the GLwDrawingArea widget when integrating your OpenGL program with Xt. The GLwDrawingArea widget sets up a configuration for GL drawing and provides resources and callbacks that are useful to the OpenGL programmer. The GLwDrawingArea widget also provides support for overlays.

There are actually two GLwDrawingArea widgets. The widget known as

GLwDrawingArea is a generic widget, suitable for use with any widget set that’s based on the Xt intrinsics. There is also a version known as GLwMDrawingArea (note the M) for use with IRIS IM programs.

The two widgets are very similar, but they do have these differences:

• GLwMDrawingArea is a subclass of the IRIS IM XmPrimitive widget, rather than being a subclass of the Xt Core widget and, therefore, has various defaults such as background color.

• GLwMDrawingArea understands IRIS IM traversal, although traversal is turned off by default.

• You can create GLwMDrawingArea directly through Xt or use an IRIS IM creation function, GlxCreateMDrawingArea().

In all other respects, the two widgets are identical. The remainder of this chapter refers to the GlxMDraw widget, but unless otherwise specified, everything stated refers to both.

Converting Your IRIS GL Program

This section discusses the actual conversion process:

96

Using Xt and a Widget Set

• “Finding Areas for Porting” explains how your can determine which parts of your

IRIS GL program you need to replace with X.

• “Using the OpenGL Widget” provides an example program of OpenGL inside the

OpenGL widget.

Finding Areas for Porting

When porting to OpenGL, you have to replace any IRIS GL windowing and event handling code. One way to do this is to run toogl and then search through the output for the toogl warnings marked “OGLXXX.” It should be reasonably straightforward to determine which warnings relate to X.

Using the OpenGL Widget

This section shows a simple example of a program that uses the IRIS IM version of the

OpenGL widget and explains how the code works.

The generic version of the widget can be used in the same way. To compile this example, use this command line:

% cc -O -o mixed mixed.c -lXm -lGL -lGLw -lGLU

When the OpenGL widget is initially opened, its visual must be set. In other words, you must first declare the display mode of the visual: single or double buffer, color index or

RGBA mode. You may also specify how many bits will be used by the components of the frame buffer: for example, depth, stencil, and accumulation bits.

In the program shown in Example 4-2, the function init_window(), which is registered with the GlxNginitCallback callback, calls glXCreateContext() to set the visual of the

OpenGL widget. In this case, the resources for the widget are set to support RGBA and double buffer mode. (See the fallback_resources[] array in the main() procedure.)

OpenGL Program Using IRIS IM OpenGL Widget

Example 4-2

/* mixed.c

*/

#include <Xm/Xm.h>

#include <Xm/Form.h>

#include <X11/keysym.h>

#include <X11/StringDefs.h>

#include "GL/GLwMDrawA.h"

97

Chapter 4: OpenGL in the X Window System

#include <GL/gl.h>

#include <GL/glu.h>

#include <stdio.h>

#include <stdlib.h> static void input(Widget, XtPointer, XtPointer); static void draw_scene_callback (Widget, XtPointer,

XtPointer); static void do_resize(Widget, XtPointer, XtPointer); static void init_window(Widget, XtPointer, XtPointer); static GLXContext glx_context; void main(int argc, char** argv)

{

Arg args[20];

int n;

Widget glw, toplevel, form;

static XtAppContext app_context;

static String fallback_resources[] = {

"*glwidget*width: 300",

"*glwidget*height: 300",

"*glwidget*rgba: TRUE",

"*glwidget*doublebuffer: TRUE",

"*glwidget*allocateBackground: TRUE",

NULL

};

toplevel = XtAppInitialize(&app_context, "Mixed", NULL,

0, &argc, argv,

fallback_resources, NULL, 0);

n = 0;

form = XmCreateForm(toplevel, "form", args, n);

XtManageChild(form);

n = 0;

XtSetArg(args[n], XmNbottomAttachment, XmATTACH_FORM);

n++;

XtSetArg(args[n], XmNtopAttachment, XmATTACH_FORM);

n++;

XtSetArg(args[n], XmNleftAttachment, XmATTACH_FORM);

n++;

XtSetArg(args[n], XmNrightAttachment, XmATTACH_FORM);

n++;

98

Using Xt and a Widget Set

glw = GLwCreateMDrawingArea(form, "glwidget", args, n);

XtManageChild (glw);

XtAddCallback(glw, GLwNexposeCallback,

draw_scene_callback, (XtPointer) NULL);

XtAddCallback(glw, GLwNresizeCallback, do_resize,

(XtPointer) NULL);

XtAddCallback(glw, GLwNginitCallback, init_window,

(XtPointer) NULL);

XtAddCallback(glw, GLwNinputCallback, input,

(XtPointer) NULL);

XtRealizeWidget(toplevel);

XtAppMainLoop(app_context);

} static int rotation = 0; void spin (void)

{

rotation = (rotation + 5) % 360;

} static void draw_scene (Widget w)

{

GLUquadricObj *quadObj;

glClear(GL_COLOR_BUFFER_BIT);

glColor3f (1.0, 1.0, 1.0);

glPushMatrix();

glTranslatef (0.0, 0.0, -5.0);

glRotatef ((GLfloat) rotation, 1.0, 0.0, 0.0);

glPushMatrix ();

glRotatef (90.0, 1.0, 0.0, 0.0);

glTranslatef (0.0, 0.0, -1.0);

quadObj = gluNewQuadric ();

gluQuadricDrawStyle (quadObj, GLU_LINE);

gluCylinder (quadObj, 1.0, 1.0, 2.0, 12, 2);

glPopMatrix ();

glPopMatrix();

glFlush();

glXSwapBuffers (XtDisplay(w), XtWindow(w));

}

99

Chapter 4: OpenGL in the X Window System

/* Process all Input callbacks*/ static void input(Widget w, XtPointer client_data,

XtPointer call)

{

char buffer[1];

KeySym keysym;

GLwDrawingAreaCallbackStruct *call_data;

call_data = (GLwDrawingAreaCallbackStruct *) call;

switch(call_data->event->type)

{

case KeyRelease:

/* It is necessary to convert the keycode to a

* keysym before it is possible to check if it is

* an escape.

*/

if (XLookupString( (XKeyEvent *) call_data->event,

buffer, 1, &keysym,

(XComposeStatus *) NULL ) == 1

&& keysym == (KeySym) XK_Escape)

exit(0);

break;

case ButtonPress:

switch (call_data->event->xbutton.button)

{

case Button1:

spin();

draw_scene(w);

break;

}

break;

default:

break;

}

} static void draw_scene_callback(Widget w, XtPointer client_data,

XtPointer call)

{

static char firstTime = 0x1;

GLwDrawingAreaCallbackStruct *call_data;

100

Using Xt and a Widget Set

call_data = (GLwDrawingAreaCallbackStruct *) call;

GLwDrawingAreaMakeCurrent(w, glx_context);

if (firstTime) {

glViewport(0, 0, call_data->width,call_data->height);

glMatrixMode(GL_PROJECTION);

glLoadIdentity();

gluPerspective(65.0, (float) call_data->width /

(float)call_data->height, 1.0, 20.0);

glMatrixMode(GL_MODELVIEW);

glLoadIdentity();

firstTime = 0;

}

draw_scene (w);

} static void do_resize(Widget w, XtPointer client_data,

XtPointer call)

{

GLwDrawingAreaCallbackStruct *call_data;

call_data = (GLwDrawingAreaCallbackStruct *) call;

GLwDrawingAreaMakeCurrent(w, glx_context);

glViewport(0, 0, call_data->width, call_data->height);

glMatrixMode(GL_PROJECTION);

glLoadIdentity();

gluPerspective(65.0, (GLfloat) call_data->width /

(GLfloat)call_data->height, 1.0, 20.0);

glMatrixMode(GL_MODELVIEW);

glLoadIdentity();

} static void init_window(Widget w, XtPointer client_data,

XtPointer call_data)

{

Arg args[1];

XVisualInfo *vi;

GLUquadricObj *quadObj;

XtSetArg(args[0], GLwNvisualInfo, &vi);

XtGetValues(w, args, 1);

glx_context = glXCreateContext(XtDisplay(w), vi, 0,

GL_FALSE);

}

101

Chapter 4: OpenGL in the X Window System

It’s a good idea to always call GlxDrawingAreaMakeCurrent() to set the current widget.

In Example 4-2, GlxDrawingAreaMakeCurrent() is called from the callback functions.

Example 4-2 draws a wire frame cylinder using OpenGL. The GlxNinputCallback calls

input()

, which handles mouse and keyboard input. Pressing the Escape key causes the program to exit. Pressing Button1 (usually the left mouse button) calls spin(), which changes the rotation of the cylinder. Then the scene is completely redrawn.

The mixed.c program has absolutely basic placement of widgets. The OpenGL drawing area widget is attached to all sides of its parent, an IRIS IM XmForm widget. This is a minimal arrangement—you can add additional IRIS IM widgets for a more sophisticated interface.

You might also want to add a WorkProc (or idle) function, which executes when no other events are occurring. A WorkProc is useful for rendering continuous motion, which doesn’t require steady input events; for example, an animation. Appendix E, “Example

Program Using Xt and a WorkProc,” contains an example program using Xt and a

WorkProc.

Background Reading

The most complete information about OpenGL and X can be found in

Kilgard, Mark J. OpenGL Programming for the X Window System. Menlo Park, CA:

Addison-Wesley Developer’s Press. 1996. ISBN 0-201-48369-9

For more information on mixed-model programming in general, you can refer to the

OpenGL Reference Manual, which contains reference pages for the OpenGL GLX command, as well as an introductory reference page, glXIntro.

For more detailed information on programming with Xt, see Volume IV of the X Window

System Series, X Toolkit Intrinsics Programming Manual, by Adrian Nye and Tim O’Reilly, published by O’Reilly & Associates, Inc. (If you’re using IRIS IM, you’ll probably want the Motif version of Volume IV.)

For more information on IRIS IM, refer to documentation on Motif, such as the

OSF/Motif Series published by Prentice Hall.

102

Using Xlib and GLX Commands

Using Xlib and GLX Commands

Using Xlib and GLX can be more complex than using Xt and a widget set, and Silicon

Graphics doesn’t recommend it unless you’re already familiar with Xlib programming.

This section provides an overview of the necessary steps for using Xlib and GLX. It also provides some simple code examples.You’ll almost certainly need to refer to more substantial Xlib documentation (such as the O’Reilly volumes), as well as the OpenGL

Reference Manual. The glXIntro reference page is a good starting point.

This section discusses the most important aspects of using Xlib and GLX and also provides several example programs in the following sections:

• “Getting Started With Xlib and GLX”

• “Using X Color Maps” on page 105

• “Using X Color Maps” on page 105

• “Using X Events” on page 106

Getting Started With Xlib and GLX

Note:

Another example of using XLib is included in OpenGL on Silicon Graphics Systems.

To port your OpenGL code to use Xlib and GLX calls, follow these steps:

1.

Add the necessary include files to your program. (See “Header Files” on page 18 for information on what files to include.)

2. Open a connection to a display: XOpenDisplay().

3. Choose an X visual: glXChooseVisual().

4. Create a GLX context: glXCreateContext().

5. Create an X window or pixmap: XCreateWindow().

6. Connect the GLX context to the X window: glXMakeCurrent().

103

Chapter 4: OpenGL in the X Window System

Opening a Window With GLX

Example 4-3 shows a simple way of following the steps given in the previous section.You

can find a version of this code in the glXIntro reference page. This sample is more heavily commented than the one in the reference page and contains some additional examples.

Example 4-3

OpenGL and GLX Program

#include <X11/Xlib.h>

#include <GL/glx.h>

#include <GL/gl.h>

#include <stdio.h> static int attributeList[] = { GLX_RGBA, None }; static Bool WaitForNotify(Display *d, XEvent *e, char *arg)

{ return(e->type == MapNotify) && (e->xmap.window == (Window)arg); } int main(int argc, char**argv)

{

Display *dpy;

XVisualInfo *vi;

Colormap cmap;

XSetWindowAttributes swa;

Window win;

GLXContext cx;

XEvent event;

/* get a connection */

dpy = XOpenDisplay(0);

if (!dpy) {

fprintf(stderr, "Cannot open display.\n");

exit(-1);

}

/* get an appropriate visual */

vi = glXChooseVisual(dpy, DefaultScreen(dpy),

attributeList);

if (!vi) {

fprintf(stderr, "Cannot find visual with desired attributes.\n");

exit(-1);

}

/* create a GLX context */

104

Using Xlib and GLX Commands

cx = glXCreateContext(dpy, vi, 0, GL_FALSE);

if (!cx) {

fprintf(stderr, "Cannot create context.\n");

exit(-1);

}

/* create a colormap -- AllocAll for color index mode */

cmap = XCreateColormap(dpy, RootWindow(dpy, vi->screen),

vi->visual, AllocNone);

if (!cmap) {

fprintf(stderr, "Cannot allocate colormap.\n");

exit(-1);

}

/* create a window */

swa.colormap = cmap;

swa.border_pixel = 0;

/* connect the context to the window */

glXMakeCurrent(dpy, win, cx);

/* clear the buffer */

glClearColor(1,1,0,1);

glClear(GL_COLOR_BUFFER_BIT);

glFlush();

/wait for a while */

sleep(10);

/* exit cleanly */

XCloseDisplay(dpy);

exit(0);

}

Using X Color Maps

Here’s a brief example of OpenGL GLX code that demonstrates the use of color maps:

XColor xc; display = XOpenDisplay(0); visual = glXChooseVisual(display,

DefaultScreen(display), attributeList); context = glXCreateContext (display,visual,0,GL_FALSE); colorMap = XCreateColormap (display,RootWindow(display,

visual->screen), visual->visual, AllocAll);

/* Note: if you don’t say AllocAll, you can’t load */

105

Chapter 4: OpenGL in the X Window System

/* the color maps! */

...

if (index < visual->colormap_size) {

xc.pixel = index;

xc.red = (unsigned short)(red * 65535.0 + 0.5);

xc.green = (unsigned short)(green * 65535.0 + 0.5);

xc.blue = (unsigned short)(blue * 65535.0 + 0.5);

xc.flags = DoRed | DoGreen | DoBlue;

XStoreColor (display, colorMap, &xc);

}

Using X Events

Here’s a simple example of a program that uses Xlib and OpenGL GLX calls for event handling: swa.event_mask = ExposureMask | StructureNotifyMask

| KeyPressMask | KeyReleaseMask; do {

XNextEvent(dpy, &event);

switch (event.type) {

case Expose:

doRedraw = GL_TRUE;

break;

case ConfigureNotify:

width = event.xconfigure.width;

height = event.xconfigure.height;

doRedraw = GL_TRUE;

break;

case KeyPress:

{

char buf[100];

int rv;

KeySym ks;

rv = XLookupString(&event.xkey, buf, sizeof(buf), &ks, 0);

switch (ks) {

case XK_s:

case XK_S:

doSave = GL_TRUE;

break;

case XK_Escape:

return 0;

106

break;

}

}

}

} while (XPending(dpy));

Using Xlib and GLX Commands

107

Appendix A

A.

OpenGL Commands and Their IRIS GL Equivalents

Table A-1 contains a list of equivalent calls that you might find useful while porting. The first column is an alphabetical list of IRIS GL calls, the second column contains the corresponding calls to use with OpenGL, and the third column contains pointers to any relevant discussion in the text.

Note:

In many cases the OpenGL commands listed will function somewhat differently from the IRIS GL commands, and the parameters may be different as well.

Be sure to refer to the OpenGL reference pages in the OpenGL Reference Manual for detailed descriptions of the functions of the these commands and the parameters they take.

You might also need to refer to X or IRIS IM documentation; some appropriate X and IRIS

IM manuals are listed in “Where to Get More Information” on page xiv.

Table A-1

IRIS GL Call

acbuf() acsize() addtopup() afunction()

IRIS GL Commands and Their OpenGL Equivalents

OpenGL/glu/glX Equivalent

glAccum() glXChooseVisual() glutCreateMenu, glutAddmenuEntry, glutAttachmenu, or use X or IRIS

IM for menus glAlphaFunc()

Where Discussed

“Accumulation Buffer Calls” on page 61

“Accumulation Buffer Calls” on page 61

“GLX and GLUT Documentation” on page xvi

Chapter 4, glXIntro reference page,

X documentation, IRIS IM documentation

“afunction() Test Functions” on page 60

109

Appendix A: OpenGL Commands and Their IRIS GL Equivalents

Table A-1 (continued)

IRIS GL Call

arc(), arcf() backbuffer() backface() bbox2() bgnclosedline() bgncurve() bgnline() bgnpoint() bgnpolygon() bgnqstrip() bgnsurface() bgntmesh() bgntrim() blankscreen()

IRIS GL Commands and Their OpenGL Equivalents

OpenGL/glu/glX Equivalent

gluPartialDisk() a glDrawBuffer(GL_BACK) glCullFace(GL_BACK)

Not supported glBegin(GL_LINE_LOOP) gluBeginCurve() glBegin(GL_LINE_STRIP) glBegin(GL_POINTS) glBegin(GL_POLYGON)

Where Discussed

“Editing toogl Output: An

Example” on page 15 and “Porting

Arcs and Circles” on page 42 glDrawBuffer reference page glCullFace reference page

“Porting bbox2() Calls” on page 65

“Porting bgn/end Commands” on page 33 and “Porting Lines” on page 36

“NURBS Curves” on page 53

“Porting bgn/end Commands” on page 33 and “Porting Lines” on page 36

“Porting bgn/end Commands” on page 33 and “Porting Points” on page 35

“Porting bgn/end Commands” on page 33, “Porting Polygons and

Quadrilaterals” on page 37, and

“Porting Tessellated Polygons” on page 41 glBegin(GL_QUAD_STRIP) gluBeginSurface()

“Porting bgn/end Commands” on page 33 and “Porting Polygons and

Quadrilaterals” on page 37

“NURBS Surfaces” on page 54 glBegin( GL_TRIANGLE_STRIP) “Porting bgn/end Commands” on page 33 and “Porting Triangles” on page 41 gluBeginTrim() “Trimming Curves” on page 54

Use X for windowing.

Chapter 4 and glXIntro reference page

110

Table A-1 (continued)

IRIS GL Call

blanktime() blendcolor() blendfunction() blink() blkqread() c3*(), c4*() callfunc() callobj() charstr() chunksize() circ(), circf() clear() clearhitcode() clipplane() clkon() clkoff()

IRIS GL Commands and Their OpenGL Equivalents

OpenGL/glu/glX Equivalent Where Discussed

Use X for windowing.

glBlendColorEXT() glBlendFunc()

Chapter 4 and glXIntro reference page

“Porting RealityEngine Graphics

Features” on page 83

“Blending” on page 59

Use GLUT or X for color maps.

“GLX and GLUT Documentation” on page xvi, Chapter 4 and glXIntro reference page

Use GLUT or X for event handling. “GLX and GLUT Documentation” on page xvi, Chapter 4 and glXIntro reference page glColor*() “Porting Color, Shading, and

Writemask Commands” on page 44

Not supported.

glCallList() glCallLists()

Not needed.

“Porting Display Lists” on page 63

“Porting bgn/end Commands” on page 33 and “Porting Display Lists” on page 63

“Fonts and Strings” on page 92

“Porting Display Lists” on page 63 gluDisk() “Porting Arcs and Circles” on page 42 glClear(GL_COLOR_BUFFER_BIT) “Windowing, Device, and Event

Calls” on page 11 and “Porting

Screen and Buffer Clearing

Commands” on page 23

Not supported glClipPlane()

XChangeKeyboardControl()

XChangeKeyboardControl()

“Porting Picking Calls” on page 79

“Porting Clipping Planes” on page 30

See X documentation.

See X documentation.

111

Appendix A: OpenGL Commands and Their IRIS GL Equivalents

Table A-1 (continued)

IRIS GL Call

closeobj() cmode() cmov(), cmov2() color(), colorf()

IRIS GL Commands and Their OpenGL Equivalents

OpenGL/glu/glX Equivalent

glEndList() glutInitDisplayMode, glXChooseVisual() glRasterPos3() glRasterPos2() glIndex*() a a

,

Where Discussed

“Porting Display Lists” on page 63

GLX and GLUT Documentation,

Chapter 4 and glXIntro and glXChooseVisual() reference pages

“Porting Pixel Operations” on page 46

“Porting bgn/end Commands” on page 33 and “Porting Color,

Shading, and Writemask

Commands” on page 44 compactify() concave() convolve() cpack()

Not needed.

gluBeginPolygon() a glConvolutionFilter2DEXT(), glSeparableFilter2DEXT(), glConvolutionParameterEXT(), glPixelTransfer() glColor*() a

“Porting RealityEngine Graphics

Features” on page 83 crv() crvn() curorigin() cursoff() curson()

Not supported.

Not supported.

Use X for cursors.

Use X for cursors.

Use X for cursors.

“Porting bgn/end Commands” on page 33 and “Porting Color,

Shading, and Writemask

Commands” on page 44

“Porting Curve and Surface

Commands” on page 52

“Porting Curve and Surface

Commands” on page 52

Chapter 4, glXIntro reference page,

X documentation

Chapter 4, glXIntro reference page,

X documentation

Chapter 4, glXIntro reference page,

X documentation

112

Table A-1 (continued)

IRIS GL Call

curstype() curvebasis() curveit() curveprecision() cyclemap() czclear() dbtext() defbasis() defcursor() deflinestyle() defpattern() defpup()

IRIS GL Commands and Their OpenGL Equivalents

OpenGL/glu/glX Equivalent Where Discussed

glutSetCursor, or use X for cursors GLX and GLUT Documentation,

Chapter 4, glXIntro reference page,

X documentation glMap1() glEvalMesh1()

“Porting Curve and Surface

Commands” on page 52

“Porting Curve and Surface

Commands” on page 52

Not supported.

Use GLUT or use X for color maps. “GLX and GLUT Documentation” on page xvi, Chapter 4, and glXIntro reference page glClear( GL_COLOR_BUFFER_BIT

| GL_DEPTH_BUFFER_BIT)

“Porting Screen and Buffer Clearing

Commands” on page 23

Not supported glMap1()

IRIS GL Dial and Button Box documentation

“Porting Curve and Surface

Commands” on page 52 glutSetCursor, or use X for cursors GLX and GLUT Documentation,

Chapter 4, glXIntro reference page,

X documentation glLineStipple()

“Porting Curve and Surface

Commands” on page 52 glPolygonStipple()

Use GLUT or use X for menus.

“Porting Lines” on page 36 and

“Porting defs, binds, and sets:

Replacing ‘Tables’ of Stored

Definitions” on page 67

“Porting Polygons and

Quadrilaterals” on page 37 and

“Porting defs, binds, and sets:

Replacing ‘Tables’ of Stored

Definitions” on page 67

“GLX and GLUT Documentation” on page xvi, Chapter 4, glXIntro reference page, X documentation

113

Appendix A: OpenGL Commands and Their IRIS GL Equivalents

Table A-1 (continued)

IRIS GL Call

defrasterfont() delobj() deltag() depthcue()

IRIS GL Commands and Their OpenGL Equivalents

OpenGL/glu/glX Equivalent

GLUT font rendering functions, glXUseXFont() a glDeleteLists()

Not supported.

glFog() a

Where Discussed

“GLX and GLUT Documentation” on page xvi, “Fonts and Strings” on page 92

“Porting Display Lists” on page 63

“Porting Display Lists” on page 63

“Porting Depth Cueing and Fog

Commands” on page 48 dglclose() dglopen() displacepolygon() dither()

Not needed—OpenGL is network transparent.

Not needed—OpenGL is network transparent.

glPolygonOffsetEXT() glPolygonOffset()—OpenGL 1.1

glEnable(GL_DITHER)

“Porting RealityEngine Graphics

Features” on page 83 dopup() doublebuffer() draw()

Use GLUT or use X for menus.

glXChooseVisual() glBegin(GL_LINES) a

“Porting Color, Shading, and

Writemask Commands” on page 44

GLX and GLUT Documentation,

Chapter 4, glXIntro reference page,

X documentation

Chapter 4 and glXIntro reference page

“Porting Commands That Required

Current Graphics Positions” on page 22 and “Porting Lines” on page 36 drawmode() editobj() endclosedline() glXMakeCurrent() a

Not supported.

glEnd()

“Porting Display Lists” on page 63

“Porting bgn/end Commands” on page 33 and “Porting Lines” on page 36

114

Table A-1 (continued)

IRIS GL Call

endcurve() endfeedback() endfullscreen() endline() endpick() endpoint() endpolygon() endpupmode() endqstrip() endselect() endsurface() endtmesh() endtrim() fbsubtexload() feedback() finish()

IRIS GL Commands and Their OpenGL Equivalents

OpenGL/glu/glX Equivalent Where Discussed

gluEndCurve() “Porting Curve and Surface

Commands” on page 52

“Porting Feedback Calls” on page 80 glRenderMode(GL_RENDER)

Not supported.

glEnd() glRenderMode(GL_RENDER) glEnd() glEnd()

“Porting bgn/end Commands” on page 33

“Porting Picking Calls” on page 79

“Porting bgn/end Commands” on page 33 and “Porting Points” on page 35

“Porting bgn/end Commands” on page 33 and “Porting Polygons and

Quadrilaterals” on page 37

Use GLUT or use X for menus.

glEnd()

GLX and GLUT Documentation,

Chapter 4, glXIntro reference page,

X documentation

“Porting bgn/end Commands” on page 33 and “Porting Polygons and

Quadrilaterals” on page 37

“Porting Picking Calls” on page 79

“NURBS Surfaces” on page 54 glRenderMode(GL_RENDER) gluEndSurface() glEnd() “Porting bgn/end Commands” on page 33 and “Porting Triangles” on page 41

“Trimming Curves” on page 54 gluEndTrim()

Not supported in OpenGL 1.0. Use glSubTexture*() in OpenGL 1.1.

“Porting RealityEngine Graphics

Features” on page 83 glFeedbackBuffer() glFinish()

“Porting Feedback Calls” on page 80

115

Appendix A: OpenGL Commands and Their IRIS GL Equivalents

Table A-1 (continued)

IRIS GL Call

fogvertex() font() foreground() freepup() frontbuffer() frontface() fsubtexload() fudge() fullscrn() gammaramp() gbegin() gconfig() genobj() gentag() getbackface() getbuffer()

IRIS GL Commands and Their OpenGL Equivalents

OpenGL/glu/glX Equivalent Where Discussed

glFog() “Porting Depth Cueing and Fog

Commands” on page 48

See glListBase().

glutSwapBuffers, glutPushWindow, glutPopWindow, or use X for windowing

GLX and GLUT Documentation,

Chapter 4 and glXIntro reference page

Use GLUT or X for menus.

GLX and GLUT Documentation,

Chapter 4, glXIntro reference page,

X documentation glDrawBuffer(GL_FRONT)

See glCullFace().

glCopyTexSubImage2D()—

OpenGL 1.1

Use X for windowing.

glutFullScreen

Use GLUT or X for color maps.

Use X for windowing.

No equivalent (not needed).

See GLX and GLUT Documentation

GLX and GLUT Documentation,

Chapter 4 and glXIntro reference page

Chapter 4 and glXIntro reference page

Chapter 4 and glXIntro reference page

“Porting Display Lists” on page 63 glGenLists()

Not supported.

glGet*() glGet*()

“Porting IRIS GL get* Commands” on page 20

“Porting IRIS GL get* Commands” on page 20

116

Table A-1 (continued)

IRIS GL Call

getbutton() getcmmode()

IRIS GL Commands and Their OpenGL Equivalents

OpenGL/glu/glX Equivalent

Use X for windowing.

glXGetCurrentContext()

Where Discussed

“Porting IRIS GL get* Commands” on page 20, Chapter 4, and glXIntro reference page

“Porting IRIS GL get* Commands” on page 20, Chapter 4 and “Porting

Color, Shading, and Writemask

Commands” on page 44 getcolor() getcpos() glGet*() glGet*() getcursor() getdcm() getdepth() getdescender() getdev() getdisplaymode() getdrawmode() getfont()

Not supported.

glIsEnabled() glGet*()

Use X for fonts.

Not supported.

glGet*() glXGetCurrentContext()

Use GLUT or X for fonts.

“Porting IRIS GL get* Commands” on page 20

“Porting IRIS GL get* Commands” on page 20

“Porting IRIS GL get* Commands” on page 20 and “Porting Depth

Cueing and Fog Commands” on page 48

“Porting IRIS GL get* Commands” on page 20

“Fonts and Strings” on page 92 and

“Porting IRIS GL get* Commands” on page 20

“Porting IRIS GL get* Commands” on page 20

“Porting IRIS GL get* Commands” on page 20

“Porting IRIS GL get* Commands” on page 20

GLX and GLUT Documentation,

“Porting IRIS GL get* Commands” on page 20 and “Fonts and Strings” on page 92

117

Appendix A: OpenGL Commands and Their IRIS GL Equivalents

Table A-1 (continued)

IRIS GL Call

getgdesc() getgpos() getheight() gethgram() gethitcode() getlsbackup() getlsrepeat() getlstyle() getlwidth() getmap(void)

IRIS GL Commands and Their OpenGL Equivalents

OpenGL/glu/glX Equivalent

glGet*(), glXGetConfig(), glXGetCurrentContext(), glXGetCurrentDrawable()

Not supported.

Where Discussed

“Porting IRIS GL get* Commands” on page 20

Use X for fonts.

glGetHistogramEXT()

Not supported.

Not supported.

glGet*() glGet*() glGet*()

Not supported.

“Porting Commands That Required

Current Graphics Positions” on page 22 and “Porting IRIS GL get*

Commands” on page 20

GLX and GLUT Documentation,

“Fonts and Strings” on page 92 and

“Porting IRIS GL get* Commands” on page 20

“Porting RealityEngine Graphics

Features” on page 83

“Porting Picking Calls” on page 79 and “Porting IRIS GL get*

Commands” on page 20

“Porting Lines” on page 36 and

“Porting IRIS GL get* Commands” on page 20

“Porting IRIS GL get* Commands” on page 20 and “Porting Lines” on page 36

“Porting IRIS GL get* Commands” on page 20 and “Porting Lines” on page 36

“Porting IRIS GL get* Commands” on page 20 and “Porting Lines” on page 36

“Porting IRIS GL get* Commands” on page 20, Chapter 4 and “Porting

Color, Shading, and Writemask

Commands” on page 44

118

Table A-1 (continued)

IRIS GL Call

getmatrix() getmcolor() getminmax() getmmode() getmonitor() getnurbsproperty() getopenobj() getorigin() getpattern() getplanes() getport()

IRIS GL Commands and Their OpenGL Equivalents

OpenGL/glu/glX Equivalent

glGet*(GL_MODELVIEW_

MATRIX), glGet*(GL_PROJECTION_

MATRIX)

Not supported.

Where Discussed

“Porting IRIS GL get* Commands” on page 20 and “Porting Matrix and

Transformation Calls” on page 24 glGetMinmaxEXT() glGet*(GL_MATRIX_MODE)

Not supported.

gluGetNurbsProperty()

Not supported.

Use X for windowing.

glGetPolygonStipple() glGet*(GL_RED_BITS), glGet*(GL_GREEN_BITS), glGet*(GL_BLUE_BITS)

Use X for windowing.

“Porting IRIS GL get* Commands” on page 20, “Porting Color, Shading, and Writemask Commands” on page 44, Chapter 4 and glXIntro reference page

“Porting RealityEngine Graphics

Features” on page 83

“Porting get* Calls for Matrices and

Transformations” on page 29.

“Porting IRIS GL get* Commands” on page 20

“Porting IRIS GL get* Commands” on page 20

“Porting Display Lists” on page 63 and “Porting IRIS GL get*

Commands” on page 20

“Porting IRIS GL get* Commands” on page 20 and Chapter 4 and glXIntro reference page

“Porting IRIS GL get* Commands” on page 20 and “Porting Polygons and Quadrilaterals” on page 37

“Porting IRIS GL get* Commands” on page 20

“Porting IRIS GL get* Commands” on page 20, Chapter 4, and glXIntro reference page

119

Appendix A: OpenGL Commands and Their IRIS GL Equivalents

Table A-1 (continued)

IRIS GL Call

getresetls() getscrbox() getscrmask() getshade() getsize() getsm() getvaluator() getvideo() getviewport() getwritemask()

IRIS GL Commands and Their OpenGL Equivalents

OpenGL/glu/glX Equivalent Where Discussed

Not supported.

Not supported.

glGet*(GL_SCISSOR_BOX) glGet*( GL_CURRENT_INDEX)

“Porting Lines” on page 36 and

“Porting IRIS GL get* Commands” on page 20

“Porting IRIS GL get* Commands” on page 20 and “Porting Viewports,

Screenmasks, and Scrboxes” on page 30

“Porting IRIS GL get* Commands” on page 20 and “Porting Viewports,

Screenmasks, and Scrboxes” on page 30

“Porting IRIS GL get* Commands” on page 20

Use X for windowing.

glGet*(GL_SHADE_MODEL)

Use glutMainLoop() or use X for event handling.

Not supported.

“Porting IRIS GL get* Commands” on page 20, Chapter 4, and glXIntro reference page

“Porting IRIS GL get* Commands” on page 20 and “Porting Color,

Shading, and Writemask

Commands” on page 44

GLX and GLUT Documentation,

“Porting IRIS GL get* Commands” on page 20, Chapter 4, and glXIntro reference page

“Porting IRIS GL get* Commands” on page 20 glGet*(GL_VIEWPORT) “Porting IRIS GL get* Commands” on page 20 and “Porting Viewports,

Screenmasks, and Scrboxes” on page 30 glGet*( GL_INDEX_WRITEMASK) “Porting IRIS GL get* Commands” on page 20 and “Porting Color,

Shading, and Writemask

Commands” on page 44

120

Table A-1 (continued)

IRIS GL Call

getwscrn() getzbuffer() gexit() gflush() ginit() glcompat()

GLXgetconfig()

GLXlink()

GLXunlink()

GLXwinset() greset() gRGBcolor() gRGBcursor() gRGBmask() gselect()

IRIS GL Commands and Their OpenGL Equivalents

OpenGL/glu/glX Equivalent Where Discussed

Use X for windowing.

glIsEnabled( GL_DEPTH_TEST)

“Porting IRIS GL get* Commands” on page 20, Chapter 4 and glXIntro reference page

“Porting IRIS GL get* Commands” on page 20

Use X for windowing.

glFlush()

Use GLUT or use X for windowing. GLX and GLUT Documentation,

Chapter 4, and glXIntro reference page

Not supported.

glXChooseVisual(), glXGetConfig() Chapter 4 and glXIntro reference page

Combination of glXCreateContext() and glXMakeCurrent()

Chapter 4 and glXIntro reference page glXMakeCurrent(display_name,

None, NULL) glXMakeCurrent() has some of the functionality.

Not supported.

glGet*(GL_CURRENT_

RASTER_COLOR)

Use GLUT or use X for cursors.

Chapter 4 and glXIntro reference page

Chapter 4 and glXIntro reference page

“Porting greset()” on page 19

“Porting Color, Shading, and

Writemask Commands” on page 44 glGet*(

GL_COLOR_WRITEMASK) glSelectBuffer()

GLX and GLUT Documentation,

Chapter 4, glXIntro reference page,

X documentation

“Porting Color, Shading, and

Writemask Commands” on page 44

121

Appendix A: OpenGL Commands and Their IRIS GL Equivalents

Table A-1 (continued)

IRIS GL Commands and Their OpenGL Equivalents

IRIS GL Call OpenGL/glu/glX Equivalent Where Discussed

gsync() gversion() hgram() iconsize() icontitle() ilbuffer() ildraw() imakebackground()

Use GLUt or use X for windowing. GLX and GLUT Documentation,

Chapter 4 and glXIntro reference page glGetString( GL_RENDERER) a

Chapter 4 and glXIntro reference page glHistogramEXT(), glResetHistogramEXT() glutIconifyWindow, or use X

“Porting RealityEngine Graphics

Features” on page 83

GLX and GLUT Documentation or X documentation for XIconSize() glutSetIconTitle, or use X

Not supported.

Not supported.

Use X for event handling.

GLX and GLUT Documentation or X documentation for XSetIconName()

“Porting RealityEngine Graphics

Features” on page 83

“Porting RealityEngine Graphics

Features” on page 83

Chapter 4 and glXIntro reference page initnames() ismex() isobj() isqueued() glInitNames()

Not supported.

glIsList()

Use X for event handling.

istag() istexloaded() keepaspect() lampoff()

Not supported.

glAreTexturesResident() —

OpenGL 1.1

Use X for windowing.

Not supported.

“Porting Display Lists” on page 63

Chapter 4 and glXIntro reference page

“Stencil Plane Calls” on page 63

“Porting RealityEngine Graphics

Features” on page 83

Chapter 4 and glXIntro reference page

See X documentation for

XChangeKeyboardControl().

122

Table A-1 (continued)

IRIS GL Call

lampon() leftbuffer() linesmooth() linewidth() linewidthf*() lmbind()

IRIS GL Commands and Their OpenGL Equivalents

OpenGL/glu/glX Equivalent

Not supported.

glDrawBuffer(GL_LEFT) glEnable( GL_LINE_SMOOTH) glLineWidth() glEnable(GL_LIGHTING) glEnable(GL_LIGHTi)

Where Discussed

See X documentation for

XChangeKeyboardControl().

“Porting RealityEngine Graphics

Features” on page 83

“Porting Lines” on page 36 and

“Antialiasing Calls” on page 60

“Porting Lines” on page 36 lmcolor() lmdef() loadmatrix() loadname() logicop() lookat() lrectread() lrectwrite() glColorMaterial() glMaterial() glLight() glLightModel() glLoadMatrix() glLoadName() glLogicOp() gluLookAt() a glReadPixels() glDrawPixels()

“Porting bgn/end Commands” on page 33, “Porting defs, binds, and sets: Replacing ‘Tables’ of Stored

Definitions” on page 67, and

“Porting Lighting and Materials

Calls” on page 68

“Porting Lighting and Materials

Calls” on page 68

“Porting defs, binds, and sets:

Replacing ‘Tables’ of Stored

Definitions” on page 67 and

“Porting Lighting and Materials

Calls” on page 68

“Porting Matrix and Transformation

Calls” on page 24

“Porting Picking Calls” on page 79

“Porting Pixel Operations” on page 46

“Porting Matrix and Transformation

Calls” on page 24

“Porting Pixel Operations” on page 46

“Porting Pixel Operations” on page 46

123

Appendix A: OpenGL Commands and Their IRIS GL Equivalents

Table A-1 (continued)

IRIS GL Call

lRGBrange() lsbackup() lsetdepth() lshaderange() lsrepeat() makeobj() maketag() mapcolor() mapw() maxsize() minmax() minsize() mmode() monobuffer() move()

IRIS GL Commands and Their OpenGL Equivalents

OpenGL/glu/glX Equivalent Where Discussed

Not supported; see glFog().

Not supported.

glDepthRange()

Not supported; see glFog().

“Porting Depth Cueing and Fog

Commands” on page 48

“Porting Lines” on page 36

“Porting Depth Cueing and Fog

Commands” on page 48

“Porting Depth Cueing and Fog

Commands” on page 48 glLineStipple() glNewList()

Not supported.

XStoreColor() gluProject()

“Porting Lines” on page 36

“Porting Display Lists” on page 63

“Stencil Plane Calls” on page 63

Chapter 4

“Porting Matrix and Transformation

Calls” on page 24

Use GLUT or use X for windowing. GLX and GLUT Documentation,

Chapter 4 and glXIntro reference page glMinmaxEXT() “Porting RealityEngine Graphics

Features” on page 83

Use GLUT or use X for windowing. GLX and GLUT Documentation,

Chapter 4 and glXIntro reference page glMatrixMode()

Superseded by selection of an appropriate GLX visual.

Not supported.

“Porting Matrix and Transformation

Calls” on page 24 glXChooseVisual() reference page and “Porting RealityEngine

Graphics Features” on page 83

“Porting Commands That Required

Current Graphics Positions” on page 22

124

Table A-1 (continued)

IRIS GL Call

msalpha() msmask() mspattern() mssize() mswapbuffers() multimap() multisample() multmatrix() n3f() newpup() newtag() nmode() noborder() noise()

IRIS GL Commands and Their OpenGL Equivalents

OpenGL/glu/glX Equivalent Where Discussed

glEnable(GL_SAMPLE_ALPHA_T

O_MASK_SGIS), glEnable(GL_SAMPLE_ALPHA_T

O_ONE_SGIS) glSampleMaskSGIS()

“Porting RealityEngine Graphics

Features” on page 83 glSamplePatternSGIS()

“Porting RealityEngine Graphics

Features” on page 83

“Porting RealityEngine Graphics

Features” on page 83 glXChooseVisual with attribute

GLX_SAMPLE_BUFFERS_SGIS glutSwapBuffers, glxSwapbuffers GLX and GLUT Documentation or X documentation

Use X for color maps.

“Porting RealityEngine Graphics

Features” on page 83

“Porting Color, Shading, and

Writemask Commands” on page 44, also Chapter 4, glXIntro reference page glEnable(

GL_MULTISAMPLE_SGIS) glMultMatrix()

“Porting RealityEngine Graphics

Features” on page 83 glNormal3fv()

Use GLUT or X for menus.

“Porting bgn/end Commands” on page 33

GLX and GLUT Documentation,

Chapter 4, glXIntro reference page,

X documentation

“Porting Display Lists” on page 63 Not supported.

glEnable(GL_NORMALIZE)

Use X for windowing.

Use X for event handling.

Chapter 4 and glXIntro reference page

Chapter 4 and glXIntro reference page

125

Appendix A: OpenGL Commands and Their IRIS GL Equivalents

Table A-1 (continued)

IRIS GL Call

noport()

IRIS GL Commands and Their OpenGL Equivalents

OpenGL/glu/glX Equivalent

Use X for windowing.

Where Discussed

Chapter 4 and glXIntro reference page normal() nurbscurve() glNormal3fv() gluNurbsCurve() a nurbssurface() objdelete() objinsert() objreplace() onemap() ortho() ortho2() overlay() gluNurbsSurface()

Not supported.

Not supported.

Not supported.

a

Use GLUT or X for color maps.

glOrtho() gluOrtho2D()

Use GLUT overlay functions or use X.

“NURBS Curves” on page 53 and

“Trimming Curves” on page 54

“NURBS Surfaces” on page 54

“Stencil Plane Calls” on page 63

“Stencil Plane Calls” on page 63

“Porting Display Lists” on page 63

“GLX and GLUT Documentation” on page xvi, “Porting Color,

Shading, and Writemask

Commands” on page 44, and

Chapter 4 and glXIntro reference page

“Porting Matrix and Transformation

Calls” on page 24

“Porting Matrix and Transformation

Calls” on page 24

“GLX and GLUT Documentation” on page xvi, Chapter 4, glXIntro reference pages, and glXChooseVisual() pagecolor() passthrough() patch() patchbasis()

Not supported.

glPassThrough() glEvalMesh2() a glMap2() a

“Porting Feedback Calls” on page 80

“Porting Curve and Surface

Commands” on page 52

“Porting Curve and Surface

Commands” on page 52

126

Table A-1 (continued)

IRIS GL Commands and Their OpenGL Equivalents

IRIS GL Call

patchcurves() patchprecision() pclos() pdr() perspective()

OpenGL/glu/glX Equivalent

glMap2() a

Not supported.

Not supported; see glEnd().

Not supported; see glVertex().

gluPerspective()

Where Discussed

“Porting Curve and Surface

Commands” on page 52

“Porting Curve and Surface

Commands” on page 52

“Porting Commands That Required

Current Graphics Positions” on page 22 and “Porting Polygons and

Quadrilaterals” on page 37

“Porting Commands That Required

Current Graphics Positions” on page 22 and “Porting Polygons and

Quadrilaterals” on page 37

“Porting Matrix and Transformation

Calls” on page 24

“Porting Picking Calls” on page 79 pick() gluPickMatrix() a

and glRenderMode(GL_SELECT) picksize() pixelmap() pixeltransfer() pixmode() pmv() pnt*() gluPickMatrix() glPixelMap() glPixelTransfer() glPixelTransfer() and glPixelStore() “Porting Pixel Operations” on page 46

Not supported; see glBegin() and glVertex().

“Porting Commands That Required

Current Graphics Positions” on page 22 and “Porting Polygons and

Quadrilaterals” on page 37 glBegin(GL_POINTS) pntsize(), pntsizef() glPointSize() a

“Porting Matrix and Transformation

Calls” on page 24 and “Porting

Picking Calls” on page 79

“Porting RealityEngine Graphics

Features” on page 83

“Porting RealityEngine Graphics

Features” on page 83

“Porting Points” on page 35

“Porting Points” on page 35

127

Appendix A: OpenGL Commands and Their IRIS GL Equivalents

Table A-1 (continued)

IRIS GL Call

pntsmooth() polarview() polf() poly() polymode() polysmooth() popattributes() popmatrix() popname() popviewport() prefposition() prefsize() pupmode() pushattributes() pushmatrix() pushname()

IRIS GL Commands and Their OpenGL Equivalents

OpenGL/glu/glX Equivalent Where Discussed

glEnable( GL_POINT_SMOOTH) “Porting Points” on page 35 and

“Antialiasing Calls” on page 60

Not supported; see glRotate() and glTranslate().

Not supported.

“Porting Matrix and Transformation

Calls” on page 24

“Porting Polygons and

Quadrilaterals” on page 37

Not supported.

glPolygonMode()

“Porting Polygons and

Quadrilaterals” on page 37

“Porting Polygons and

Quadrilaterals” on page 37

“Antialiasing Calls” on page 60 glEnable(

GL_POLYGON_SMOOTH) glPopAttrib(), glPopClientAttrib() “Porting greset()” on page 19 explains how to use glPopAttrib() glPopMatrix() “Porting Matrix and Transformation

Calls” on page 24 glPopName() “Porting Picking Calls” on page 79 glPopAttrib()

Use X for windowing.

“Porting Viewports, Screenmasks, and Scrboxes” on page 30

Chapter 4 and glXIntro reference page

Use X for windowing.

Use X for windowing.

Chapter 4 and glXIntro reference page

Chapter 4 and glXIntro reference page glPushAttrib(), glPushClientAttrib() glPushMatrix() glPushName()

“Porting Matrix and Transformation

Calls” on page 24

“Porting Picking Calls” on page 79

128

Table A-1 (continued)

IRIS GL Call

pushviewport() pwlcurve() qcontrol() qdevice() qenter() qgetfd() qread() qreset() qtest() rcrv(), rcrvn() rdr() readcomponent() readdisplay() readpixels()

IRIS GL Commands and Their OpenGL Equivalents

OpenGL/glu/glX Equivalent

glPushAttrib(GL_VIEWPORT) gluPWLCurve()

Use X for event handling.

Use X for event handling.

Use X for event handling.

Use X for event handling.

Use X for event handling.

Use X for event handling.

Use X for event handling.

Not supported.

Not supported.

glReadPixels() gives partial support; some readcomponent() features aren’t supported.

Not supported.

glReadPixels()

Where Discussed

“Porting Viewports, Screenmasks, and Scrboxes” on page 30

“Trimming Curves” on page 54

Chapter 4 and glXIntro reference page

Chapter 4 and glXIntro reference page

Chapter 4 and glXIntro reference page

Chapter 4 and glXIntro reference page

Chapter 4 and glXIntro reference page

Chapter 4 and glXIntro reference page

Chapter 4 and glXIntro reference page

“Porting Curve and Surface

Commands” on page 52

“Porting Commands That Required

Current Graphics Positions” on page 22

“Porting RealityEngine Graphics

Features” on page 83 readRGB() Not supported.

“Porting Pixel Operations” on page 46

“Porting Pixel Operations” on page 46

129

Appendix A: OpenGL Commands and Their IRIS GL Equivalents

Table A-1 (continued)

IRIS GL Call

readsource() rect(), rectf() rectcopy() rectread() rectwrite() rectzoom() resetls() reshapeviewport()

RGBcolor()

RGBcursor()

RGBmode()

RGBrange()

RGBsize()

RGBwritemask()

IRIS GL Commands and Their OpenGL Equivalents

OpenGL/glu/glX Equivalent Where Discussed

glReadBuffer() “Porting Pixel Operations” on page 46

See glRect() and glPolygonMode().

“Porting Polygons and

Quadrilaterals” on page 37 glCopyPixels() “Porting Pixel Operations” on page 46 glReadPixels() glDrawPixels()

“Porting Pixel Operations” on page 46

“Porting Pixel Operations” on page 46 glPixelZoom()

Not supported.

“Porting Pixel Operations” on page 46

“Porting Lines” on page 36

Not supported.

glColor()

Chapter 4 and glXIntro reference page

“Porting bgn/end Commands” on page 33 and “Porting Color,

Shading, and Writemask

Commands” on page 44

Use glutSetCursor or use X for cursors.

Use X for windowing.

GLX and GLUT Documentation,

Chapter 4, glXIntro reference page,

X documentation

Chapter 4 and glXIntro reference page

Not supported.

Not supported, but the glXChooseVisual() function does some similar things.

glColorMask() glXChooseVisual() reference page

“Porting Color, Shading, and

Writemask Commands” on page 44

130

Table A-1 (continued)

IRIS GL Call

rightbuffer() ringbell() rmv() rot() rotate() rpatch() rpdr() rpmv() sbox(), sboxf() scale() sclear() scrbox() screenspace()

IRIS GL Commands and Their OpenGL Equivalents

OpenGL/glu/glX Equivalent

glDrawBuffer(GL_RIGHT)

Not supported.

Not supported.

glRotate() glRotate()

Not supported.

Not supported.

Not supported.

glRect() glScale() glClear( a

GL_STENCIL_BUFFER_BIT)

Not supported.

Not supported.

Where Discussed

“Porting RealityEngine Graphics

Features” on page 83

X documentation for XBell()

“Porting Commands That Required

Current Graphics Positions” on page 22

“Porting Matrix and Transformation

Calls” on page 24

“Porting Matrix and Transformation

Calls” on page 24

“Porting Curve and Surface

Commands” on page 52

“Porting Commands That Required

Current Graphics Positions” on page 22 and “Porting Polygons and

Quadrilaterals” on page 37

“Porting Commands That Required

Current Graphics Positions” on page 22 and “Porting Polygons and

Quadrilaterals” on page 37

“Porting Polygons and

Quadrilaterals” on page 37

“Porting Matrix and Transformation

Calls” on page 24

“Porting Screen and Buffer Clearing

Commands” on page 23 and

“Stencil Plane Calls” on page 63

“Porting Viewports, Screenmasks, and Scrboxes” on page 30

“Porting Matrix and Transformation

Calls” on page 24

131

Appendix A: OpenGL Commands and Their IRIS GL Equivalents

Table A-1 (continued)

IRIS GL Commands and Their OpenGL Equivalents

IRIS GL Call OpenGL/glu/glX Equivalent Where Discussed

scrmask() scrnattach() scrnselect() scrsubdivide() select() setbell() setcursor() setdblights() setdepth() setlinestyle() setmap() glScissor()

Use X for windowing.

Use X for windowing.

setmonitor() Not supported.

setnurbsproperty() gluNurbsProperty() setpattern() glPolygonStipple()

“Porting Viewports, Screenmasks, and Scrboxes” on page 30

Chapter 4 and glXIntro reference page

Chapter 4 and glXIntro reference page

Not supported.

glRenderMode()

Not supported.

“Porting Picking Calls” on page 79

X documentation for

XChangeKeyboardControl() glutSetCursor, or use X for cursors GLX and GLUT Documentation,

Chapter 4, glXIntro reference page, and X documentation dial and button box documentation Not supported.

glDepthRange() a glLineStipple()

Use GLUT or X for color maps.

“Porting Lines” on page 36 and

“Porting defs, binds, and sets:

Replacing ‘Tables’ of Stored

Definitions” on page 67

GLX and GLUT Documentation,

“Porting Color, Shading, and

Writemask Commands” on page 44,

Chapter 4, and glXIntro reference page

“Porting Polygons and

Quadrilaterals” on page 37 and

“Porting defs, binds, and sets:

Replacing ‘Tables’ of Stored

Definitions” on page 67

132

Table A-1 (continued)

IRIS GL Call

setpup() setvaluator()

IRIS GL Commands and Their OpenGL Equivalents

OpenGL/glu/glX Equivalent

Use GLUT or X for menus.

Use GLUT or X for devices.

Where Discussed

GLX and GLUT Documentation,

Chapter 4, glXIntro reference page,

X documentation

GLX and GLUT Documentation,

Chapter 4, glXIntro reference page,

X documentation setvideo() shademodel()

Not supported.

glShadeModel() “Porting Color, Shading, and

Writemask Commands” on page 44 shaderange() singlebuffer() glFog()

Use X for windowing.

smoothline() spclos() splf() stencil() stensize() stepunit() stereobuffer() strwidth() subpixel() glEnable( GL_LINE_SMOOTH)

Not supported.

Not supported see glBegin().

glStencilFunc(), glStencilOp() glStencilMask()

Use X for windowing.

Superseded by selection of an appropriate GLX visual.

Use X for fonts and strings.

Not needed.

GLX and GLUT Documentation,

Chapter 4 and glXIntro reference page

“Porting Lines” on page 36

“Porting Polygons and

Quadrilaterals” on page 37

“Porting Polygons and

Quadrilaterals” on page 37

“Stencil Plane Calls” on page 63

“Stencil Plane Calls” on page 63

Chapter 4 and glXIntro reference page glXChooseVisual() reference page and “Porting RealityEngine

Graphics Features” on page 83

“Fonts and Strings” on page 92

“Porting Antialiasing Calls” on page 58

133

Appendix A: OpenGL Commands and Their IRIS GL Equivalents

Table A-1 (continued)

IRIS GL Call

subtexload() swapbuffers() swapinterval() swaptmesh() swinopen() swritemask() t2*(), t3*(), t4*() tevbind() tevdef() texbind() texdef2d()

IRIS GL Commands and Their OpenGL Equivalents

OpenGL/glu/glX Equivalent Where Discussed

glTexSubImage2DEXT()—OpenGL

1.0

glTexSubImage2D()—OpenGL 1.1

“Porting RealityEngine Graphics

Features” on page 83 glXSwapBuffers() glXIntro and glXSwapBuffers() reference pages

Not supported.

Not supported; see glBegin(GL_TRIANGLE_FAN)

Use X for windowing

“Porting Triangles” on page 41 glStencilMask()

Chapter 4 and glXIntro reference page

“Stencil Plane Calls” on page 63 glTexCoord*() glTexEnv()

“Porting Texture Calls” on page 73

“Porting defs, binds, and sets:

Replacing ‘Tables’ of Stored

Definitions” on page 67 and

“Porting Lighting and Materials

Calls” on page 68 glTexEnv() glTexImage2D(), glTexParameter(), gluBuild2DMipmaps(), glTexImage2D(), glTexParameter(), gluBuild2DMipmaps()

“Porting defs, binds, and sets:

Replacing ‘Tables’ of Stored

Definitions” on page 67, “Porting

Lighting and Materials Calls” on page 68, and “Translating tevdef()” on page 75

“Porting defs, binds, and sets:

Replacing ‘Tables’ of Stored

Definitions” on page 67 and

“Porting Texture Calls” on page 73

“Porting defs, binds, and sets:

Replacing ‘Tables’ of Stored

Definitions” on page 67, “Porting

Lighting and Materials Calls” on page 68, and “Translating texdef()” on page 76

134

Table A-1 (continued)

IRIS GL Call

texdef3d() texgen()

IRIS GL Commands and Their OpenGL Equivalents

OpenGL/glu/glX Equivalent

glTexImage3DEXT() glTexGen()

Where Discussed

“Porting RealityEngine Graphics

Features” on page 83

“Porting Lighting and Materials

Calls” on page 68 and “Translating texgen()” on page 78 textcolor() textinit() textport() tie()

Not supported.

Not supported.

Not supported.

Use X for event handling.

tlutbind() tlutdef()

Not supported.

Not supported.

Chapter 4 and glXIntro reference page

“Porting RealityEngine Graphics

Features” on page 83

“Porting RealityEngine Graphics

Features” on page 83 tpoff() tpon() translate()

Not supported.

Not supported.

glTranslate() “Porting Matrix and Transformation

Calls” on page 24 underlay() unqdevice() glXChooseVisual()

Use X for event handling.

Chapter 4 and glXIntro reference page

“Porting v() Commands” on page 33 v2*(), v3*(), v4*() videocmd() viewport() glVertex*()

Not supported.

glViewport() winattach() Use GLUT or X for windowing.

“Porting Viewports, Screenmasks, and Scrboxes” on page 30

GLX and GLUT Documentation,

Chapter 4, and glXIntro reference page

135

Appendix A: OpenGL Commands and Their IRIS GL Equivalents

Table A-1 (continued)

IRIS GL Call

winclose() winconstraints() windepth() window() winget() winmove() winopen() winpop() winposition() winpush() winset() wintitle() wmpack()

IRIS GL Commands and Their OpenGL Equivalents

OpenGL/glu/glX Equivalent Where Discussed

glXDestroyContext(),

XCloseDisplay()

Use X for windowing.

Use X for windowing.

glFrustum()

Chapter 4 and glXIntro reference page

Chapter 4 and glXIntro reference page

“Porting Matrix and Transformation

Calls” on page 24 glXGetCurrentContext() glutPositionWindow(), or use X for windowing

GLX and GLUT Documentation,

Chapter 4 and glXIntro reference page glutShowWindow(), or use X for windowing

GLX and GLUT Documentation,

Chapter 4 and glXIntro reference page glutPopWindow, or use X for windowing glutPositionWindow, or use X for windowing glColorMask()

GLX and GLUT Documentation,

Chapter 4 and glXIntro reference page

GLX and GLUT Documentation,

Chapter 4 and glXIntro reference page glutPushWindow, or use X for windowing

GLX and GLUT Documentation,

Chapter 4 and glXIntro reference page

Use GLUT or use X for windowing. GLX and GLUT Documentation,

Chapter 4 and glXIntro and glXMakeCurrent() reference pages glutSetWindowTitle, or use X for windowing

GLX and GLUT Documentation

Chapter 4 and glXIntro reference page

Chapter 4

136

Table A-1 (continued)

IRIS GL Commands and Their OpenGL Equivalents

IRIS GL Call OpenGL/glu/glX Equivalent Where Discussed

writemask() writepixels() writeRGB() xfpt*() zbsize() zbuffer() zclear() glIndexMask() glDrawPixels() glDrawPixels()

Not supported.

“Porting Picking Calls” on page 79;

“Porting Feedback Calls” on page 80

Superseded by selection of an appropriate GLX visual.

glXChooseVisual() reference page and “Porting RealityEngine

Graphics Features” on page 83 glEnable(GL_DEPTH_TEST) glClear( GL_DEPTH_BUFFER_BIT) “Porting Screen and Buffer Clearing

Commands” on page 23 zdraw() zfunction()

Not supported.

glDepthFunc() zsource() zwritemask()

Not supported.

glDepthMask() “Porting Color, Shading, and

Writemask Commands” on page 44 a. Note that this is not a direct equivalent of IRIS GL functionality—be careful when porting.

137

Appendix B

B.

Differences Between OpenGL and IRIS GL

This appendix contains a list of differences between OpenGL and IRIS GL in alphabetical order. The list is based, in part, on a document by Kurt Akeley (May 1992) that was updated by Mark Kilgard in May 1997. Each difference is given a simple concept name, based on an IRIS GL concept, followed by a description. To look up a difference, find the concept name in the alphabetical list and read the description.

accumulation from the z-buffer Reading from and writing to the z-buffer from the accumulation buffer isn’t supported in OpenGL accumulation wrapping OpenGL accumulation buffer operation is not defined when component values exceed 1.0 or go below -1.0.

antialiased lines arc attribute lists

OpenGL stipples antialiased lines. IRIS GL does not.

OpenGL supports arcs in its utility library (GLU).

The attributes pushed by IRIS GL pushattributes() differ from any of the attribute sets that are pushed by OpenGL

glPushAttrib()

and glPushClientAttrib(). Because all

OpenGL states can be read back, however, it is possible to implement any desired push/pop semantics using the

OpenGL API.

automatic mipmap generation The OpenGL texture interface does not support automatic mipmap generation. However, the utility library supports automatic generation of mipmap images for both 1D and 2D textures. See the gluBuild1DMipmaps and gluBuild2DMipmaps reference pages.

automatic texture scaling The OpenGL texture interface does not support automatic scaling of images to power-of-two dimensions. However, scaling is supported by the OpenGL utility library. See the gluScaleImage reference page.

bbox OpenGL does not support conditional execution of display lists.

139

Appendix B: Differences Between OpenGL and IRIS GL buffers, multiple callfunc circle clear options closed lines color maps color/normal flag color packing

Anything involving multiple buffers or windowing must be done in X or with GLUT.

OpenGL does not support callback from display lists. Note that IRIS GL also did not support this functionality when client and server were on different platforms.

OpenGL supports circles in the GLU. In OpenGL both circles and arcs (disks and partial disks) can have holes.

Subdivision of the primitives can be changed in OpenGL and the primitives’ surface normals are available for lighting.

OpenGL really clears buffers. It does not apply most currently specified pixel operations, such as blending and logicop, regardless of their modes, though there are some options that are applied. To clear using such features, you must render a window-size polygon.

OpenGL renders all single-width aliased lines such that abutting lines share no pixels. This means that the “last” pixel of an independent line is not drawn.

Changing the color map under OpenGL must be done using the X color map.

OpenGL lighting is explicitly enabled or disabled. When enabled, it is effective regardless of the order in which colors and normals are specified.

Lighting cannot be enabled or disabled between OpenGL

glBegin()

and glEnd() commands. If you need to disable lighting between glBegin() and glEnd(), you must do it by specifying zero ambient, diffuse, and specular material reflectance. Then set the material emission to the desired color.

OpenGL has no need for cpack(); you can use four-item vectors to specify colors instead.

140

color range with c3i() concave polygons current computed color current graphics position curves defs/binds depthcue

The OpenGL glColor*() routines that appear to correspond directly to IRIS GL c3*() and c4*() routines are not actually equivalent. For instance, the IRIS GL c3i() function took arguments in the range [0, 255] for each color; but in

OpenGL, glColor3i() allows signed arguments with values up to over two billion. Check the OpenGL Programming Guide for details on argument value ranges, and use glColor3ub() as a replacement for c3i().

The OpenGL API does not handle concave polygons, but the

GLU library does provide support for decomposing concave, non-self-intersecting contours into triangles. These triangles can either be drawn immediately or returned. See the gluNewTess reference page.

OpenGL has no notion of a current computed color. If you’re using OpenGL as a lighting engine, you can use feedback to obtain colors generated by lighting calculations.

OpenGL does not maintain a current graphics position. IRIS

GL commands that depended on current graphics position, such as relative lines and polygons, are not available in

OpenGL.

OpenGL does not support IRIS GL curves. Use of NURBS curves is recommended.

OpenGL 1.0 does not have the concept of a material, light, or texture objects, only of material, light, and texture properties. OpenGL programmers can use display lists to create their own objects. In OpenGL 1.1, you can use texture objects, as discussed in the OpenGL Programming Guide.

OpenGL provides no direct support for depth cueing.

However, its fog support is a more general capability that you can easily use to emulate IRIS GL depthcue().

141

Appendix B: Differences Between OpenGL and IRIS GL display list editing error checking error return values error side effects evaluators feedback fog

OpenGL display lists cannot be edited, only created and destroyed. Because display list names are specified by the programmer, however, it is possible to redefine individual display lists in a hierarchy.

OpenGL display lists are designed for data caching, not for database management. They are guaranteed to be stored on the server in client/server environments, so they are not limited by network bandwidth during execution.

OpenGL display lists can be called between glBegin() and

glEnd()

commands, so the display list hierarchy can be made fine enough that it can, in effect, be edited.

OpenGL checks for errors more carefully than IRIS GL. For example, all OpenGL commands that are not accepted between glBegin() and glEnd() are detected as errors, and have no other effect.

When an OpenGL command that returns a value detects an error, it always returns zero. OpenGL commands that return data through passed pointers make no change to the array contents if an error is detected.

When an OpenGL command results in an error, its only side effect is to update the error flag to the appropriate value. No other state changes are made. (An exception is the

OUT_OF_MEMORY error, which is fatal.)

Input and output that was done with such functions as

getbutton()

, qread(), and qdevice() in IRIS GL must be done using X calls with OpenGL, as must cursor-manipulation functions.

In OpenGL, feedback is standardized so that it doesn’t change from machine to machine. “Porting Feedback Calls” on page 80 explains how to port your IRIS GL feedback calls.

In OpenGL, you can’t use depth-cueing and fog at the same time, because fog is used to emulate depth-cueing. IRIS GL allows more options to fog; some OpenGL implementations may compute fog per-vertex instead of per-fragment. Some new extension for fog functionality will be released as extensions to OpenGL 1.1.

142

fonts and strings frontbuffer hollow polygons index clamping input and output integer colors integer normals

OpenGL expects character glyphs to be manipulated as individual display lists. It provides a display list calling function that accepts a list of display list names, each name represented as 1, 2, or 4 bytes. glCallLists() adds a separately specified offset to each display list name before the call, allowing lists of display list names to be treated as strings.

This mechanism provides all the functionality of IRIS GL fonts, and considerably more. For example, characters consisting of triangles can be easily manipulated.

OpenGL programs can use the OpenGL Character Renderer

(GLC) library for accessing particular fonts. See the glcintro reference page.

IRIS GL had complex rules for defeating rendering to the front buffer in singlebuffer mode. OpenGL does as it is asked in this regard.

OpenGL does not support hollow polygons. However, you can use the OpenGL stencil capability to render hollow polygons.

Where possible, OpenGL treats color and stencil indexes as bitfields rather than numbers. Thus indexes are masked, rather than clamped, to the supported range of the framebuffer.

I/O in OpenGL is usually handled by X calls. See Chapter 4 for more information.

Signed integer color components (red, green, blue, or alpha) are linearly mapped to floating point such that the most negative integer maps to -1.0 and the most positive integer maps to 1.0. This mapping occurs when the color is specified, before it replaces the current color.

Unsigned integer color components are linearly mapped to floating point such that 0 maps to 0.0 and the largest representable integer maps to 1.0. This mapping occurs when the color is specified, before it replaces the current color.

Integer normal components are mapped just like signed color components, such that the most negative integer maps to -1.0, and the most positive integer maps to 1.0.

143

Appendix B: Differences Between OpenGL and IRIS GL invariance lighting equation line stipple repeat mapw() material color

OpenGL guarantees certain invariances that IRIS GL does not. For example, OpenGL guarantees that identical code sequences sent to the same system, differing only in the blending function specified, will generate the same pixel fragments. (The fragments may be different if blending is enabled and disabled, however.)

The OpenGL lighting equation differs slightly from the IRIS

GL equation. OpenGL supports separate attenuation for each light source, rather than a single attenuation for all the light sources as in IRIS GL, and OpenGL regularizes the equation so that ambient, diffuse, and specular lighting contributions are all attenuated. In addition, OpenGL lets you specify separate colors for the ambient, diffuse, and specular intensities of light sources, and for the ambient, diffuse, and specular reflectance of materials. All OpenGL light and material colors must include an alpha value, though only the diffuse material-color alpha value is actually used for lighting.

Setting the specular exponent to zero does not defeat specular lighting in OpenGL.

OpenGL supports local lights in color index mode. IRIS GL does not.

OpenGL line stipple repeat is clamped to [1, 256], while IRIS

GL clamps this value to [1, 255].

OpenGL utilities don’t directly support mapping between object and window coordinates. If you specify the right projection matrix and viewport, you may be able to achieve the same effect using gluProject().

In IRIS GL, you could call lmcolor() between a call to

bgnprimitive()

and the corresponding endprimitive() call.

In OpenGL, you can’t call glColorMaterial() between a

glBegin()

and its corresponding glEnd().

Material coloring in IRIS GL it was connected with lighting models. In OpenGL, it’s part of the OpenGL state.

144

matrix mode All OpenGL matrix operations operate on the current matrix, rather than on a particular matrix, as do the IRIS GL

ortho()

, ortho2(), perspective(), and window() commands.

All OpenGL matrix operations except glLoadIdentity() and

glLoadMatrix()

multiply the current matrix rather than replacing it (as do ortho(), ortho2(), perspective(), and

window()

in IRIS GL).

mipmaps, automatic generation The OpenGL texture interface does not support automatic generation of mipmap images. GLU does support automatic generation of mipmap images for both 1D and 2D textures; however, GLU mipmap generation isn’t as flexible as that of

IRIS GL. (For instance, GLU doesn’t currently allow you to set weights for the texels when you average texels to generate a small mipmap from a larger one.) mixed-model move/draw/pmove/pdraw/ pclos

For an extensive discussion of this topic, see Chapter 4,

“OpenGL in the X Window System.” Note in particular that

IRIS GL mixed-model routines had, in some cases, names confusingly similar to unrelated OpenGL routines; see

“Function Naming Conventions” in Chapter 4 for details.

OpenGL supports only glBegin/glEnd style graphics, because it does not maintain a current graphics position. The scalar parameter specification of the old move/draw commands is accepted by OpenGL for all vertex related commands, however.

mprojection mode

MSINGLE mode multi-buffer drawing multisampling

IRIS GL did not transform geometry by the modelview matrix while in projection matrix mode. OpenGL always transforms by both the modelview nad the projection matrix, regardless of matrix mode.

See the entry for “single matrix mode” in this appendix.

OpenGL renders to each color buffer individually, rather than computing a single new color value based on the contents of one color buffer and writing it to all the enabled color buffers, as IRIS GL did.

Multisampling is supported only in an extension to

OpenGL. See the OpenGL on Silicon Graphics Systems document.

145

Appendix B: Differences Between OpenGL and IRIS GL normals

NURBS old polygon mode packed color formats patches per-bit color writemask per-bit depth writemask

When OpenGL transforms normals, it uses the exact inverse of the modelview matrix. Thus, all scale commands, even scale commands with the same scale values for x, y, and z, affect the lengths of transformed normals. Avoid calling

glScale()

if you want the performance advantage of leaving

GL_NORMALIZE disabled.

OpenGL supports NURBS with a combination of core capability (evaluators) and GLU support. GLU currently supports only Bernstein polynomials, not all splines; in the future, GLU may support changing the basis matrix to handle all splines. See the gluNewNurbsRenderer reference page.

Aliased OpenGL polygons are always point sampled. The old polygon compatibility mode of the IRIS GL, where pixels outside the polygon perimeter were included in its rasterization, is not supported. If your code uses old polygon mode, it’s probably for rectangles. Old polygon mode rectangles appear one pixel wider and higher.

OpenGL accepts colors as 8-bit components, but these components are treated as an array of bytes rather than as bytes packed into larger words. By encouraging array indexing rather than shifting, OpenGL promotes endian-invariant programming.

Just as IRIS GL accepted packed colors both for geometric and pixel rendering, OpenGL accepts arrays of color components for geometric and pixel rendering

OpenGL does not support IRIS GL patches. Use of evaluators is recommended.

OpenGL writemasks for color components enable or disable changes to the entire component (red, green, blue, or alpha), not to individual bits of components. Note that per-bit writemasks are supported for both color indexes and stencil indexes, however.

OpenGL writemasks for depth components enable or disable changes to the entire component, not to individual bits of the depth component.

146

performance pick pixel coordinates pixel fragments pixel zoom pixmode

The performance of an OpenGL program depends in part on whether certain OpenGL features are used. A straightforward port of an IRIS GL program will probably require tuning to achieve maximum performance in

OpenGL. For some tips on maximizing OpenGL performance, see “Performance” on page 14.

The OpenGL utility library includes support for generating a pick matrix. See the gluPickMatrix reference page.

OpenGL and IRIS GL agree that the origin of a window’s coordinate system is at its lower left corner. OpenGL places the origin at the lower left corner of this pixel, however, while IRIS GL placed it at the center of the lower left pixel.

Note that the X Window System assumes an upper left corner for its origin.

Pixels drawn by glDrawPixels() or glCopyPixels() are always rasterized and converted to fragments. The resulting fragments are textured, fogged, depth buffered, blended, and so on, just as if they had been generated from geometric points. Fragment data that are not provided by the source pixels are augmented from the current raster position. For example, RGBA pixels take the raster position Z and texture coordinates. Depth pixels take the raster position color and texture coordinates.

OpenGL negative zoom factors reflect about the current graphics position. IRIS GL doesn’t define the operation of negative zoom factors, and instead provides

RIGHT_TO_LEFT and TOP_TO_BOTTOM reflection pixmodes. These reflection modes reflect in place, rather than about the current raster position. OpenGL doesn’t define reflection modes. Also, OpenGL allows fractional zoom factors.

OpenGL pixel transfers operate on individual color components, rather than on packed groups of four 8-bit components as does IRIS GL. While OpenGL provides substantially more pixel capability than IRIS GL, it does not support packed color constructs, and it does not allow color components to be reassigned (red to green, red to blue, and so on) during pixel copy operations.

147

Appendix B: Differences Between OpenGL and IRIS GL polf()/poly() polygon mode polygon provoking vertex polygon stipple polygon vertex count readdisplay

OpenGL provides no direct support for vertex lists other than display lists. Functions like polf() and poly() can easily be implemented using the OpenGL API, however.

OpenGL supports only filled, outlined, and dotted polygons. There is no hollow polygon mode as in IRIS GL.

OpenGL polygon modes are specified separately for front and back facing polygons, while IRIS GL shares a single mode for all polygons.

Flat shaded IRIS GL polygons took the color of the last vertex specified, while OpenGL polygons take the color of the first vertex specified. (Note that this is true only for the

GL_POLYGON primitive, not for triangles, triangle strips, and other primitive types, each of which take their colors from different vertices. See the reference page for glShadeModel for details.)

In IRIS GL the polygon stipple pattern is screen-relative. In

OpenGL it is window-relative.

There is no limit to the number of vertexes between

glBegin()

and glEnd() in OpenGL, even for

glBegin(POLYGON)

. In IRIS GL polygons are limited to no more than 255 vertexes.

Reading pixels outside window boundaries is properly a window system capability, rather than a renderer capability.

Silicon Graphics supports an extension to X that replaces the

IRIS GL readdisplay() command. See the XReadDisplay reference page.

RealityEngine graphics features Many of the special RealityEngine graphics features of

IRIS GL (including multisampling and some texture-mapping features) have been implemented as extensions to OpenGL.

relativemove/draw/pmove/ pdraw/pclos

OpenGL does not maintain a current graphics position, and therefore is unable to support relative vertex operations. The semantics of such operations can easily be emulated by using the matrix and glTranslate().

reset linestyle IRIS GL resetls() has not been supported for some time, and is not supported by OpenGL.

148

RGBA logicop() sbox() scalar arguments scissor scrbox() scrsubdivide() single matrix mode specular exponent, setting to zero

OpenGL 1.0 does not support logical operations on RGBA buffers. OpenGL 1.1 adds support for logical operations on

RGBA buffers.

sbox()

is an IRIS GL rectangle primitive that is well defined only if transformed without rotation, and is designed to be faster than standard rectangles. While OpenGL does not support such a primitive, it can be tuned to render rectangles very quickly when the matrixes and other modes are in states that simplify calculations.

All OpenGL commands that are accepted between glBegin() and glEnd() have entry points that accept scalar arguments.

For example, glColor4f(red,green,blue,alpha)

.

OpenGL glScissor() does not track the viewport. The IRIS

GL viewport() command automatically updates the scrmask.

OpenGL doesn’t support bounding box computation.

OpenGL doesn’t support explicit screen subdivision.

scrsubdivide()

was used in IRIS GL to handle perspective properly when interpolating colors and textures. Most

Silicon Graphics platforms now handle texture interpolation correctly, but not all platforms do perspective-corrected color interpolation.

If you notice a perspective problem in interpolation, try specifying this hint:

glHint(GL_PERSPECTIVE_CORRECTION_HINT,

GL_NICEST)

Under some circumstances, that may improve the interpolation. GL_NICEST specifies quality at the expense of speed, however, so if speed is a high priority you may be forced to settle for linear interpolation.

OpenGL always maintains two matrices: the modelview matrix and the projection matrix. While an OpenGL implementation may consolidate these into a single matrix for performance reasons, it must always present the two-matrix model to the programmer. See “Porting

MSINGLE Mode Code” in Chapter 3 for more information.

See the entry for “lighting equation” in this appendix.

149

Appendix B: Differences Between OpenGL and IRIS GL stencil stereo subpixel mode swapbuffers() swaptmesh() texture filtering texture lookup tables texture scaling, automatic texturing, 3D uniform scaling vector arguments

When there is no depth buffer, or when the depth buffer is not enabled, the glStencilOp() argument zpass controls stencil operation when the stencil test passes. The IIS GL stencil operation is defined by its pass parameter (equivalent to OpenGL zfail) in this case.

Stereo rendering on RealityEngine graphics systems under

OpenGL is accomplished by choosing an appropriate X visual.

All OpenGL rendering is subpixel positioned—subpixel mode is always on.

Anything involving multiple buffers or windowing must be done in X or with GLUT.

OpenGL does not support the swaptmesh() capability. It does offer two types of triangle meshes, however: one that corresponds to the default “strip” behavior of the IRIS GL, and another that corresponds to calling swaptmesh() prior to the third and all subsequent vertexes when using IRIS GL.

OpenGL textures are filtered with a border when they are clamped. IRIS GL does not use the border data in this case.

Texture lookup tables aren’t supported in OpenGL 1.0 but are supported in OpenGL 1.1.

The OpenGL texture interface does not support automatic scaling of images to power-of-two dimensions. However, the GLU supports image scaling.

Three-dimensional texturing is provided as part of an extension to OpenGL.

If you use only unit-length normals in IRIS GL, and if the modelview matrix is the product only of rotations and uniform scales, you don’t need to enable normalization of the normal vectors.

In OpenGL, however, uniform scaling does affect the length of normal vectors, even unit-length normals

All OpenGL commands that are accepted between glBegin() and glEnd() have entry points that accept vector arguments.

For example, glColor4fv(v).

150

window management window offset

z-buffer, reading from

z-buffer sizing

z rendering

OpenGL includes no window system commands. It is always supported as an extension to a window or operating system that includes capability for device and window control. Each extension provides a system-specific mechanism for creating, destroying, and manipulating

OpenGL rendering contexts. For example, the OpenGL extension to the X window system (GLX) includes roughly ten commands for this purpose.

IRIS GL commands such as gconfig() and drawmode() are not implemented by OpenGL.

In OpenGL, windows have static frame buffer configurations.

IRIS GL returned viewport and character position in screen, rather than window, coordinates. OpenGL always deals with window coordinates.

If you wanted to read from the z-buffer in IRIS GL, you specified that buffer with readsource() and then used

lrectread()

or rectread() to do the reading. If you want to read from the z-buffer in OpenGL, you simply specify that buffer as a parameter to glReadPixels().

Changing the depth of the z-buffer can be done by selecting an appropriate visual.

OpenGL does not support rendering colors to the depth buffer. It does allow for additional color buffers, which can be implemented using the same memory that is used for depth buffers in other window configurations—but these additional color buffers cannot share memory with the depth buffer in any single configuration.

151

Appendix C

C.

OpenGL Names, Types, and Error

This appendix provides some background information on OpenGL command names, defined types, and error handling. It’s intended mainly as a quick reference. For more detailed information, refer to the OpenGL Programming Guide.

OpenGL Command Names

This section describes the naming convention for OpenGL calls. For a complete list of

OpenGL equivalents to IRIS GL routines, see Appendix A, “OpenGL Commands and

Their IRIS GL Equivalents.”

gl—

OpenGL commands begin with the gl prefix (glEnable(), glTranslatef(), and so on).

glu—

OpenGL Utility Library (GLU) commands begin with the glu prefix

(gluDisk(), gluErrorString(), and so on).

glX—

Commands that belong to the OpenGL extension to X (GLX) begin with the glX prefix (glXChooseVisual(), glXCopyContext(), and so on).

glut

—Commands in the GLUT (OpenGL Utility Toolkit) library begin with a glut prefix (glutInit, glutMenuStatusFunc, and so on).

OpenGL commands are formed by a root name, optionally followed by up to four characters. The first character indicates the number of arguments. The second character, or pair of characters, specifies the type of the arguments. Table C-1 lists the character suffixes and the corresponding argument types (some of these values might be different on a 64-bit architecture).

Table C-1

Letter b s

Command Suffixes and Corresponding Argument Types

Type

8-bit integer

16-bit integer

C Type

char short

153

Appendix C: OpenGL Names, Types, and Error

i

Letter f d ub us ui

Table C-1 (continued)

Command Suffixes and Corresponding Argument Types

Type

32-bit integer

32-bit floating point

64-bit floating point

8-bit unsigned integer

16-bit unsigned integer

32-bit unsigned integer

C Type

long float double unsigned char unsigned short unsigned long

The final character, if present, is v. The v indicates that the command takes a pointer to an array of values—a vector—rather than a series of individual arguments.

IRIS GL used a similar mechanism for some commands. The predecessor to glVertex*(), for example, was v(), which also used a suffix to specify the number and type of its arguments.

Here are some examples of OpenGL command naming: void glVertex2i( GLint x, GLint y); void glVertex3f( GLfloat x, GLfloat y, GLfloat z); void glVertex3dv( const GLdouble *v) ;

The first version of the vertex call, glVertex2i(), takes two integer arguments. The second,

glVertex3f()

, is a three-dimensional version, which expects three floats. The third version, glVertex3dv(), expects an argument in the form of a vector, which is a pointer to an array. In this case, the array should have three elements.

154

OpenGL Defined Types

OpenGL Defined Types

Table C-2 lists C data types and their equivalent OpenGL defined types.

Table C-2

OpenGL Equivalents to C Data Types

C Type

bitmask value boolean value double double value clamped to [ 0.0, 1.0 ] enumerated type float float value clamped to [ 0.0, 1.0 ] long short signed char unsigned char unsigned int unsigned short void

Equivalent OpenGL Type

GLbitfield

GLboolean

GLdouble

GLclampd

GLenum

GLfloat

GLclampf

GLint

GLshort

GLbyte

GLubyte

GLuint

GLushort

GLvoid

155

Appendix C: OpenGL Names, Types, and Error

Error Handling

When an error occurs, OpenGL sets an error flag to the appropriate error value. You can test error conditions using the glGetError() call, which returns the error number.

Table C-3 lists possible error values. For details, see the reference page for glGetError().

Table C-3 glGetError()

Return Values

Error

NO_ERROR

INVALID_ENUM

INVALID_VALUE

INVALID_OPERATION

STACK_OVERFLOW

STACK_UNDERFLOW

OUT_OF_MEMORY

Description Command Ignored?

No error

Enumerated argument out of range

Numeric argument out of range

Operation illegal in current state

No

Yes

Yes

Yes

Command would cause a stack overflow

Command would cause a stack underflow

Yes

Yes

Not enough memory left to execute command Unknown

156

Appendix D

D.

Example OpenGL Program With the GLUT Library

This program uses OpenGL and the GLUT library to display a planet rotating around the sun. It demonstrates how to composite modeling transformations to draw translated and rotated models. Pressing the left, right, up, and down arrow keys alters the rotation of the planet around the sun.

/*

* planet.c

* This program shows how to composite modeling transformations

* to draw translated and rotated models.

* Interaction: pressing the d and y keys (day and year)

* alters the rotation of the planet around the sun.

*/

#include <GL/glut.h>

#include <stdlib.h> static int year = 0, day = 0; void init(void)

{

glClearColor(0.0, 0.0, 0.0, 0.0);

glShadeModel(GL_FLAT);

} void display(void)

{

glClear(GL_COLOR_BUFFER_BIT);

glColor3f(1.0, 1.0, 1.0);

glPushMatrix();

glutWireSphere(1.0, 20, 16); /* draw sun */

glRotatef((GLfloat)year, 0.0, 1.0, 0.0);

glTranslatef(2.0, 0.0, 0.0);

glRotatef((GLfloat)day, 0.0, 1.0, 0.0);

glutWireSphere(0.2, 10, 8); /* draw smaller planet */

glPopMatrix();

glutSwapBuffers();

}

157

Appendix D: Example OpenGL Program With the GLUT Library void reshape(int w, int h)

{

glViewport(0, 0, (GLsizei) w, (GLsizei) h);

glMatrixMode(GL_PROJECTION);

glLoadIdentity();

gluPerspective(60.0, (GLfloat)w/(GLfloat)h, 1.0, 20.0);

glMatrixMode(GL_MODELVIEW);

glLoadIdentity();

gluLookAt(0.0, 0.0, 5.0, 0.0, 0.0, 0.0, 0.0, 1.0, 0.0);

}

/* ARGSUSED1 */ void keyboard (unsigned char key, int x, int y)

{

switch (key) {

case 'd':

day = (day + 10) % 360;

glutPostRedisplay();

break;

case 'D':

day = (day - 10) % 360;

glutPostRedisplay();

break;

case 'y':

year = (year + 5) % 360;

glutPostRedisplay();

break;

case 'Y':

year = (year - 5) % 360;

glutPostRedisplay();

break;

case 27:

exit(0);

break;

default:

break;

}

} int main(int argc, char **argv)

{

glutInit(&argc, argv);

glutInitDisplayMode(GLUT_DOUBLE|GLUT_RGB);

glutInitWindowSize(500, 500);

158

glutInitWindowPosition(100, 100);

glutCreateWindow(argv[0]);

init();

glutDisplayFunc(display);

glutReshapeFunc(reshape);

glutKeyboardFunc(keyboard);

glutMainLoop();

return 0;

}

159

Appendix E

E.

Example Program Using Xt and a WorkProc

This appendix contains an example program that uses Xt, IRIS IM, and the IRIS IM version of the Silicon Graphics widget. The program displays a planet with a moon, orbiting a sun, and uses a WorkProc for the animation.

/* opensolar.c

* opensolar displays a planet with a moon, orbiting a sun.

* To compile:

* cc -O -o opensolar opensolar.c -lXm -lGLw -lm -lGLU -lGL

*/

#include <Xm/Xm.h>

#include <Xm/Frame.h>

#include <Xm/Form.h>

#include <X11/keysym.h>

#include <X11/StringDefs.h>

#include <GL/GLwMDrawA.h>

#include <GL/gl.h>

#include <GL/glu.h>

#include <GL/glx.h>

#include <stdio.h>

#include <stdlib.h>

#include <math.h>

#include "malloc.h" typedef struct _spin {

short year;

} SPINDATA, *SPINPTR;

/* function prototypes */ void main(int argc, char **argv); void initCB (Widget w, XtPointer client_data,

XtPointer call_data); void exposeCB (Widget w, XtPointer spin,

XtPointer call_data); void resizeCB (Widget w, XtPointer spin,

XtPointer call_data);

161

Appendix E: Example Program Using Xt and a WorkProc void inputCB (Widget w, XtPointer client_data,

XtPointer call_data);

Boolean drawWP (XtPointer spin); void drawscene(SPINPTR spin); void setbeachball(int stripes); void beachball(unsigned long color1, unsigned long color2);

XtAppContext app_context;

XtWorkProcId workprocid = NULL;

GLXContext glx_context;

Display * global_display;

Window global_window;

/* main

* This program shows a solar system, with a sun, planet, and

* moon (in OpenGL). The user can exit with the ESCape key

* or through the window manager menu.

*/ void main(int argc, char **argv)

{

Arg wargs[15];

int n;

Widget glw, toplevel, frame, form;

SPINPTR spin;

static String fallback_resources[] = {

"*frame*shadowType: SHADOW_IN", "*glwidget*width: 750",

"*glwidget*height: 600", "*glwidget*rgba: TRUE",

"*glwidget*doublebuffer: TRUE",

"*glwidget*allocateBackground: TRUE", NULL

};

/* create main data structure, spin pointer */

spin = (SPINPTR) malloc (sizeof (SPINDATA));

spin->year = 0;

toplevel = XtAppInitialize(

&app_context, /* Application context */

"Opensolar", /* Application class */

NULL, 0, /* command line option list */

&argc, argv, /* command line args */

fallback_resources,

NULL, /* argument list */

0); /* number of arguments */

162

n = 0;

form = XmCreateForm(toplevel, "form", wargs, n);

XtManageChild(form);

n = 0;

XtSetArg(wargs[n], XtNx, 30);

n++;

XtSetArg(wargs[n], XtNy, 30);

n++;

XtSetArg(wargs[n], XmNbottomAttachment, XmATTACH_FORM);

n++;

XtSetArg(wargs[n], XmNleftAttachment, XmATTACH_FORM);

n++;

XtSetArg(wargs[n], XmNrightAttachment, XmATTACH_FORM);

n++;

XtSetArg(wargs[n], XmNtopAttachment, XmATTACH_FORM);

n++;

XtSetArg(wargs[n], XmNleftOffset, 30);

n++;

XtSetArg(wargs[n], XmNbottomOffset, 30);

n++;

XtSetArg(wargs[n], XmNrightOffset, 30);

n++;

XtSetArg(wargs[n], XmNtopOffset, 30);

n++;

frame = XmCreateFrame (form, "frame", wargs, n);

XtManageChild (frame);

n = 0;

glw = GLwCreateMDrawingArea(frame, "glwidget", wargs, n);

XtManageChild (glw);

XtAddCallback(glw, GLwNginitCallback, initCB,

(XtPointer) NULL);

XtAddCallback(glw, GLwNexposeCallback, exposeCB,

(XtPointer) spin);

XtAddCallback(glw, GLwNresizeCallback, resizeCB,

(XtPointer) spin);

XtAddCallback(glw, GLwNinputCallback, inputCB,

(XtPointer) NULL);

XtRealizeWidget(toplevel); /* instantiate it now */

XtAppMainLoop(app_context); /* loop for events */

} /* end main() */

163

Appendix E: Example Program Using Xt and a WorkProc

/* initCB

* The initCB subroutine initializes graphics modes and

* transformation matrices.

*/ void initCB (Widget w, XtPointer client_data,

XtPointer call_data)

{

Arg args[1];

XVisualInfo *vi;

XtSetArg(args[0], GLwNvisualInfo, &vi);

XtGetValues(w, args, 1);

global_display = XtDisplay(w);

global_window = XtWindow(w);

glx_context = glXCreateContext(global_display, vi, 0,

GL_FALSE);

} /* end initCB() */

/* exposeCB() and resizeCB() are called when the window

* is uncovered, moved, or resized.

*/ void exposeCB (Widget w, XtPointer ptr, XtPointer call_data)

{

SPINPTR spin;

static char firstTime = 0x1;

GLwDrawingAreaCallbackStruct *call_ptr;

call_ptr = (GLwDrawingAreaCallbackStruct *) call_data;

GLwDrawingAreaMakeCurrent(w, glx_context);

if (firstTime) {

glClearColor(0.0, 0.0, 0.0, 0.0);

glShadeModel (GL_FLAT);

glEnable(GL_DEPTH_TEST);

glMatrixMode(GL_PROJECTION);

glLoadIdentity ();

gluPerspective(45.0, (GLfloat)(call_ptr->width)

/(GLfloat)(call_ptr->height), 1.0, 25.0);

glMatrixMode(GL_MODELVIEW);

glLoadIdentity ();

glTranslatef(0.0, 0.0, -12.0);

workprocid = XtAppAddWorkProc(app_context, drawWP, ptr);

/* ptr is spin */

firstTime = 0;

164

}

spin = (SPINPTR) ptr;

drawscene(spin);

} void resizeCB (Widget w, XtPointer ptr, XtPointer call_data)

{

GLwDrawingAreaCallbackStruct *call_ptr;

SPINPTR spin;

spin = (SPINPTR) ptr;

call_ptr = (GLwDrawingAreaCallbackStruct *) call_data;

GLwDrawingAreaMakeCurrent(w, glx_context);

glViewport (0, 0, (GLsizei) (call_ptr->width-1),

(GLsizei) (call_ptr->height-1));

glMatrixMode(GL_PROJECTION);

glLoadIdentity ();

gluPerspective(45.0, (GLfloat)(call_ptr->width) /

(GLfloat)(call_ptr->height), 1.0, 25.0);

glMatrixMode(GL_MODELVIEW);

glLoadIdentity ();

glTranslatef(0.0, 0.0, -12.0);

drawscene(spin);

}

/* inputCB() handles all types of input from the GL widget.

* The KeyRelease handles the ESCape key, so that it exits

* the program.

*/ void inputCB (Widget w, XtPointer client_data,

XtPointer call_data)

{

char buffer[1];

KeySym keysym;

GLwDrawingAreaCallbackStruct *call_ptr;

XKeyEvent *kevent;

call_ptr = (GLwDrawingAreaCallbackStruct *) call_data;

kevent = (XKeyEvent *) (call_ptr->event);

switch(call_ptr->event->type) {

case KeyRelease:

/* Must convert the keycode to a keysym before

* checking if it is an escape

*/

165

Appendix E: Example Program Using Xt and a WorkProc

if (XLookupString(kevent,buffer,1,&keysym,NULL) == 1

&& keysym == (KeySym)XK_Escape)

exit(0);

break;

default:

break;

}

}

/* drawWP() is called by the WorkProc. When the scene

* is in automatic motion, the WorkProc calls this routine,

* which adds 1 degree (10 tenths) to the cumulative amount

* of rotation. drawscene() is called, so the image is

* redrawn. It returns(FALSE) so the WorkProc does not

* discontinue operation.

*/

Boolean drawWP (XtPointer ptr)

{

SPINPTR spin;

spin = (SPINPTR) ptr;

spin->year = (spin->year + 10) % 3600;

drawscene (spin);

return (FALSE);

}

/* drawscene

* drawscene calculates angles relative to the spin->year

* and then draws sun, planet, and moon.

*/ void drawscene(SPINPTR spin)

{

short sunangle;

/* actual dist is 1.5e8 km; mult by 3.0e-8 fudgefactor */

float earthdist = 4.5;

short dayangle;

float earthscale = 0.5;

short monthangle;

float moondist = 0.9;

float moonscale = 0.2;

glClear(GL_DEPTH_BUFFER_BIT|GL_COLOR_BUFFER_BIT);

glPushMatrix();

166

glRotatef(10.0, 1.0, 0.0, 0.0); /* tilt entire scene */

glPushMatrix();

sunangle = (spin->year*365/25) % 3600;

/* sun rotates on axis every 25 days */

glRotatef(.1*(sunangle), 0.0, 1.0, 0.0);

/* cpack format color1, color2 */

/* swapped by hand: was beachball(0x20C0FF, 0x200FFFF); */

beachball(0xFFC02000, 0xFFFF0020);

glPopMatrix();

glPushMatrix();

glRotatef(.1*(spin->year), 0.0, 1.0, 0.0);

glTranslatef(earthdist, 0.0, 0.0);

glPushMatrix();

dayangle = (spin->year*50) % 3600;

/* dayangle fudged so earth rotation can be seen */

glRotatef(.1*(dayangle), 0.0, 1.0, 0.0);

glScalef(earthscale, earthscale, earthscale);

glColor3f(0.0, 0.0, 1.0);

/* swap by hand; was beachball(0xFF0000, 0xC02000);*/

beachball(0x0000FF00, 0x0020C000); /* earth */

glPopMatrix();

monthangle = (spin->year*365/28) % 3600;

glRotatef(.1*(monthangle), 0.0, 1.0, 0.0);

glTranslatef(moondist, 0.0, 0.0);

glScalef(moonscale, moonscale, moonscale);

glColor3f(1.0, 1.0, 1.0);

/* swap by hand; was beachball(0xFFFFFF, 0xC0C0C0); */

beachball(0xFFFFFF00, 0xC0C0C000); /* moon */

glPopMatrix();

glPopMatrix();

glXSwapBuffers(global_display, global_window);

} /* end drawscene() */

/*

* BEACHBALL

*/

/* three dimensional vector */ typedef float vector[3]; vector front = { 0.0, 0.0, 1.0 }; vector back = { 0.0, 0.0, -1.0 }; vector top = { 0.0, 1.0, 0.0 }; vector bottom = { 0.0, -1.0, 0.0 }; vector right = { 1.0, 0.0, 0.0 };

167

Appendix E: Example Program Using Xt and a WorkProc vector left = { -1.0, 0.0, 0.0 }; vector center = { 0.0, 0.0, 0.0 };

/* Number of colored stripes. Should be even to look right */

#define BEACHBALL_STRIPES 12

/* Default number of polygons making up a stripe. Should */

/* be even */

#define BEACHBALL_POLYS 16

/* array of vertices making up a stripe */ vector stripe_point[BEACHBALL_POLYS + 3];

/* has the beachball been initialized */

Boolean beachball_initialized = FALSE;

/* Number of polygons making up a stripe */ int beachball_stripes;

/* Number of vertices making up a stripe */ int stripe_vertices;

/* Initializes beachball_point array to a stripe of unit */

/* radius. */ void setbeachball(int stripes)

{

int i,j;

float x,y,z; /* vertex points */

float theta,delta_theta; /* angle from top pole to bottom*/

float offset; /* offset from center of stripe to vertex */

/* radius of cross-section at current latitude */

float cross_radius;

float cross_theta; /* angle occupied by a stripe */

beachball_stripes = stripes;

/* polys distributed by even angles from top to bottom */

delta_theta = M_PI/((float)BEACHBALL_POLYS/2.0);

theta = delta_theta;

cross_theta = 2.0*M_PI/(float)beachball_stripes;

j = 0;

stripe_point[j][0] = top[0];

stripe_point[j][1] = top[1];

stripe_point[j][2] = top[2];

j++;

168

for (i = 0; i < BEACHBALL_POLYS; i += 2) {

cross_radius = fsin(theta);

offset = cross_radius * ftan(cross_theta/2.0);

stripe_point[j][0] = - offset;

stripe_point[j][1] = fcos(theta);

stripe_point[j][2] = cross_radius;

j++;

stripe_point[j][0] = offset;

stripe_point[j][1] = stripe_point[j-1][1];

stripe_point[j][2] = stripe_point[j-1][2];

j++;

theta += delta_theta;

} /* end for */

stripe_point[j][0] = bottom[0];

stripe_point[j][1] = bottom[1];

stripe_point[j][2] = bottom[2];

stripe_vertices = j + 1;

beachball_initialized = TRUE;

}

/* Draws a canonical beachball. The colors are cpack values

* when in RGBmode.

*/ void beachball(unsigned long c1, unsigned long c2)

{

float angle, delta_angle;

int i, j;

if (! beachball_initialized)

setbeachball(BEACHBALL_STRIPES);

angle = 0.0;

delta_angle = 360.0/(float)beachball_stripes;

for (i = 0; i < beachball_stripes; i++) {

if ( i%2 == 0)

glColor4ubv((GLubyte *)(&c1));

169

Appendix E: Example Program Using Xt and a WorkProc

else

glColor4ubv((GLubyte *)(&c2));

glPushMatrix();

glRotatef(angle, 0.0, 1.0, 0.0);

angle += delta_angle;

glBegin(GL_TRIANGLE_STRIP);

for (j = 0; j < stripe_vertices; j++)

glVertex3fv(stripe_point[j]);

glEnd();

glPopMatrix();

}

}

170

Appendix F

F.

Example Mixed-Model Programs With Xlib

This appendix contains two example mixed-model programs that use Xlib. Each example program is shown first in IRIS GL, then in OpenGL.

Example One: iobounce.c

iobounce.c is a simple interactive program that bounces a ball around a 2D surface. Users can use the mouse buttons to change the velocity of the ball. The IRIS GL version of the program is presented first, then the OpenGL version.

IRIS GL Version of iobounce.c

The IRIS GL version of iobounce.c is a “pure” IRIS GL program; it does not contain X calls.

/* iobounce.c:

* "pool" ball that "bounces" around a 2-d "surface".

* RIGHTMOUSE stops ball

* MIDDLEMOUSE increases y velocity

* LEFTMOUSE increases x velocity

*/

#include <stdio.h>

#include <gl/gl.h>

#include <gl/device.h> long xmaxscrn, ymaxscrn; /* maximum size of screen in x and y */

#define XMIN 100

#define YMIN 100

#define XMAX 900

#define YMAX 700 long xvelocity = 0, yvelocity = 0;

171

Appendix F: Example Mixed-Model Programs With Xlib main()

{

Device dev;

short val;

long sizex, sizey;

initialize();

while (TRUE) {

while (qtest()) {

dev = qread(&val);

switch (dev) {

case REDRAW: /* redraw window re: move/resize/push/pop */

reshapeviewport();

ortho2(XMIN - 0.5, XMAX + 0.5, YMIN - 0.5,

YMAX + 0.5);

drawball();

break;

case LEFTMOUSE: /* increase xvelocity */

if (xvelocity >= 0)

xvelocity++;

else

xvelocity--;

break;

case MIDDLEMOUSE: /* increase yvelocity */

if (yvelocity >= 0)

yvelocity++;

else

yvelocity--;

break;

case RIGHTMOUSE: /* stop ball */

xvelocity = yvelocity = 0;

break;

case ESCKEY:

gexit();

exit(0);

}

}

drawball();

}

} initialize() {

xmaxscrn = getgdesc(GD_XPMAX)-1;

172

Example One: iobounce.c

ymaxscrn = getgdesc(GD_YPMAX)-1;

prefposition(xmaxscrn/4,xmaxscrn*3/4,ymaxscrn/4,ymaxscrn*3/4);

winopen("iobounce");

winconstraints();

doublebuffer();

gconfig();

shademodel(FLAT);

ortho2(XMIN - 0.5, XMAX + 0.5, YMIN - 0.5, YMAX + 0.5);

qdevice(ESCKEY);

qdevice(LEFTMOUSE);

qdevice(MIDDLEMOUSE);

qdevice(RIGHTMOUSE);

} drawball() {

static xpos = 500,ypos = 500;

long radius = 10;

color(BLACK);

clear();

xpos += xvelocity;

ypos += yvelocity;

if (xpos > XMAX - radius ||

xpos < XMIN + radius) {

xpos -= xvelocity;

xvelocity = -xvelocity;

}

if (ypos > YMAX - radius ||

ypos < YMIN + radius) {

ypos -= yvelocity;

yvelocity = -yvelocity;

}

color(YELLOW);

circfi(xpos, ypos, radius);

swapbuffers();

}

173

Appendix F: Example Mixed-Model Programs With Xlib

OpenGL Version of iobounce.c

Thie example contains the OpenGL version of iobounce.c. Windowing and event handling are now controlled with Xlib, rather than IRIS GL calls.

/* iobounce.c:

*

* "pool ball" that "bounces" around a 2-d "surface".

* RIGHTMOUSE stops ball

* MIDDLEMOUSE increases y velocity

* LEFTMOUSE increases x velocity

*

* (ported from ~4Dgifts/example/grafix/iobounce.c)

*/

#include <GL/glx.h>

#include <GL/gl.h>

#include <GL/glu.h>

#include <stdio.h>

#include <stdlib.h>

#include <X11/keysym.h>

#include <X11/Xlib.h>

#include <X11/Xutil.h>

#define XMIN 100

#define YMIN 100

#define XMAX 900

#define YMAX 700

#define BLACK 0

#define YELLOW 3

#define LEFTMOUSE 3

#define MIDDLEMOUSE 2

#define RIGHTMOUSE 1

#define TRUE 1

#define FALSE 0 long xmaxscrn, ymaxscrn; /* maximum size of screen /*

/* in x and y */

Display *dpy; /* The X server connection */

Atom del_atom; /* WM_DELETE_WINDOW atom */

Window glwin; /* handle to the GL window */

174

Example One: iobounce.c

XEvent event; static void openwindow(char *); static void drawball(void); static void clean_exit(void); long xvelocity = 0, yvelocity = 0; main(int argc, char *argv[])

{

int myExpose, myConfigure,

myButtRelease, myKeyPress,

myButtonNumber; /* store which events occur */

long xsize, ysize;

myExpose = myConfigure = myButtRelease = myKeyPress =

myButtonNumber = FALSE;

openwindow(argv[0]);

while (TRUE) {

KeySym keysym;

char buf[4];

/* this "do while" loop does the ‘get events’ half of the */

/* "get events,process events" action of the infinite while. */

/* This is to ensure the event queue is always drained before */

/* the events that have come in are processed. */

while (XEventsQueued(dpy,QueuedAfterReading)) { /* end "do { } while"

* XEventsQueued(dpy,QueuedAfterReading)

* is like qtest()--it only tells you if

* there’re any events presently in the

* queue.it does not disturb the event

* queue’s contents in any way. */

XNextEvent(dpy, &event);

switch (event.type) {

/* "Expose" events are sort of like "REDRAW" in gl-speak in

* terms of when a window or a previously invisible part

* becomes visible */

case Expose: /* Exposures */

175

Appendix F: Example Mixed-Model Programs With Xlib

myExpose = TRUE;

break;

/* "ConfigNotify" events are like "REDRAW" in terms of changes to

* a window’s size or position.*/

case ConfigureNotify: /* Resize GL manually */

xsize = event.xconfigure.width;

ysize = event.xconfigure.height;

myConfigure = TRUE;

break;

/* Wait for "ButtonRelease" events so the queue doesn’t fill up

* the way it would if the user sits on ButtonPresss. */

case ButtonRelease:

if (event.xbutton.button == Button1) {

myButtonNumber = LEFTMOUSE;

myButtRelease = TRUE;

} else if (event.xbutton.button ==

Button2) {

myButtonNumber = MIDDLEMOUSE;

myButtRelease = TRUE;

} else if (event.xbutton.button ==

Button3) {

myButtonNumber = RIGHTMOUSE;

myButtRelease = TRUE;

} /* twirl the green sphere */

break;

/* "ClientMessage" is generated if the WM itself is dying

* and sends an exit signal to any running prog. */

case ClientMessage:

if (event.xclient.data.l[0] == del_atom)

clean_exit();

break;

/* "KeyPress" events are those that would be generated before

* whenever queueing up any KEYBD key via qdevice. */

case KeyPress:

/* save out which unmodified key (i.e. the key was not

* modified w/something like "Shift", "Ctrl", or "Alt")

* got pressed for use below. */

XLookupString((XKeyEvent *)&event, buf, 4, &keysym, 0);

myKeyPress = TRUE;

break;

176

Example One: iobounce.c

} /* end switch (event.type) */

}

/* On an "Expose" event, redraw the affected pop’d or

* de-iconized window

*/

if (myExpose) {

drawball(); /* draw the GL stuff */

myExpose = FALSE; /* reset flag--queue now empty */

}

/* On a "ConfigureNotify" event, the GL window has either

* been moved or resized. Respond accordingly and then

* redraw its contents.

*/

if (myConfigure) {

glViewport(0, 0, xsize, ysize);

glLoadIdentity();

gluOrtho2D(XMIN-0.5, XMAX+0.5, YMIN-0.5, YMAX+0.5);

drawball(); /* draw the GL stuff */

myConfigure = FALSE; /* reset flag--queue now

* empty */

}

/* On a "ButtonRelease" event, myButtonNumber stores which

* mouse button was pressed/released and then we update

* x/yvelocity accordingly

* /

if (myButtRelease) {

if (myButtonNumber == LEFTMOUSE) { /* increase

xvelocity */

if (xvelocity >= 0)

xvelocity += 3;

else

xvelocity -= 3;

} else if (myButtonNumber == MIDDLEMOUSE) {

/* increase yvelocity*/

if (yvelocity >= 0)

yvelocity += 3;

else

yvelocity -= 3;

} else if (myButtonNumber == RIGHTMOUSE) {

/* stop ball */

xvelocity = yvelocity = 0;

177

Appendix F: Example Mixed-Model Programs With Xlib

} else {

fprintf(stderr,"ERROR: %s thinks

mouse button # ");

fprintf(stderr,"%d was

pressed(?)\n",argv[0],myButtonNumber);

}

drawball();

myButtRelease = FALSE;

}

/* On a keypress of Esc key, exit program. */

if (myKeyPress) {

if (keysym == XK_Escape)

clean_exit();

}

drawball();

}

} static int attributeList[] = { GLX_DOUBLEBUFFER,

None };

GLUquadricObj *qobj; static Bool WaitForNotify(Display *d, XEvent *e, char *arg) {

return (e->type == MapNotify) && (e->xmap.window ==

(Window)arg);

} static void openwindow(char *progname) {

int scrnnum; /* X screen number */

int xorig, yorig; /* window (upper-left) origin */

XVisualInfo *vi;

GLXContext cx;

Colormap cmap;

XSizeHints Winhints;/* used to fix window size */

XSetWindowAttributes swa;

XColor colorstruct;

/* Connect to the X server and get screen info */

if ((dpy = XOpenDisplay(NULL)) == NULL) {

fprintf(stderr, "%s: cannot connect to X server %s\n",

progname, XDisplayName(NULL));

178

Example One: iobounce.c

exit(1);

}

scrnnum = DefaultScreen(dpy);

ymaxscrn = DisplayHeight(dpy, scrnnum);

xmaxscrn = DisplayWidth(dpy, scrnnum);

/* get an appropriate visual */

vi = glXChooseVisual(dpy, DefaultScreen(dpy),

attributeList);

if (vi == NULL) {

printf("Couldn’t get visual.\n");

exit(0);

}

/* create a GLX context */

cx = glXCreateContext(dpy, vi, None, GL_TRUE);

if (cx == NULL) {

printf("Couldn’t get context.\n");

exit(0);

}

/* create a colormap */

cmap = XCreateColormap(dpy, RootWindow(dpy, vi->screen),

vi->visual, AllocAll);

XSync(dpy, 0);

/* create a window */

swa.colormap = cmap;

swa.border_pixel = 0;

/* express interest in certain events */

swa.event_mask = StructureNotifyMask | KeyPressMask |

ButtonPressMask |

ButtonReleaseMask | ExposureMask;

glwin = XCreateWindow(dpy, RootWindow(dpy, vi->screen),

10, 10, 300, 300,

0, vi->depth, InputOutput,

vi->visual,

CWBorderPixel|CWColormap|CWEventMask, &swa);

XMapWindow(dpy, glwin);

XIfEvent(dpy, &event, WaitForNotify, (char*)glwin);

/* connect the context to the window */

179

Appendix F: Example Mixed-Model Programs With Xlib

glXMakeCurrent(dpy, glwin, cx);

/* express interest in WM killing this app */

if ((del_atom = XInternAtom(dpy, "WM_DELETE_WINDOW",

True)) != None)

XSetWMProtocols(dpy, glwin, &del_atom, 1);

colorstruct.pixel = BLACK;

colorstruct.red = 0;

colorstruct.green = 0;

colorstruct.blue = 0;

colorstruct.flags = DoRed | DoGreen | DoBlue;

XStoreColor(dpy, cmap, &colorstruct);

colorstruct.pixel = YELLOW;

colorstruct.red = 65535;

colorstruct.green = 65535;

colorstruct.blue = 0;

colorstruct.flags = DoRed | DoGreen | DoBlue;

XStoreColor(dpy, cmap, &colorstruct);

glLoadIdentity();

gluOrtho2D(XMIN - 0.5, XMAX + 0.5, YMIN - 0.5, YMAX + 0.5);

/* clear the buffer */

glClearIndex((GLfloat)BLACK);

qobj = gluNewQuadric();

gluQuadricDrawStyle(qobj,GLU_FILL);

glFlush();

} static void drawball(void) {

static int xpos = 500, ypos = 500;

GLdouble radius = 14.0;

glClear(GL_COLOR_BUFFER_BIT);

xpos += xvelocity;

ypos += yvelocity;

if (xpos > XMAX - radius || xpos < XMIN + radius) {

xpos -= xvelocity;

xvelocity = -xvelocity;

}

if (ypos > YMAX - radius || ypos < YMIN + radius) {

ypos -= yvelocity;

yvelocity = -yvelocity;

}

180

Example Two: zrgb.c

glIndexi(YELLOW);

glPushMatrix();

glTranslatef(xpos, ypos, 0.);

gluDisk( qobj, 0., radius, 10, 1);

glPopMatrix();

glXSwapBuffers(dpy, glwin);

}

/* clean_exit -- Clean up before exiting */ static void clean_exit(void)

{

gluDeleteQuadric(qobj);

XCloseDisplay(dpy);

exit(0);

}

Example Two: zrgb.c

The zrgb.c example program includes depth buffering. This program won’t work on 8-bit

IRIS workstations. The IRIS GL version is presented first.

IRIS GL Version of zrgb.c

This is the IRIS GL version of zrgb.c. Like iobounce.c, this is a pure IRIS GL program.

/* zrgb.c

*

* This program demostrates zbuffering 3 intersecting RGB

* polygons while in doublebuffer mode where,movement of the

* mouse with the LEFTMOUSE button depressed will, rotate the 3

* polygons. This is done via compound rotations allowing

* continuous screen-oriented rotations. (See orient(),

* and draw_scene() below). Notice the effective way there

* is no wasted CPU usage when the user moves the mouse out

* of the window without holding down LEFTMOUSE--there is no

* qtest being performed and so the program simply blocks on

* the qread statement. Press the "Esc"[ape] key to exit.

* Please note that this program will not work on any 8-bit

* IRIS machine.

* ratman - 1989

181

Appendix F: Example Mixed-Model Programs With Xlib

*/

#include <stdio.h>

#include <gl/gl.h>

#include <gl/device.h>

Matrix objmat = {

{1.0, 0.0, 0.0, 0.0},

{0.0, 1.0, 0.0, 0.0},

{0.0, 0.0, 1.0, 0.0},

{0.0, 0.0, 0.0, 1.0},

};

Matrix idmat = {

{1.0, 0.0, 0.0, 0.0},

{0.0, 1.0, 0.0, 0.0},

{0.0, 0.0, 1.0, 0.0},

{0.0, 0.0, 0.0, 1.0},

};

/* Modes the program can be in */

#define NOTHING 0

#define ORIENT 1 int mode = 0; int omx, mx, omy, my; /* old and new mouse position */ float scrnaspect; /* aspect ratio value */ long zfar; /* holds specific machine’s */

/* maximum Z depth value */ main(argc, argv) int argc; char *argv[];

{

long dev;

short val;

int redrawneeded=TRUE; /* Is true when the scene */

/* needs redrawing */

initialize(argv[0]);

while (TRUE) {

if (redrawneeded) {

draw_scene();

182

redrawneeded=FALSE;

}

while (qtest() || (!redrawneeded)) {

switch(dev=qread(&val)) {

case ESCKEY: /* exit when key is going up, */

/* not down */

if (val) /* this avoids the scenario */

/* where a window */

break; /* underneath this program’s */

/* window--say */

exit(0); /* another copy of this */

/* program--getting the */

/* ESC UP event and exiting */

/* also. */

case REDRAW:

reshapeviewport();

redrawneeded=TRUE;

break;

case LEFTMOUSE:

if (val) {

mode = ORIENT;

omx = mx;

omy = my;

} else

mode = NOTHING;

break;

case MOUSEX:

omx = mx;

mx = val;

if (mode == ORIENT) {

update_scene();

redrawneeded=TRUE;

}

break;

case MOUSEY:

omy = my;

my = val;

if (mode == ORIENT) {

update_scene();

Example Two: zrgb.c

183

Appendix F: Example Mixed-Model Programs With Xlib

redrawneeded=TRUE;

}

break;

}

}

}

} initialize(progname) char *progname;

{

long xscrnsize; /* size of screen in x used

* to set globals */

long testifZinst;

/*

* This program requires the following to run:

* -- z buffer

* -- ability to do double-buffered RGB mode

*/

/* Test for Z buffer */

testifZinst = getgdesc(GD_BITS_NORM_ZBUFFER);

if (testifZinst == FALSE) {

fprintf(stderr,"BUMmer!--%s won’t work on ",

progname);

fprintf(stderr,"this machine--zbuffer option not

installed.\n");

exit(0);

}

/* Test for double-buffered RGB */

if (getgdesc(GD_BITS_NORM_DBL_RED) == 0) {

fprintf(stderr,"BUMmer!--%s won’t work on ",

progname);

fprintf(stderr,"this machine--not enough

bitplanes.\n");

exit(0);

}

/* Code to keep same aspec ratio as the screen */

keepaspect(getgdesc(GD_XMMAX), getgdesc(GD_YMMAX));

scrnaspect =

(float)getgdesc(GD_XMMAX)/(float)getgdesc(GD_YMMAX);

184

winopen(progname);

wintitle("Zbuffered RGB #1");

doublebuffer();

RGBmode();

gconfig();

zbuffer(TRUE);

glcompat(GLC_ZRANGEMAP, 0);

zfar = getgdesc(GD_ZMAX);

qdevice(ESCKEY);

qdevice(LEFTMOUSE);

qdevice(MOUSEX);

qdevice(MOUSEY);

} update_scene() {

switch (mode) {

case ORIENT:

orient();

break;

}

} orient () {

pushmatrix();

loadmatrix(idmat);

rotate(mx-omx, ’y’);

rotate(omy-my, ’x’);

multmatrix(objmat);

getmatrix(objmat);

popmatrix();

} draw_scene() {

czclear(0x00C86428, zfar);

Example Two: zrgb.c

185

Appendix F: Example Mixed-Model Programs With Xlib

perspective(400, scrnaspect, 30.0, 60.0);

translate(0.0, 0.0, -40.0);

multmatrix(objmat);

rotate(-580, ’y’); /* skews original view

* to show all polygons */

draw_polys();

swapbuffers();

} float polygon1[3][3] = { {-10.0, -10.0, 0.0,},

{ 10.0, -10.0, 0.0,},

{-10.0, 10.0, 0.0,} }; float polygon2[3][3] = { { 0.0, -10.0, -10.0,},

{ 0.0, -10.0, 10.0,},

{ 0.0, 5.0, -10.0,} }; float polygon3[4][3] = { {-10.0, 6.0, 4.0,},

{-10.0, 3.0, 4.0,},

{ 4.0, -9.0, -10.0,},

{ 4.0, -6.0, -10.0,} }; draw_polys() {

bgnpolygon();

cpack(0x00000000);

v3f(&polygon1[0][0]);

cpack(0x007F7F7F);

v3f(&polygon1[1][0]);

cpack(0x00FFFFFF);

v3f(&polygon1[2][0]);

endpolygon();

bgnpolygon();

cpack(0x0000FFFF);

v3f(&polygon2[0][0]);

cpack(0x007FFF00);

v3f(&polygon2[1][0]);

cpack(0x00FF0000);

v3f(&polygon2[2][0]);

endpolygon();

bgnpolygon();

cpack(0x0000FFFF);

v3f(&polygon3[0][0]);

cpack(0x00FF00FF);

186

v3f(&polygon3[1][0]);

cpack(0x00FF0000);

v3f(&polygon3[2][0]);

cpack(0x00FF00FF);

v3f(&polygon3[3][0]);

endpolygon();

}

OpenGL Version of zrgb.c

This is the OpenGL version of zrgb.c.

/*

* zrgb.c

*/

#include <GL/glx.h>

/*

#include <GL/gl.h>

#include <GL/glu.h>

*/

#include <stdio.h>

#include <stdlib.h>

#include <X11/keysym.h>

#include <X11/Xlib.h>

#include <X11/Xutil.h>

#define TRUE 1

#define FALSE 0

Display *dpy; /* The X server connection */

Atom del_atom; /* WM_DELETE_WINDOW atom */

Window glwin; /* handle to the GL window */

XEvent event;

/* function declarations */ static void openwindow(char *); static void resize_buffer(void); static void clean_exit(void); void initGL(void); void orient(void); void drawScene(void); void drawPolys(void);

Example Two: zrgb.c

187

Appendix F: Example Mixed-Model Programs With Xlib static float objmat[16] = {

1.0, 0.0, 0.0, 0.0,

0.0, 1.0, 0.0, 0.0,

0.0, 0.0, 1.0, 0.0,

0.0, 0.0, 0.0, 1.0,

}; short ax, ay, az; /* angles for the "twirling" green

* sphere to ride on */ long xsize, ysize; /* current size-of-window keepers */ long zfar; /* used in czclear for the machine’s

* zbuffer max */ long buffermode; /* flag tracks current window

* (single or double) */ double scrnaspect; /* aspect ratio value */ int xpos, ypos, oxpos, oypos; /* old and new mouse position */ main(argc,argv) int argc; char **argv;

{

int myExpose, myConfigure, myButtPress, myKeyPress;

int needToDraw = 0; /* don’t set this to true until

* we get our first Expose event */

myExpose = myConfigure = myButtPress = myKeyPress = FALSE;

openwindow(argv[0]);

/* start out making the singlebuffer window be

* our current GL window */

initGL(); /* do GL init stuff */

/*

* The event loop.

*/

while (1) { /* standard logic: get event(s),

* process event(s) */

XEvent event;

KeySym keysym;

char buf[4];

188

/* this "do while" loop does the ‘get events’

* half of the "get events, process events" action

* of the infinite while. this is to ensure

* the event queue is always drained before the events

* that have come in are processed.

*/

do {

XNextEvent(dpy, &event);

switch (event.type) {

/* "Expose" events are sort of like "REDRAW" in

* gl-speak in terms of when a window becomes

* visible, or a previously

* invisible part becomes visible.

*/

case Expose: /* Exposures */

needToDraw = myExpose = TRUE;

break;

/* "ConfigNotify" events are like "REDRAW" in

* terms of changes to a window’s size or position.

*/

case ConfigureNotify: /* Resize GL manually */

xsize = event.xconfigure.width;

ysize = event.xconfigure.height;

needToDraw = myConfigure = TRUE;

break;

/* Wait for "MotionNotify" events so the

* queue doesn’t fill up

*/

case MotionNotify:

myButtPress = TRUE;

xpos = event.xmotion.x;

ypos = event.xmotion.y;

break;

/* "ClientMessage" is generated if the WM itself

* is being gunned down and sends an exit signal

* to any running prog.

*/

case ClientMessage:

if (event.xclient.data.l[0] == del_atom)

Example Two: zrgb.c

189

Appendix F: Example Mixed-Model Programs With Xlib

clean_exit();

break;

/* "KeyPress" events are those that would be

* generated before whenever queueing up any

KEYBD key via qdevice.

*/

case KeyPress:

/* save out which unmodified key (i.e. the

* key was not modified w/something like

* "Shift", "Ctrl", or "Alt") got pressed

* for use below.

*/

XLookupString((XKeyEvent *)&event, buf, 4,

&keysym, 0);

myKeyPress = TRUE;

break;

} /* end switch (event.type) */

} while (XPending(dpy)); /* end "do { } while".

* XPending() is like

* qtest()--it only

* tells you if there’re

* any events presently in

* the queue. it does not

* disturb queue’s contents

* in any way.

*/

/* On an "Expose" event, redraw the affected pop’d or

* de-iconized window

*/

if (myExpose) {

resize_buffer();

myExpose = FALSE; /* reset flag--queue now empty */

}

/* On a "ConfigureNotify" event, the GL window has either

* been moved or resized. Respond accordingly and then

* redraw its contents.

*/

if (myConfigure) {

oxpos = xpos;

190

oypos = ypos;

resize_buffer();

myConfigure = FALSE; /* reset flag--queue now

* empty */

}

if (needToDraw) {

drawScene();

needToDraw = FALSE;

}

/* On a keypress of Esc key, exit program.

*/

if (myKeyPress) {

if (keysym == XK_Escape)

clean_exit();

}

if (myButtPress) {

orient();

drawScene();

myButtPress = FALSE;

}

} /* end while(1) */

} /* end main */ static int attributeList[] = { GLX_RGBA,

GLX_DOUBLEBUFFER,

GLX_RED_SIZE, 1,

GLX_GREEN_SIZE, 1,

GLX_BLUE_SIZE, 1,

GLX_DEPTH_SIZE, 1,

None }; static int attributeList2[] = { GLX_RGBA,

GLX_RED_SIZE, 1,

GLX_GREEN_SIZE, 1,

GLX_BLUE_SIZE, 1,

GLX_DEPTH_SIZE, 1,

None }; static Bool WaitForNotify(Display *d, XEvent *e, char *arg) {

return (e->type == MapNotify) && (e->xmap.window ==

(Window)arg);

Example Two: zrgb.c

191

Appendix F: Example Mixed-Model Programs With Xlib

}

XSizeHints Winhints; /* used to fix window size */

/* openwindow - establish connection to X server, get screen info, specify the

* attributes we want the WM to try to provide, and create the GL window */ static void openwindow(char *progname) {

XVisualInfo *vi;

GLXContext cx;

Colormap cmap;

XSizeHints Winhints; /* used to fix window size*/

XSetWindowAttributes swa;

int scrnnum; /* X screen number */

int xorig, yorig; /* window (upper-left) origin */

long scrnheight;

/* define window initial size */

xorig = 50; yorig = 40;

xsize = 300; ysize = 240;

scrnaspect = xsize / (double) ysize;

/* Connect to the X server and get screen info */

if ((dpy = XOpenDisplay(NULL)) == NULL) {

fprintf(stderr, "%s: cannot connect to X server %s\n",

progname, XDisplayName(NULL));

exit(1);

}

scrnnum = DefaultScreen(dpy);

scrnheight = DisplayHeight(dpy, scrnnum);

/* get an appropriate visual */

vi = glXChooseVisual(dpy, DefaultScreen(dpy),

attributeList);

if (vi == NULL) {

fprintf(stderr, "Unable to obtain visual

Doublebuffered visual\n");

vi = glXChooseVisual(dpy, DefaultScreen(dpy),

attributeList2);

}

if (vi == NULL) {

printf("Unable to obtain Singlebuffered

VISUAL(????)\n");

exit(0);

192

Example Two: zrgb.c

}

/* create a GLX context */

cx = glXCreateContext(dpy, vi, None, GL_TRUE);

/* create a colormap */

cmap = XCreateColormap(dpy, RootWindow(dpy, vi->screen),

vi->visual, AllocNone);

/* create a window */

swa.colormap = cmap;

swa.border_pixel = 0;

swa.event_mask = StructureNotifyMask | ButtonPressMask |

ExposureMask |

Button1MotionMask |

KeyPressMask; /* express interest in

* events */;

glwin = XCreateWindow(dpy, RootWindow(dpy, vi->screen),

xorig, yorig, xsize, ysize,

0, vi->depth, InputOutput,

vi->visual,

CWBorderPixel|CWColormap|CWEventMask, &swa);

XMapWindow(dpy, glwin);

XIfEvent(dpy, &event, WaitForNotify, (char*)glwin);

/* connect the context to the window */

glXMakeCurrent(dpy, glwin, cx);

if (!(glwin)) {

fprintf(stderr,"%s: couldn’t create ‘parent’ X

window\n",progname);

exit(1);

}

/* define string that will show up in the window title bar

* (and icon) */

XStoreName(dpy, glwin, "z-buffered rgb program");

/* specify the values for the Window Size Hints we want to

* enforce: this window’s aspect ratio needs to stay at

* 1:1, constrain min and max window size, and specify the

* initial size of the window.

*/

Winhints.width = xsize; /* specify desired x/y size of

193

Appendix F: Example Mixed-Model Programs With Xlib

* window */

Winhints.height = ysize;

Winhints.min_width = xorig; /* define min and max */

Winhints.max_width = scrnheight-1; /* width and height */

Winhints.min_height = yorig;

Winhints.max_height = scrnheight-1;

Winhints.min_aspect.x = xsize; /* keep aspect to a xsize:ysize ratio */

Winhints.max_aspect.x = xsize;

Winhints.min_aspect.y = ysize;

Winhints.max_aspect.y = ysize;

/* set the corresponding flags */

Winhints.flags = USSize|PMaxSize|PMinSize|PAspect;

XSetNormalHints(dpy, glwin, &Winhints);

/* express interest in WM killing this app */

if ((del_atom = XInternAtom(dpy, "WM_DELETE_WINDOW",

True)) != None)

XSetWMProtocols(dpy, glwin, &del_atom, 1);

return ;

}

/* window has been moved or resized so update viewport & CTM stuff. */ static void resize_buffer() {

XSync(dpy, False); /* STILL NEED THIS????? */

/* Need before GL reshape */

scrnaspect = xsize / (double) ysize;

glViewport(0, 0, (short) (xsize-1), (short) (ysize-1));

}

/* clean up before exiting */ static void clean_exit(void)

{

XCloseDisplay(dpy);

exit(0);

}

/* setup all necessary GL initialzation parameters. */ void initGL()

{

glEnable(GL_DEPTH_TEST);

glClearColor(0.16, 0.39, 0.78, 0.0);

glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);

glLoadIdentity();

194

gluPerspective(400.0, scrnaspect, 30.0, 1000.0);

} void orient()

{

float dx, dy;

glPushMatrix();

dx = xpos-oxpos;

dy = oypos-ypos;

glLoadIdentity();

glRotatef((float) (0.03*(xpos-oxpos)), 1.0, 0.0, 0.0);

glRotatef((float) (0.03*(oypos-ypos)), 0.0, 1.0, 0.0);

glMultMatrixf(objmat);

glGetFloatv(GL_MODELVIEW_MATRIX, objmat);

glPopMatrix();

} void drawScene()

{

glClear(GL_COLOR_BUFFER_BIT | GL_DEPTH_BUFFER_BIT);

glPushMatrix();

glTranslatef(0.0, 0.0, -40.0);

glMultMatrixf(objmat);

glRotatef(-220.0, 0.0, 1.0, 0.0); /* skews orig view to

* show all polys */

drawPolys();

glPopMatrix();

glFlush ();

glXSwapBuffers(dpy, glwin);

} float polygon1[3][3] = { {-10.0, -10.0, 0.0,},

{ 10.0, -10.0, 0.0,},

{-10.0, 10.0, 0.0,} }; float polygon2[3][3] = { { 0.0, -10.0, -10.0,},

{ 0.0, -10.0, 10.0,},

{ 0.0, 5.0, -10.0,} }; float polygon3[4][3] = { {-10.0, 6.0, 4.0,},

{-10.0, 3.0, 4.0,},

{ 4.0, -9.0, -10.0,},

{ 4.0, -6.0, -10.0,} };

Example Two: zrgb.c

195

Appendix F: Example Mixed-Model Programs With Xlib void drawPolys()

{

glBegin(GL_POLYGON);

glColor4f(0.0, 0.0, 0.0, 0.0);

glVertex3fv(&polygon1[0][0]);

glColor4f(0.5, 0.5, 0.5, 0.0);

glVertex3fv(&polygon1[1][0]);

glColor4f(1.0, 1.0, 1.0, 0.0);

glVertex3fv(&polygon1[2][0]);

glEnd();

glBegin(GL_POLYGON);

glColor4f(1.0, 1.0, 0.0, 0.0);

glVertex3fv(&polygon2[0][0]);

glColor4f(0.0, 1.0, 0.5, 0.0);

glVertex3fv(&polygon2[1][0]);

glColor4f(0.0, 0.0, 1.0, 0.0);

glVertex3fv(&polygon2[2][0]);

glEnd();

glBegin(GL_POLYGON);

glColor4f(1.0, 1.0, 0.0, 0.0);

glVertex3fv(&polygon3[0][0]);

glColor4f(1.0, 0.0, 1.0, 0.0);

glVertex3fv(&polygon3[1][0]);

glColor4f(0.0, 0.0, 1.0, 0.0);

glVertex3fv(&polygon3[2][0]);

glColor4f(1.0, 0.0, 1.0, 0.0);

glVertex3fv(&polygon3[3][0]);

glEnd();

}

196

Index

A

AC_ACCUMULATE

,

62

AC_ADD

,

62

AC_CLEAR_ACCUMULATE

,

62

AC_MULT

,

62

AC_RETURN

,

62 acbuf()

,

62 acbuf() arguments

,

62 accumulation buffer

,

61 accumulation buffer operations

,

62 acsize()

,

62

AF_ALWAYS

,

60

AF_EQUAL

,

60

AF_GEQUAL

,

60

AF_GREATER

,

60

AF_LEQUAL

,

60

AF_LESS

,

60

AF_NEVER

,

60

AF_NOTEQUAL

,

60 afunction()

,

60 alpha component, lighting

,

68 alpha test functions

,

60

AMBIENT

,

70 angles

,

43 antialiasing

,

58, 60 blending

,

59 end correction

,

61 lines

,

36 points

,

36 arc()

,

42 arcf()

,

15, 42 arcs porting

,

42 using quadrics

,

32

Athena widget set

,

95, 96 attenuation

,

68 attribute groups

,

19

B

back, polygons

,

38 beautifier, cb

,

10 begin and end commands

,

33 bgnclosedline()

,

36 bgncurve()

,

53 bgn/end commands

,

33 bgnline()

,

36 bgnpoint()

,

35 bgnpolygon()

,

37 bgnqstrip()

,

37 bgnsurface()

,

54 bgntmesh()

,

42 bgntrim()

,

54 binds

,

67 blend factors

,

59 blendfunction()

,

59

197

Index blend functions

,

59 blending

,

59

C

c()

,

45 callbacks concave polygons

,

41 with quadric objects

,

32 callfunc()

,

64 callobj()

,

64 cb

,

10

C comments, and toogl

,

10 character strings

,

92 choosing visuals for blending

,

59 circ()

,

42 circf()

,

42 circles porting

,

42 using quadrics

,

32 clear()

,

12 clipplane()

,

30 closeobj()

,

64 cmov()

,

47 color

,

44 color()

,

44 color constants

,

12, 44

COLORINDEXES

,

70 color maps

,

44, 92 mixed model

,

90 simulating RGB with

,

92

Xlib

,

105 comments,toogl

,

9 comparing files

,

9 comparison functions stencil

,

63

198

concave polygons

,

37, 41 cones using quadrics

,

32 conversion tool, see toogl coordinates, texture

,

74 cpack()

,

44 crv()

,

52 crvn()

,

52 current graphics position

,

22 current matrix mode

,

26 curvebasis()

,

52 curveit()

,

52 curveprecision()

,

52 curves

,

52 trimming

,

54 types (NURBS)

,

53 cylinders using quadrics

,

32 czclear()

,

24

D

defbasis()

,

52 defined color constants

,

12, 44 deflinestyle()

,

36, 67 defpattern()

,

39, 67 defs

,

67 delobj()

,

64 deltag()

,

64 depthcue()

,

48 depth cueing

,

48 destination alpha bits

,

59 device calls toogl

,

11 differences, OpenGL and IRIS GL

,

1

DIFFUSE

,

70

diffuse lighting components

,

68 direct rendering

,

15 disks using quadrics

,

32 display lists

,

63 editing

,

65 example

,

66 for X bitmap fonts

,

92 performance of

,

15 display mode

,

92 dither()

,

46 dithering

,

46 documentation

,

102

IRIS IM

,

xiv, 102

Motif

,

xiv, 102

X

,

xiv, 102 double-matrix mode

,

24 draw()

,

22 drawing commands

,

31 drawing single points

,

35

E

editing display lists

,

65 editing toogl output

,

10 editobj()

,

64

EMISSION

,

70 endclosedline()

,

36 end commands

,

33 end correction

,

61 endcurve()

,

53 endfeedback()

,

80 endpick()

,

79 endpoint()

,

35 endpolygon()

,

37 endqstrip()

,

37 endselect()

,

79 endsurface()

,

54 endtmesh()

,

42 endtrim()

,

54 event calls and toogl

,

11 event handling mixed model

,

90

Xlib

,

106 extensions video source

,

87 extensions to OpenGL

,

87

F

feedback()

,

80 flat shading

,

46 fog

,

48 fog modes

,

50 fogvertex()

,

48 fonts mixed model

,

90 porting

,

92 front, polygons

,

38 function flags,stencil

,

63 functions alpha testing

,

60 functions, blending

,

59

G

gdiff

,

9 genobj()

,

64 gentag()

,

64 getcmmode()

,

45 getcolor()

,

45

Index

199

Index get commands

,

13, 20 getdcm()

,

48 getgpos()

,

22 getlsbackup()

,

37 getlsrepeat()

,

36 getlstyle()

,

36 getlwidth()

,

36 getmap()

,

45 getmatrix()

,

29 getmcolor()

,

45 getmmode()

,

29 getpattern()

,

39 getresetls()

,

37 getscrbox()

,

30 getscrmask()

,

31 getsm()

,

46 getviewport()

,

30 getwritemask()

,

45

GL_ACCUM

,

62

GL_ADD

,

62

GL_ALWAYS

,

60

GL_AMBIENT

,

70

GL_AMBIENT_AND_ DIFFUSE

,

70

GL_BLEND

,

75

GL_COLOR_INDEXES

,

70

GL_CONSTANT_

,

71

GL_CONSTANT_ATTENUATION

,

71

GL_DECAL

,

75

GL_DIFFUSE

,

70

GL_DONT_CARE

,

61

GL_EMISSION

,

70

GL_EQUAL

,

60

GL_EYE_LINEAR

,

78

GL_EYE_PLANE

,

78

GL_FASTEST

,

49, 61

200

GL_GEQUAL

,

60

GL_GREATER

,

60

GL_LEQUAL

,

60

GL_LESS

,

60

GL_LIGHT_MODEL_ AMBIENT

,

70

GL_LIGHT_MODEL_ LOCAL_VIEWER

,

70

GL_LIGHT_MODEL_ TWO_SIDE

,

70

GL_LINEAR

,

77

GL_LINEAR_ATTENUATION

,

71

GL_LINEAR_MIPMAP_LINEAR

,

77

GL_LINEAR_MIPMAP_NEAREST

,

77

GL_LOAD

,

62

GL_MATRIX_MODE

,

29

GL_MODELVIEW

,

28

GL_MODELVIEW_MATRIX

,

29

GL_MODULATE

,

75

GL_MULT

,

62

GL_NEAREST

,

77

GL_NEAREST_MIPMAP_LINEAR

,

77

GL_NEAREST_MIPMAP_NEAREST

,

77

GL_NEVER

,

60

GL_NICEST

,

49, 61

GL_NOTEQUAL

,

60

GL_OBJECT_LINEAR

,

78

GL_OBJECT_PLANE

,

78

GL_POSITION

,

71

GL_PROJECTION

,

28

GL_PROJECTION_MATRIX

,

29

GL_Q

,

78

GL_QUADRATIC_ATTENUATION

,

71

GL_R

,

78

GL_RETURN

,

62

GL_S

,

78

GL_SHININESS

,

70

GL_SPECULAR

,

70

GL_SPHERE_MAP

,

78

GL_SPOT_CUTOFF

,

71

GL_SPOT_DIRECTION

,

71

GL_SPOT_EXPONENT

,

71

GL_T

,

78

GL_TEXTURE

,

28

GL_TEXTURE_BORDER_COLOR

,

77

GL_TEXTURE_ENV_COLOR

,

75

GL_TEXTURE_MAG_FILTER

,

77

GL_TEXTURE_MATRIX

,

29

GL_TEXTURE_MIN_FILTER

,

77

GL_TEXTURE_WRAP_S

,

77

GL_TEXTURE_WRAP_T

,

77 glAccum()

,

62 glBegin()

,

33, 35 lines

,

36 polygons

,

37 glBegin/glEnd valid commands

,

35 glBlendFunc()

,

59 glCallList()

,

64 glCallLists()

,

64 fonts

,

93 glClear()

,

24 accumulation buffer

,

62 stencil planes

,

63 glClearAccum()

,

24, 62 glClearDepth()

,

24 glClearStencil()

,

24, 63 glClipPlane()

,

30 glColor()

,

44 glColorMask()

,

45 glColorMaterial()

,

69 glCopyPixels()

,

47 glDeleteLists()

,

64 glDepthMask()

,

45 glDisable() antialiasing

,

61 dithering

,

46 fog

,

48 polygon stippling

,

39 textures

,

73 glDrawPixels()

,

47 glEdgeFlag()

,

38 glEnable()

,

36 antialiasing

,

60 blending

,

59 dithering

,

46 fog

,

48 lighting

,

69 logicop

,

47

NURBS

,

52 polygon stippling

,

39 stencil planes

,

63 textures

,

73 glEnd()

,

33 and porting lines

,

35 lines

,

36 polygons

,

37 porting

,

33 glEndList()

,

64 glFeedbackBuffer()

,

80 glFog() arguments

,

49 porting

,

48 glFrustum()

,

27 glGenLists()

,

64 glGet*()

,

20 color index

,

45 color mask

,

45 line width

,

36

RGB color values

,

45 shade model

,

46 glGetClipPlane()

,

30 glGetLight()

,

69

Index

201

Index glGetMaterial()

,

69 glGetPolygonStipple()

,

39 glGetTexParameter()

,

74 glHint() and antialiasing

,

61 glIndex()

,

44 glIndexMask()

,

45 glInitNames()

,

79 glIsList()

,

64 glLight()

,

69 glLightModel()

,

69 glLineStipple()

,

36 glLineWidth()

,

36 glListBase()

,

64 fonts

,

93 glLoadIdentity()

,

26 glLoadMatrixd()

,

26 glLoadMatrixf()

,

26 glLoadName()

,

79 glLogicOp()

,

47 glMap1()

,

53 glMaterial()

,

69 glMaterial() parameters

,

70 glMatrixMode()

,

26 glMultMatrix()

,

24 glMultMatrixd()

,

27 glMultMatrixf()

,

27 glNewList()

,

64 glOrtho()

,

27 glPassThrough()

,

80 glPixelStore()

,

39, 47 glPixelTransfer()

,

47 glPixelZoom()

,

47 glPointSize()

,

36 glPolygonMode()

,

38 glPolygonStipple()

,

39

202

glPopAttrib()

,

19 glPopMatrix()

,

27 glPopName()

,

79 glPushAttrib()

,

19 glPushMatrix()

,

27 glPushName()

,

79 glRasterPos()

,

47 glReadBuffer()

,

47 glReadPixels()

,

47 glRect()

,

38 glRenderMode() feedback

,

80 picking

,

79 select

,

79 glRotate()

,

24 glRotated()

,

27 glRotatef()

,

27 glScaled()

,

27 glScalef()

,

27 glScissor()

,

31 glSelectBuffer()

,

79 glShadeModel()

,

46 glStencilFunc()

,

63 glStencilMask()

,

63 glStencilOp()

,

63 glTexCoord()

,

74 glTexEnv()

,

74 glTexGen()

,

74, 78 glTexImage1D()

,

74 glTexImage2D()

,

74 glTexParameter()

,

74 glTranslated()

,

27 glTranslatef()

,

27 gluBeginCurve()

,

53 gluBeginPolygon()

,

41 gluBeginSurface()

,

54

gluBeginTrim()

,

54 gluBuild1DMipmaps()

,

74 gluBuild2DMipmaps()

,

73, 74 gluCylinder()

,

32 gluDeleteNurbsRenderer()

,

52 gluDeleteQuadric()

,

32, 44 gluDeleteTess()

,

41 gluDisk()

,

32, 42 gluEndCurve()

,

53 gluEndPolygon()

,

41 gluEndSurface()

,

54 gluEndTrim()

,

54 gluLookAt()

,

26 gluNewNurbsRenderer()

,

52 gluNewQuadric()

,

32, 44 gluNewTess()

,

41 gluNextContour()

,

41 gluNurbsCallback()

,

52 gluNurbsCurve()

,

53, 54 gluNurbsSurface()

,

54 gluOrtho2D()

,

27 gluPartialDisk()

,

32, 42 gluPerspective()

,

27 gluPickMatrix()

,

27, 79 gluProject()

,

27 gluPwlCurve()

,

54 gluQuadricCallback()

,

32 gluQuadricDrawstyle()

,

32 gluQuadricNormals()

,

32 gluQuadricOrientation()

,

32

GLU quadrics routines

,

31 gluQuadricTexture()

,

32 gluScaleImage()

,

74 gluSphere()

,

32, 43, 44 gluTessCallback()

,

41 gluTessVertex()

,

41 gluUnProject()

,

27 glVertex()

,

33 glViewport()

,

30

GLwDraw

,

91, 94

GLwMDraw

,

91, 94 glXChooseVisual()

,

103 accumulation buffer

,

62

GLX commands

,

103 glXCreateContext()

,

97, 103

GlxCreateMDraw

,

96

GlxDraw,IRIS IM version

,

96

GlxDrawingAreaMakeCurrent()

,

102 glXMakeCurrent()

,

103

GlxMDraw

,

96

GlxNinputCallback

,

102

GLX routines

,

91 glXUseXFont()

,

92 gouraud shading

,

46 graphics position, current

,

22 greset()

,

19 gRGBcolor()

,

45 gRGBmask()

,

45 groups, state attribute

,

19

H

header files

,

18 hint modes, fog

,

50 how to port

,

4

I

image scaling

,

74 include files

,

18

Index

203

Index initnames()

,

79 installing color maps

,

92

IRIS IM

,

91, 94, 95 traversal

,

96

IRIS IM documentation

,

xiv, 102 isobj()

,

64 istag()

,

64

L

LCOLOR

,

71 lighting

,

68 display lists

,

68 two-sided

,

71 light models

,

68 linear fog

,

48 lines drawing

,

36 quadric routines

,

32 stipples

,

36 linesmooth()

,

36, 60 linewidth()

,

36 lmbind()

,

67, 68 lmcolor()

,

69 lmdef()

,

67, 68 loadmatrix()

,

26 loadname()

,

79 logical pixel operations

,

46 logicop()

,

47 lookat()

,

26 lrectread()

,

47 lrectwrite()

,

47 lRGBrange()

,

48 lsbackup()

,

37 lshaderange()

,

48 lsrepeat()

,

36

204

M

makeobj()

,

64 maketag()

,

64 mapcolor()

,

45 mapw()

,

27 mapw2()

,

27 material parameters

,

70 materials display lists

,

68 porting overview

,

68 matrices

,

24 matrix modes

,

27 mipmaps

,

73 mixed-model programming

,

90, 96

Athena widget set

,

96

GlxDraw (IRIS IM version)

,

96

GlxMdraw

,

96 installing colormaps

,

92

IRIS IM

,

95, 96

GlxMDraw

,

96 traversal

,

96 without IRIS IM

,

96

Xlib

,

91, 103

Xt

,

95 mmode()

,

26 modelview matrix

,

27 modes, fog

,

50

Motif documentation

,

xiv, 102 move()

,

22

MPROJECTION

,

28

MTEXTURE

,

28 multimap()

,

45 multiplying matrices

,

25 multmatrix()

,

24, 27

MVIEWING

,

28

Index

N

normals and GLU quadrics

,

32

NURBS curve types

,

53 objects

,

52 surfaces

,

54 surface types

,

54 trimming

,

54 nurbscurve()

,

53, 54 nurbssurface()

,

54

O

objdelete()

,

64 objinsert()

,

64 objreplace()

,

64 onemap()

,

45

OpenGL extensions

,

87

OpenGL widget

,

96 ortho()

,

27 ortho2()

,

27

P

parentheses, and toogl

,

12 pass/fail operations for stencil planes

,

63 passthrough()

,

80 patch()

,

52 patchbasis()

,

52 patchcurves()

,

52 patchprecision()

,

52 pclos()

,

22, 37 pdr()

,

22, 37 performance

,

14 perspective()

,

27 pick()

,

79 picking

,

79 picksize()

,

27, 79 pixel operations

,

46 pixmode()

,

47 pmv()

,

22, 37 pnt()

,

35 pntsize()

,

36 pntsmooth()

,

36, 60 points antialiasing

,

36 drawing single points

,

35 quadric routines

,

32 set point size

,

36 vertices as points

,

36 pol()

,

37 polarview()

,

26 poly()

,

37 polygons

,

37 arcs, circles

,

42 back/front

,

38 concave

,

41 modes

,

37, 38 quadric routines

,

32 stipples

,

39 tessellated

,

41 triangles

,

41 polymode()

,

38 polynomial curve

,

53, 54 polysmooth()

,

60 popmatrix()

,

27 popname()

,

79 popviewport()

,

30 porting, how to

,

4 porting tools

,

3

POSITION

,

71 projection matrix

,

27

205

Index pushmatrix()

,

27 pushname()

,

79 pushviewport()

,

30 pwlcurve()

,

54

Q

qread()

,

90 quadrics routines

,

31 quadrilaterals

,

37 quotes, and toogl

,

12

R

rational curves

,

53, 54 rcrv()

,

52 rcrvn()

,

52 rdr()

,

22 readRGB()

,

47 readsource()

,

47

RealityEngine graphics

,

83-87 rect()

,

38 rectangles, drawing

,

38 rectcopy()

,

47 rectf()

,

38 rectread()

,

47 rectwrite()

,

47 rectzoom()

,

47 rendering, direct

,

15 repeat factor for lines

,

36 resetls()

,

37 reshapeviewport()

,

30

RGB, simulating with color map

,

92

RGBcolor()

,

45

RGBwritemask()

,

45

206

rot()

,

27 rotate()

,

24, 27 rotations

,

24 rpatch()

,

52 rpdr()

,

37 rpmv()

,

22, 37

S

sbox()

,

38 sboxf()

,

38 scale()

,

27 scaling images

,

74 sclear()

,

24, 63 scrbox()

,

30 scrmask()

,

31 select()

,

79 setlinestyle()

,

36, 67 setmap()

,

45 setpattern()

,

39, 67 sets

,

67 setting matrix mode

,

26

SGIX_video_source

,

87 shademodel()

,

46 shading

,

44, 46

SHININESS

,

70 single-matrix mode

,

24 single points

,

35 slices, spheres

,

43 smoothline()

,

36 smooth shading

,

46 spclos()

,

37

SPECULAR

,

70 specular lighting components

,

68 sphdraw()

,

43, 44

Index spheres

,

43 slices, stacks

,

43 sphere library

,

31 using quadrics

,

32 sphfree()

,

44 sphgnpolys()

,

44 sphmode()

,

44 sphobj()

,

44 sphrotmatrix()

,

44 splf()

,

37

SPOTDIRECTION

,

71

SPOTLIGHT

,

71 stacks, spheres

,

43 state attribute groups

,

19 state variables, saving/restoring

,

19 stencil()

,

63 stencil function flags

,

63 stencil planes

,

63 stensize()

,

63 steps to porting

,

4 stippled polygons

,

39 stored definitions

,

67 strings

,

92 subpixel mode

,

58 surfaces

NURBS

,

54 porting

,

52 surface types, NURBS

,

54 swaptmesh()

,

42 swritemask()

,

63

T

t2()

,

74 tables

,

67 tessellated polygons

,

37, 41 test functions, alpha

,

60 tevbind()

,

67, 74 tevdef()

,

67, 74, 75 texbind()

,

67, 74 texdef()

,

67, 76 texdef2d()

,

74 texgen()

,

74, 78 text handling

,

92 textures

,

73 with quadrics

,

32

TG_CONTOUR

,

78

TG_LINEAR

,

78

TG_SPHEREMAP

,

78 toogl and spaces, tabs

,

10 calling

,

7

C comments and

,

10 comments

,

9 device calls

,

11 editing output

,

10 event calls

,

11 options

,

8 parentheses and quotes

,

12 processing entire directory

,

9 tips

,

10 windowing calls

,

11 tools for porting

,

3 transformations

,

24 translate()

,

27 traversal

,

96 triangle fans

,

41 triangles

,

41 triangle strips

,

41 trimming curves

,

54

TV_ALPHA

,

75

TV_BLEND

,

75

TV_COLOR

,

75

207

Index

TV_COMPONENT_SELECT

,

75

TV_DECAL

,

75

TV_MODULATE

,

75 two-sided lighting

,

71

TX_BILINEAR

,

77

TX_MAGFILTER

,

77

TX_MINFILTER

,

77

TX_MIPMAP_BILINEAR

,

77

TX_MIPMAP_LINEAR

,

77

TX_MIPMAP_POINT

,

77

TX_POINT

,

77

TX_Q

,

78

TX_R

,

78

TX_S

,

78

TX_T

,

78

TX_TRILINEAR

,

77

TX_WRAP

,

77

TX_WRAP_S

,

77

TX_WRAP_T

,

77

U

User Interface Language

,

94

V

v()

,

33 vertices

,

33 video source extension

,

87 viewport()

,

30 visuals for blending

,

59 for stencil planes

,

63

208

W

widget sets

,

91, 94 window()

,

27 windows depth

,

92 toogl windowing calls

,

11

Xlib

,

104 winopen()

,

90 wmpack()

,

45

WorkProc

,

102 writemask()

,

45 writemasks

,

44

X

X bitmap fonts

,

92

XCreateWindow()

,

103

X documentation

,

xiv, 102

X functions

XSetWMColormapWindows()

,

92

Xlib

,

91, 103 color maps

,

105 event handling

,

106 windows

,

104

XmForm widget

,

102

XOpenDisplay()

,

103

XSetWMColormapWindows()

,

92

XStoreColor()

,

45

Xt

,

91, 94, 95 mixed model programming

,

96

X Toolkit Intrinsics See Xt $nopage$

,

95

Z

zclear()

,

24 zwritemask()

,

45

Tell Us About This Manual

As a user of Silicon Graphics products, you can help us to better understand your needs and to improve the quality of our documentation.

Any information that you provide will be useful. Here is a list of suggested topics:

• General impression of the document

• Omission of material that you expected to find

• Technical errors

• Relevance of the material to the job you had to do

• Quality of the printing and binding

Please send the title and part number of the document with your comments. The part number for this document is 007-1797-030.

Thank you!

Three Ways to Reach Us

• To send your comments by electronic mail, use either of these addresses:

– On the Internet: [email protected]

– For UUCP mail (through any backbone site): [your_site]!sgi!techpubs

• To fax your comments (or annotated copies of manual pages), use this fax number: 650-932-0801

• To send your comments by traditional mail, use this address:

Technical Publications

Silicon Graphics, Inc.

2011 North Shoreline Boulevard, M/S 535

Mountain View, California 94043-1389

Was this manual useful for you? yes no
Thank you for your participation!

* Your assessment is very important for improving the work of artificial intelligence, which forms the content of this project

Download PDF

advertisement