Figure 4-0

Display 4-0

SwatDisplay 4-0

Table 4-0
4GenDisplay / GenPrimary

Applications communicate with users through a "user interface." The system 
needs a way of grouping the user-interface components together. For this 
reason, most applications will have a GenPrimary object. This object serves 
as the top-level object in the user interface tree. 

GenPrimaryClass is a subclass of GenDisplayClass. The GenDisplay 
object, like the GenPrimary object, manages other pieces of the user interface 
(menus, triggers, text objects, etc.). Furthermore, the GenDisplay object is a 
great boon to applications that need to perform several tasks at once (as, for 
example, a word processor which can have several files open at once). An 
application can have several GenDisplay objects, all of them children of a 
GenDisplayGroup object. Collectively, displays and primaries are called 
windows. All windows have certain functionality in common; that 
functionality can vary according to the specific UI.

The Document Control objects can be set to create GenDisplay objects when 
files are opened and to attach them automatically to a GenDisplayGroup. 
This enormously simplifies managing multiple documents. See 
"GenDocument," Chapter 13, for information on the Document Control 
objects.

These objects are very simple to use. In particular, the GenPrimary is very 
easy to declare and use. Although all applications use the GenPrimary, many 
will not need the GenDisplay. However, because GenPrimaryClass is a 
subclass of GenDisplayClass, this chapter begins with an overview of 
GenDisplayClass, then continues with a full discussion of 
GenPrimaryClass, and concludes with advanced information about 
GenDisplayClass. Before reading this chapter, you should be familiar with 
the use and creation of generic user interface objects. 

	4.1	A First Look at GenDisplay

Not all applications will need to use GenDisplay objects. However, almost all 
applications will have a GenPrimary object. Since GenPrimaryClass is a 
subclass of GenDisplayClass, programmers should be acquainted with 
GenDisplayClass. 


This section describes the data fields of GenDisplayClass and certain 
useful messages. It does not have all the information you will need to create 
these objects. If you will be using GenDisplay objects in your application, you 
will have to read section 4.3 on page 344.

	4.1.1	GenDisplay Object Structure

The GenDisplay object is a subclass of GenClass and therefore inherits all 
the data fields and attributes of that class. It has few data fields that are set 
by the application; these fields are listed in Code Display 4-1.

Code Display 4-1 Instance Data of GenDisplayClass

/* There are only two instance fields specifically defined for GenDisplayClass.
 * Also, an instance field for GenClass, GI_attrs, has different defaults in
 * GenDisplayClass. */

/* GDI_attributes is a one-byte field for attributes flags. There is only one flag
 * defined for this field, namely GDA_USER_DISMISSABLE, which is on by default. */
    @instance GenDisplayAttrs				GDI_attributes = GDA_USER_DISMISSABLE;

/* The GenDisplay object has a datum for a pointer to a document object. If a
 * Document Control is used to create display objects, it will associate each
 * display with a document object; each will have an optr to the other. */
    @instance optr				GDI_document;

/* The default setting of GI_attrs is different in GenDisplayClass than it is in 
 * GenClass: */
    @default GI_attrs = 			(@default 
			 | GA_TARGETABLE
			 | GA_KBD_SEARCH_PATH);

/* The following hints specify whether the display should be minimized or
 * maximized when it is built, and its appearance when minimized. */
    @vardata void HINT_DISPLAY_MINIMIZED_ON_STARTUP;
    @vardata void HINT_DISPLAY_NOT_MINIMIZED_ON_STARTUP;
    @vardata void HINT_DISPLAY_MAXIMIZED_ON_STARTUP;
    @vardata void HINT_DISPLAY_NOT_MAXIMIZED_ON_STARTUP;
    @vardata void HINT_DISPLAY_USE_APPLICATION_MONIKER_WHEN_MINIMIZED;

/* The following hints and attributes indicate whether the user should be able to
 * minimize, maximize, or resize the window. */
    @vardata void ATTR_GEN_DISPLAY_NOT_MINIMIZABLE;
    @vardata void ATTR_GEN_DISPLAY_NOT_MAXIMIZABLE;
    @vardata void HINT_DISPLAY_NOT_RESIZABLE;

/* ATTR_GEN_DISPLAY_NOT_RESTORABLE indicates that the user should not be able to
 * de-maximize the display once it is maximized. */
    @vardata void ATTR_GEN_DISPLAY_NOT_RESTORABLE;

/* ATTR_GEN_DISPLAY_TRAVELING_OBJECTS is the ChunkHandle of a list of "traveling
 * objects;" these objects are made the children of whichever GenDisplay is on top
 * in a given display region (see section 4.3.3.4 on page 355).*/
    @vardata ChunkHandle ATTR_GEN_DISPLAY_TRAVELING_OBJECTS;

/* The following hints and attributes specify whether the display's menu bar 
 * appears and whether it appears as a "popped out" floating menu. */
    @vardata void HINT_DISPLAY_MENU_BAR_HIDDEN_ON_STARTUP;
    @vardata void TEMP_GEN_DISPLAY_MENU_BAR_HIDDEN;
    @vardata void ATTR_GEN_DISPLAY_MENU_BAR_POPPED_OUT;
    @vardata void HINT_DISPLAY_USE_APPLICATION_MONIKER_WHEN_MENU_BAR_POPPED_OUT;

/* The GenDisplay uses the following vardata fields to store its
 * minimized/maximized state across a shutdown. You should not access these
 * fields. If you want to find out if a GenDisplay is minimized or maximized, send
 * it MSG_GEN_DISPLAY_GET_MINIMIZED or MSG_GEN_DISPLAY_GET_MAXIMIZED. */
    @vardata		void ATTR_GEN_DISPLAY_MINIMIZED_STATE;
    @vardata		void ATTR_GEN_DISPLAY_MAXIMIZED_STATE;

/* HINT_DISPLAY_DEFAULT_ACTION_IS_NAVIGATE_TO_NEXT_FIELD specifies the default 
 * action for the GenDisplay. */
    @vardata void HINT_DISPLAY_DEFAULT_ACTION_IS_NAVIGATE_TO_NEXT_FIELD;



	4.1.1.1	The GDI_attributes Field

MSG_GEN_DISPLAY_GET_ATTRS, MSG_GEN_DISPLAY_SET_ATTRS

The GenDisplay object has a one-byte record called GDI_attributes to store 
attribute flags. There is only one attribute flag, namely 
GDA_USER_DISMISSABLE. If this attribute is set, the user can dismiss a 
display through the UI (without choosing a command in the application). 
Details of this depend on the specific UI; for example, in OSF/Motif, the user 
could dismiss a display by double-clicking the "Control button."

n	MSG_GEN_DISPLAY_GET_ATTRS



GenDisplayAttrs 	MSG_GEN_DISPLAY_GET_ATTRS();

This message retrieves the GDI_attributes field from the destination object.

Source:	Unrestricted.

Destination:	Any GenDisplay or GenPrimary object.

Return:	A GenDisplayAttrs record. The only flag defined is 
GDA_USER_DISMISSABLE.

Interception:	This message is not normally intercepted.

n	MSG_GEN_DISPLAY_SET_ATTRS



void	MSG_GEN_DISPLAY_SET_ATTRS(

	GenDisplayAttrs		attrs);

This message changes the GenDisplayAttrs field of the destination object. 

Source:	Unrestricted.

Destination:	Any GenDisplay or GenPrimary object.

Parameters:	attrs	Field of GenDisplayAttrs flags. There is only one 
flag defined, namely GDA_USER_DISMISSABLE.

Interception:	This message is not normally intercepted.

	4.1.1.2	The GDI_document Field

Applications often use the Document Control objects to manage files. With 
this mechanism, every file is associated with a document object. Often, each 
file will have its own GenDisplay object as well. In this case, GDI_document 
will contain an optr to the GenDocument object associated with this 
GenDisplay. For more information on this, see section 4.3 on page 344. The 
Document Control objects create and destroy the GenDisplays automatically, 
and set this field accordingly. The GenDisplay object uses this field only when 
the display is closed; see section 4.3.3.1 on page 353. To retrieve the value of 
this field, send MSG_GEN_DISPLAY_GET_DOCUMENT to the display (see 
section 4.3.3.3 on page 354).

	4.1.2	Minimizing and Maximizing

MSG_GEN_DISPLAY_SET_MINIMIZED, 
MSG_GEN_DISPLAY_SET_NOT_MINIMIZED, 
MSG_GEN_DISPLAY_GET_MINIMIZED, 
MSG_GEN_DISPLAY_SET_MAXIMIZED, 
MSG_GEN_DISPLAY_SET_NOT_MAXIMIZED, 
MSG_GEN_DISPLAY_GET_MAXIMIZED, 
HINT_DISPLAY_MINIMIZED_ON_STARTUP, 
HINT_DISPLAY_NOT_MINIMIZED_ON_STARTUP, 
HINT_DISPLAY_MAXIMIZED_ON_STARTUP, 
HINT_DISPLAY_NOT_MAXIMIZED_ON_STARTUP, 
ATTR_GEN_DISPLAY_NOT_MINIMIZABLE, 
HINT_DISPLAY_NOT_MAXIMIZABLE, 
ATTR_GEN_DISPLAY_NOT_RESTORABLE,
HINT_DISPLAY_DEFAULT_ACTION_IS_NAVIGATE_TO_NEXT_FIELD

Windows (i.e. displays and "primary" windows) can be resized by the user. 
How resizing is done depends on the specific UI; for example, in OSF/Motif, a 
user resizes a window by dragging its edge. Most specific UIs also allow the 
user to "minimize" or "maximize" a window. When a window is maximized, it 
is expanded to fill all available space; that is, a primary window will fill the 
screen, while a GenDisplay will fill the display area. Windows can also be 
"minimized." A window's behavior when it is minimized depends on the 
specific UI. For example, in OSF/Motif, a minimized Primary is displayed as 
an icon at the bottom of the screen; a minimized Display is removed from the 
display area, but stays in the display control's display list.

Most of the mechanics of minimizing and maximizing windows is taken care 
of by the specific UI. For example, OSF/Motif provides minimize and 
maximize buttons on all Displays and Primaries which do not specifically 
disable the functionality. However, an application can send messages to 
Primary and Display objects to change their minimized/maximized state, or 
to find out what the current state is.

If you do not wish to have a window be minimizable, you can set the vardata 
flag ATTR_GEN_DISPLAY_NOT_MINIMIZABLE. Similarly, if you do not wish 
the window to be maximizable, you can set the flag 
ATTR_GEN_DISPLAY_NOT_MAXIMIZABLE. These instruct the specific UI not 
to provide the controls for minimizing and maximizing. 

You can find out whether a window is currently minimized by sending it 
MSG_GEN_DISPLAY_GET_MINIMIZED. Similarly, you can find out whether 
the window is maximized by sending MSG_GEN_DISPLAY_GET_MAXIMIZED.

If a GenDisplay or GenPrimary has the vardata 
HINT_DISPLAY_MINIMIZED_ON_STARTUP, the object will be created in its 
minimized state. Similarly, if you set 
HINT_DISPLAY_NOT_MINIMIZED_ON_STARTUP, the display will be created 
in its non-minimized form. If you set 
HINT_DISPLAY_MAXIMIZED_ON_STARTUP, the specific UI will create the 
object in its maximized state; correspondingly, if you set 
HINT_DISPLAY_NOT_MAXIMIZED_ON_STARTUP, the specific UI will create 
the display in a non-maximized state. As with all hints, the specific UI may 
ignore these directives. If you set conflicting hints (for example, both 
HINT_DISPLAY_MINIMIZED_ON_STARTUP and 
HINT_DISPLAY_MAXIMIZED_ON_STARTUP), the results are undefined.

Most displays which can be maximized can also be "restored"; that is, a 
control is provided which de-maximizes the object, restoring it to the size it 
was before it was maximized. If the object has the attribute 
ATTR_GEN_DISPLAY_NOT_RESTORABLE, this control will not be provided; 
once a display is maximized, the user will not be able to un-maximize it. This 
hint is generally set only for GenDisplay objects that are maximized on 
startup.

If you do not want a user to be able to resize a GenDisplay or GenPrimary, 
set the vardata HINT_DISPLAY_NOT_RESIZABLE. The specific UI will not 
provide the means for the user to resize the window. This hint will not 
prevent the user from minimizing or maximizing the display.

If you want the user to be able to navigate from GenDisplays using TAB 
navigation, add 
HINT_DISPLAY_DEFAULT_ACTION_IS_NAVIGATE_TO_NEXT_FIELD to the 
object's instance data.

n	MSG_GEN_DISPLAY_SET_MINIMIZED



void	MSG_GEN_DISPLAY_SET_MINIMIZED();

This message instructs a display or primary object to minimize itself. The 
result depends on the specific UI. Primary windows are usually iconified; 
display windows might be iconified or temporarily removed. If the window is 
already minimized, the message has no effect.

Source:	Unrestricted.

Destination:	Any GenDisplay or GenPrimary object.

Interception:	You should not change the behavior of this message. You may intercept 
this message to find out when a window is being minimized; however, 
you should make sure to pass this message on to the superclass.

n	MSG_GEN_DISPLAY_SET_MAXIMIZED



void	MSG_GEN_DISPLAY_SET_MAXIMIZED();

This message instructs a display or primary object to maximize itself. If the 
window is already maximized, the message has no effect.

Source:	Unrestricted.

Destination:	Any GenDisplay or GenPrimary object.

Interception:	You should not change the behavior of this message. You may intercept 
this message to find out when a window is being maximized; however, 
you should make sure to pass this message on to the superclass.

n	MSG_GEN_DISPLAY_SET_NOT_MINIMIZED



void	MSG_GEN_DISPLAY_SET_NOT_MINIMIZED();

This message instructs a display or primary object to de-minimize itself. It 
will generally be restored to its position and configuration as of the time it 
was minimized. If the window is not minimized, the message has no effect.

Source:	Unrestricted.

Destination:	Any GenDisplay or GenPrimary object.

Interception:	You should not change the behavior of this message. You may intercept 
this message to find out when a window is being de-minimized; 
however, you should make sure to pass this message on to the 
superclass.

n	MSG_GEN_DISPLAY_SET_NOT_MAXIMIZED



void	MSG_GEN_DISPLAY_SET_NOT_MAXIMIZED();

This message instructs a display or primary object to de-maximize itself. It 
will generally be restored to its position and configuration as of the time it 
was maximized. If the window is not maximized, the message has no effect.

Source:	Unrestricted.

Destination:	Any GenDisplay or GenPrimary object.

Interception:	You should not change the behavior of this message. You may intercept 
this message to find out when a window is being de-maximized; 
however, you should make sure to pass this message on to the 
superclass.

n	MSG_GEN_DISPLAY_GET_MINIMIZED



Boolean	MSG_GEN_DISPLAY_GET_MINIMIZED();

This message indicates whether the recipient is minimized.

Source:	Unrestricted.

Destination:	Any GenDisplay or GenPrimary object.

Return:	Returns true (i.e. non-zero) if recipient is minimized; otherwise, it 
returns false (i.e. zero).

Interception:	You should not intercept this message.

n	MSG_GEN_DISPLAY_GET_MAXIMIZED



Boolean	MSG_GEN_DISPLAY_GET_MAXIMIZED();

This message indicates whether the recipient is maximized.

Source:	Unrestricted.

Destination:	Any GenDisplay or GenPrimary object.

Return:	Returns true (i.e. non-zero) if recipient is maximized; otherwise, it 
returns false (i.e. zero).

Interception:	You should not intercept this message.

	4.2	Using the GenPrimary

MSG_GEN_PRIMARY_GET_LONG_TERM_MONIKER, 
MSG_GEN_PRIMARY_USE_LONG_TERM_MONIKER, 
MSG_GEN_PRIMARY_REPLACE_LONG_TERM_MONIKER, 
HINT_PRIMARY_FULL_SCREEN, HINT_PRIMARY_NO_FILE_MENU, 
HINT_PRIMARY_NO_EXPRESS_MENU, 
HINT_PRIMARY_OPEN_ICON_BOUNDS, HINT_PRIMARY_NO_HELP_BUTTON


Almost every application will have a single GenPrimary object. GEOS uses 
the GenPrimary to create and manage the primary window of an application. 
A few applications may have several GenPrimary objects; a very few will 
have no GenPrimary at all. (Applications with no GenPrimary generally do 
not have any user interface; they often are intended to work with other 
applications, communicating via streams.)

The structure of the GenPrimary object is almost the same as that of 
GenDisplay. The instance data definitions for GenPrimaryClass are shown 
in Code Display 4-2 below.

Code Display 4-2 Instance data for GenPrimaryClass

/* There is only one instance field specifically defined for GenPrimaryClass. */

/* A GenPrimary object can have a long moniker, which is displayed at the top of
 * the window. The moniker is stored in a chunk in the object block containing the
 * GenPrimary; the attribute GPI_longTermMoniker contains the handle of this
 * chunk. The long-term moniker is described below.*/
    @instance ChunkHandle				GPI_longTermMoniker;

/* GenPrimaryClass also modifies the default GI_attrs settings. */
    @default GI_attrs = @default | GA_TARGETABLE;

/* HINT_PRIMARY_FULL_SCREEN indicates that the primary object should be sized to
 * fill a large portion of the screen. If this hint is not present, the Primary
 * will be just large enough to accommodate its children.*/
    @vardata void 			HINT_PRIMARY_FULL_SCREEN;

/* Ordinarily, every Primary window is created with a File menu. You can suppress
 * this by including HINT_PRIMARY_NO_FILE_MENU. */
    @vardata void 			HINT_PRIMARY_NO_FILE_MENU;

/* Also by default, any launched Primary window gets added to the Express Menu. If 
 * you wish to suppress this behavior, add HINT_PRIMARY_NO_EXPRESS_MENU. */
    @vardata void			HINT_PRIMARY_NO_EXPRESS_MENU;

/* If a primary object is minimizable, the location of the minimized primary is
 * stored in the vardata field HHINT_PRIMARY_OPEN_ICON_BOUNDS.
 */
    @vardata Rectangle			HINT_PRIMARY_OPEN_ICON_BOUNDS

/* By default, all primary windows have a "help" button; when the user clicks on
 * it, the window's help text is brought up. If you don't want the primary to
 * provide help text, you can use the hint HINT_PRIMARY_NO_HELP_BUTTON.
 */
    @vardata void 		HINT_PRIMARY_NO_HELP_BUTTON;



When a Primary window is created, it is usually sized to contain all of its 
components. However, you can suggest that it be sized to fill almost all the 
screen by setting the hint HINT_PRIMARY_FULL_SCREEN. This hint says 
that the Primary should be sized to fill a large portion of the screen, though 
not all of it. (For example, OSF/Motif sets the Primary to fill the whole screen 
except for a narrow space for icons at the bottom.) If this hint is not present, 
the Primary will be just large enough to accommodate its children.

A GenPrimary normally creates a File menu within its menu bar. To 
suppress creation of this file menu, add HINT_PRIMARY_NO_FILE_MENU. 
GenPrimarys, by default, are also added to the list of active applications 
within the system's express menu. Add 
HINT_PRIMARY_NO_EXPRESS_MENU if you wish to avoid adding the 
launched GenPrimary to the express menu.

When a Primary is minimized, it is displayed as an icon with a caption 
beneath it. The icon and caption will be taken from the Primary's moniker 
list (GI_visMoniker). If the Primary lacks either a text moniker or a graphic 
moniker, the missing moniker will be read from the Application object's 
GI_visMoniker field. Most applications will not set GI_visMoniker in the 
Primary object, since it would usually mean duplicating the monikers 
already in the Application object. However, some applications will set this 
(e.g. because they have several Primary objects and want each one to have a 
different icon when minimized).

When the Primary is expanded from a minimized state, its minimized 
location is stored in the hint HINT_PRIMARY_OPEN_ICON_BOUNDS. The 
next time the Primary is minimized, it will be returned to that location.

GPI_longTermMoniker contains a secondary moniker for the Primary object. 
This moniker is displayed along with the Primary moniker, in a way which 
depends on the specific UI. (In OSF/Motif, the Primary's text monikers are 
shown in its title bar: first the text moniker from GI_visMoniker, then a dash, 
then the moniker from GPI_longTermMoniker.) If the GenPrimary has a 
GenDisplayGroup as a child, the GenDisplayGroup will automatically set 
this field to contain the moniker of the top-most GenDisplay. The application 
can override this by sending the Primary 
MSG_GEN_PRIMARY_USE_LONG_TERM_MONIKER, described below.

Most Primary objects will have help text; under most specific UIs, the 
Primary will have a "help" button to bring up this text. If you don't want to 
provide help text, you should set the hint 
HINT_PRIMARY_NO_HELP_BUTTON.

n	MSG_GEN_PRIMARY_GET_LONG_TERM_MONIKER



ChunkHandle 	MSG_GEN_PRIMARY_GET_LONG_TERM_MONIKER();

Use this message to find out the moniker of a GenPrimary object. The 
message returns the chunk handle of the moniker; the moniker is in the same 
block as the GenPrimary object.

Source:	Unrestricted.

Destination:	GenPrimary.

Return:	Returns the chunk handle of the primary's long-term moniker. The 
chunk is in the same object block as the GenPrimary.

Interception:	This message is not ordinarily intercepted.

n	MSG_GEN_PRIMARY_USE_LONG_TERM_MONIKER



void 	MSG_GEN_PRIMARY_USE_LONG_TERM_MONIKER(

	ChunkHandle		moniker);			/* must be in same object block as
					 * primary */

This message instructs a primary window to change its long-term moniker. 
The new long-term moniker must already be in a chunk in the same object 
block as the Primary. The chunk containing the obsolete long-term moniker 
will not be freed; you must do this manually.

Source:	Unrestricted.

Destination:	GenPrimary.

Parameters:	moniker	ChunkHandle of chunk in same object block as the 
GenPrimary. The chunk should contain the new 
long-term moniker.

Interception:	This message is not ordinarily intercepted.

n	MSG_GEN_PRIMARY_REPLACE_LONG_TERM_MONIKER



void	MSG_GEN_PRIMARY_REPLACE_LONG_TERM_MONIKER(@stack

	VisUpdateMode 		updateMode,

	word 		height, 

	word 		width, 

	word 		length,

	VisMonikerDataType 		dataType,

	VisMonikerSourceType 		sourceType,

	dword 		source);

This message is used to replace a primary's long term moniker with a new 
one. This message's arguments are precisely like those to the message 
MSG_GEN_REPLACE_VIS_MONIKER. Note that a long term moniker is 
ordinarily a simple text string. For more information, see "Managing Visual 
Monikers", section 2.4.2 of chapter 2.

Source:	Unrestricted.

Destination:	GenPrimary.

Parameters:		The parameters are the same as those for 
MSG_GEN_REPLACE_VIS_MONIKER.

Return:	Returns the chunk handle of the new long-term moniker. The moniker 
will be allocated in the Primary's object block.

Interception:	This message is not ordinarily intercepted.

	4.3	Using Multiple Displays

Many applications will need to have several similar user interface areas. For 
example, a word processor might have several documents open at once; each 
of these would need its own text area. GEOS provides a facility for this. 

An application can have several GenDisplay objects, each of which must be a 
child of a GenDisplayGroup object. The user can then switch back and forth 
between the displays using the GenDisplayControl (which is usually a child 
of a "Window" menu). The switching is transparent to the application.

If the application uses one display for each document, it should use the 
Document Control objects to create the displays. The Document Control can 
automatically duplicate a resource containing a generic object tree headed by 
a GenDisplay and make that GenDisplay a child of the GenDisplayGroup 
each time a document is opened or created. For details, see "GenDocument," 
Chapter 13.

	4.3.1	GenDisplayGroup


If an application uses GenDisplay objects, it must have a GenDisplayGroup 
object. This object makes sure there is space in the GenPrimary for the 
displays.

The GenDisplayGroup must be either a child of the GenPrimary (in which 
case the specific UI will decide where to put the display area) or a child of a 
GenInteraction which is a child of the GenPrimary (if the application 
wants the display area in a specific part of the GenPrimary). The 
GenDisplayGroup should be run by the UI thread.

GenDisplayGroupClass has no instance data which may be set or 
examined by the application. However, GenDisplayGroupClass is a 
subclass of GenClass, and inherits all of its instance data. When you declare 
a GenDisplayGroup, you may specify its GenClass instance data normally; 
you may also include any of the hints described in the following sections.

	4.3.1.1	The GenDisplayGroup Instance Data

HINT_DISPLAY_GROUP_SEPARATE_MENUS, 
HINT_DISPLAY_GROUP_ARRANGE_TILED, 
HINT_DISPLAY_GROUP_FULL_SIZED_ON_STARTUP, 
HINT_DISPLAY_GROUP_OVERLAPPING_ON_STARTUP, 
HINT_DISPLAY_GROUP_FULL_SIZED_IF_TRANSPARENT_DOC_CTRL_MODE
, HINT_DISPLAY_GROUP_TILE_HORIZONTALLY, 
HINT_DISPLAY_GROUP_TILE_VERTICALLY, 
HINT_DISPLAY_GROUP_SIZE_INDEPENDENTLY_OF_DISPLAYS

GenDisplayGroupClass is a subclass of GenClass. Other than vardata, this 
class adds no other instance data. There are several hints defined for 
GenDisplayGroupClass. Most of these hints specify how displays should 
be arranged on startup.

Code Display 4-3 GenDisplayGroup Instance Data

/* GenDisplayGroupClass adds no instance fields. It does modify the default 
 * GI_attrs settings, however. */
    @default GI_attrs = @default | GA_TARGETABLE;

/* This hint allows each GenDisplay to contain its own menu bar. */
    @vardata void			HINT_DISPLAY_GROUP_SEPARATE_MENUS;

/* These hints specify how a GenDisplayGroup will arrange its GenDisplays. */
    @vardata void			HINT_DISPLAY_GROUP_ARRANGE_TILED;
    @vardata void			HINT_DISPLAY_GROUP_FULL_SIZED_ON_STARTUP;
    @vardata void			HINT_DISPLAY_GROUP_OVERLAPPING_ON_STARTUP;
    @vardata void			
HINT_DISPLAY_GROUP_FULL_SIZED_IF_TRANSPARENT_DOC_CTRL_MODE;
    @vardata void			HINT_DISPLAY_GROUP_TILE_HORIZONTALLY;
    @vardata void			HINT_DISPLAY_GROUP_TILE_VERTICALLY;
    @vardata void			HINT_DISPLAY_GROUP_SIZE_INDEPENDENTLY_OF_DISPLAYS;

/* These attributes affect the availability of overlapping and 
 * full-sized states. */
    @vardata void			ATTR_GEN_DISPLAY_GROUP_NO_FULL_SIZED;
    @vardata void			ATTR_GEN_DISPLAY_GROUP_NO_OVERLAPPING;
    @vardata void			ATTR_GEN_DISPLAY_OVERLAPPING_STATE;



In some specific UIs (such as OSF/Motif), menus which are children of a 
GenDisplay object may appear in two ways: they may be drawn on the 
Primary's menu bar (the default in OSF/Motif), or they may appear in a menu 
bar on the display itself. HINT_DISPLAY_GROUP_SEPARATE_MENUS 
indicates that each display should be given its own menu bar (if the specific 
UI permits this).

There are several hints which specify how the displays should be configured 
when the GenDisplayGroup is built.

HINT_DISPLAY_GROUP_FULL_SIZED_ON_STARTUP indicates that the 
GenDisplayGroup should be in full-size mode on startup; that is, all of its 
children should be maximized.

HINT_DISPLAY_GROUP_OVERLAPPING_ON_STARTUP indicates that the 
GenDisplayGroup should be in overlapping mode on startup; that is, its 
children should be non-maximized.

HINT_DISPLAY_GROUP_FULL_SIZED_IF_TRANSPARENT_DOC_CTRL_MODE 
forces a GenDisplayGroup to start full-sized if the application is in 
"transparent document control" mode, which is set by the user level of the 
application. This hint overrides 
HINT_DISPLAY_GROUP_OVERLAPPING_ON_STARTUP, if present.

HINT_DISPLAY_GROUP_ARRANGE_TILED indicates that the 
GenDisplayGroup should be in overlapping mode on startup, and further 
that the displays should be tiled; that is, they should be non-maximized and 
arranged in a non-overlapping way to fill the display area.

You can specify a preference for how the displays should be tiled by setting 
HINT_DISPLAY_GROUP_TILE_HORIZONTALLY or 
HINT_DISPLAY_GROUP_TILE_VERTICALLY. 
HINT_DISPLAY_GROUP_TILE_HORIZONTALLY indicates that you want tiled 
displays to be arranged horizontally, with each display tall enough to fill the 
display area. Similarly, HINT_DISPLAY_GROUP_TILE_VERTICALLY indicates 
that you want tiled displays to be arranged vertically, with each display wide 
enough to fill the display area. If both hints are set, the result varies 
depending on the specific UI.

HINT_DISPLAY_GROUP_SIZE_INDEPENDENTLY_OF_DISPLAYS sizes a 
GenDisplayGroup by what its parent wants rather than what any of its 
children GenDisplays want. This may improve geometry performance in a 
complex GenPrimary/GenDisplay combination.

	4.3.1.2	Arranging Displays in the Display Group

MSG_GEN_DISPLAY_GROUP_SET_OVERLAPPING, 
MSG_GEN_DISPLAY_GROUP_SET_FULL_SIZED, 
MSG_GEN_DISPLAY_GROUP_GET_FULL_SIZED, 
MSG_GEN_DISPLAY_GROUP_TILE_DISPLAYS, 
ATTR_GEN_DISPLAY_GROUP_NO_FULL_SIZED, 
ATTR_GEN_DISPLAY_GROUP_NO_OVERLAPPING, 
ATTR_GEN_DISPLAY_GROUP_OVERLAPPING_STATE

The GenDisplayGroup can be in "full-sized" or "overlapping" mode. If the 
GenDisplayGroup is in "full-size" mode, all of its children are maximized 
(except any displays which are set "non-maximizable"). If it is not in 
full-sized mode, it is said to be in "overlapping" mode; that is, none of its 
children are maximized. When a user maximizes any display which belongs 
to a GenDisplayGroup, the GenDisplayGroup automatically goes into 
"full-size" mode and maximizes all of its children.

If you include ATTR_GEN_DISPLAY_GROUP_NO_FULL_SIZED, the 
GenDisplayControl will not be able to go into full-size mode; it will always be 
in overlapping mode. Similarly, if set 
ATTR_GEN_DISPLAY_GROUP_NO_OVERLAPPING, the GenDisplayControl 
will not be able to go into overlapping mode; it will always be in full-sized 
mode, and all displays will always be maximized. Naturally, you may not 
include both of these attributes at once; if you do, results are undefined.

Messages are provided which switch the GenDisplayGroup into one or 
another of these modes. You might not need to use any of these messages. If 
you use a GenDisplayControl object, the user will be able to switch from 
overlapping to full-size and also to tile the displays by using that object. 
However, you can also send the following messages directly.

You can set a GenDisplayGroup to full-sized mode by sending it the message 
MSG_GEN_DISPLAY_GROUP_SET_FULL_SIZED. This message causes the 
GenDisplayGroup to maximize every one of its children. Children which 
cannot be maximized will be unaffected. The window layering and 
focus/target settings are not changed.

You can set a GenDisplayGroup to overlapping mode by sending it the 
message MSG_GEN_DISPLAY_GROUP_SET_OVERLAPPING. This message 
causes a GenDisplayGroup object to de-maximize all of its children. Children 
which are not restorable will be unaffected. The window layering and 
focus/target settings are not changed.

You can find out whether a GenDisplayGroup object is in full-sized mode by 
sending it MSG_GEN_DISPLAY_GROUP_GET_FULL_SIZED. If the 
GenDisplayGroup is in full-sized mode, this message will return true.

You can also put a GenDisplayGroup into "tiled" mode. This is a special case 
of overlapping mode. When a GenDisplayGroup is put in tiled mode, it first 
puts itself in overlapping mode. It then attempts to arrange and resize its 
display children so they fill the display area without overlapping. To put a 
GenDisplayGroup into tiled mode, send it the message 
MSG_GEN_DISPLAY_GROUP_TILE_DISPLAYS.

The GenDisplayGroup keeps track of its overlapping state across shutdowns. 
It does this by setting ATTR_GEN_DISPLAY_GROUP_OVERLAPPING_STATE. 
Applications may not set or change this attribute directly.

n	MSG_GEN_DISPLAY_GROUP_SET_FULL_SIZED



void	MSG_GEN_DISPLAY_GROUP_SET_FULL_SIZED();

This message instructs a GenDisplayGroup to put itself in "full-sized" mode; 
that is, all of its maximizable children will be maximized. This message is 
ignored if the GenDisplayGroup has the vardata attribute 
ATTR_GEN_DISPLAY_GROUP_NO_FULL_SIZED.

Source:	Unrestricted.

Destination:	GenDisplayGroup.

Interception:	Not generally intercepted.

n	MSG_GEN_DISPLAY_GROUP_SET_OVERLAPPING



void	MSG_GEN_DISPLAY_GROUP_SET_OVERLAPPING();

This message instructs a GenDisplayGroup to put itself in "overlapping" 
mode. This message is ignored if the GenDisplayGroup has the vardata 
attribute ATTR_GEN_DISPLAY_GROUP_NO_OVERLAPPING.

Source:	Unrestricted.

Destination:	GenDisplayGroup.

Interception:	Not generally intercepted.

n	MSG_GEN_DISPLAY_GROUP_GET_FULL_SIZED



Boolean	MSG_GEN_DISPLAY_GROUP_GET_FULL_SIZED();

This message finds out whether a GenDisplayGroup is in "full-sized" mode.

Source:	Unrestricted.

Destination:	GenDisplayGroup.

Return:	Returns true (i.e. non-zero) if the GenDisplayGroup is in full-sized 
mode; otherwise, it returns false (i.e. zero).

Interception:	Not generally intercepted.

n	MSG_GEN_DISPLAY_GROUP_TILE_DISPLAYS



void	MSG_GEN_DISPLAY_GROUP_TILE_DISPLAYS;

This message instructs a GenDisplayGroup to put itself in "tiled" mode. That 
is, it should first put itself in "overlapping" mode; it should then arrange and 
resize the displays so they fill the display area without overlapping. The 
message is ignored if the GenDisplayGroup has the vardata attribute 
ATTR_GEN_DISPLAY_GROUP_NO_OVERLAPPING.

Source:	Unrestricted.

Destination:	GenDisplayGroup.

Interception:	Not generally intercepted.

	4.3.1.3	Selecting a Display

MSG_GEN_DISPLAY_GROUP_SELECT_DISPLAY

Ordinarily, the user switches from one display to another in one of two ways. 
The user may use the specific UI's way of switching displays (e.g. clicking on 
the display); or he may use the GenDisplayControl (described below) to 
switch displays. The application can also force the Display Group to bring a 
certain display to the top by sending it 
MSG_GEN_DISPLAY_GROUP_SELECT_DISPLAY. However, this is not usually 
done; applications should generally let the user switch displays with the 
GenDisplayControl.

n	MSG_GEN_DISPLAY_GROUP_SELECT_DISPLAY



void	MSG_GEN_DISPLAY_GROUP_SELECT_DISPLAY(

	word	displayNum);

This message instructs a display group to select a certain display, bringing it 
to the top and making it the focus. Applications should not ordinarily need to 
send this.

Source:	Usually GenDisplayControl or its associated objects; however, any 
object can send this.

Destination:	GenDisplayGroup.

Parameters:	displayNum	The display to select. This is an integer specifying 
the position of the desired display among the 
GenDisplayGroup's children; that is, its first child 
is number zero, its next child is number one, and so 
on.

Interception:	This message is not ordinarily intercepted.

Tips:	You can find a display's position number by sending 
MSG_GEN_FIND_CHILD to the GenDisplayGroup, passing the optr of 
the desired display. See section 2.5.1 of chapter 2.

	4.3.2	GenDisplayControl


The GenDisplayGroup object does half the job of managing display objects: it 
creates a space for the displays and manages them as its children. However, 
the display group does very little interaction with the user. Instead, the user 
works mainly with the GenDisplayControl object.

The GenDisplayControl is usually a child of a "Window" GenInteraction, 
which is itself a child of the primary. GenDisplayControlClass is a 
subclass of GenControlClass, and it has all the functionality of that class. 
For more information, see "Generic UI Controllers," Chapter 12.

GenDisplayControlClass is based very closely on GenControlClass. The 
differences between it and GenControlClass are shown below in Code 
Display 4-4.

Code Display 4-4 Instance Data of GenDisplayControlClass

/* GDCII_attrs is a byte-length flag field. There is currently only one flag,
 * namely GDCA_MAXIMIZED_NAME_ON_PRIMARY; this specifies that if the active
 * display is maximized, its name should be shown as the primary's long-term 
 * moniker. */
    @instance 		GenDisplayControlAttributes				GDCII_attrs =
						(GDCA_MAXIMIZED_NAME_ON_PRIMARY);

@default		GI_states = @default | GS_ENABLED;
@default 		GCI_output = {TO_APP_TARGET};

typedef WordFlags GDCFeatures;
#define GDCF_OVERLAPPING_MAXIMIZED					0x0004
#define GDCF_TILE					0x0002
#define GDCF_DISPLAY_LIST					0x0001

typedef WordFlags GDCToolboxFeatures;
#define GDCTF_OVERLAPPING_MAXIMIZED					0x0004
#define GDCTF_TILE					0x0002
#define GDCTF_DISPLAY_LIST					0x0001

#define GDC_DEFAULT_FEATURES 				(GDCF_OVERLAPPING_MAXIMIZED | GDCF_TILE 
				| GDCF_DISPLAY_LIST)

#define GDC_DEFAULT_TOOLBOX_FEATURES (GDCF_DISPLAY_LIST)

/* A GenDisplayControl also features a single hint which affects the display of 
 * the features list. */
    @vardata void HINT_DISPLAY_CONTROL_NO_FEATURES_IF_TRANSPARENT_DOC_CTRL_MODE;



The GDCII_attrs field contains a set of GenDisplayControlAttributes. 
There is currently only one flag defined among these attributes:

GDCA_MAXIMIZED_NAME_ON_PRIMARY
If this attribute is set and the active display is maximized, the 
name of the selected display will be shown in the long term 
moniker of the GenPrimary.

HINT_DISPLAY_CONTROL_NO_FEATURES_IF_TRANSPARENT_DOC_CTRL_M
ODE suppresses display of the features list if the application is running in 
"transparent document control" mode, as selected by the user level of the 
application.

	4.3.3	Using GenDisplayClass Objects

All GenDisplay objects must be children of a GenDisplayGroup object. 
GenDisplay objects can be created in several ways: an application can declare 
them in its code; it can instantiate them at run-time and make them children 
of the GenDisplayGroup; or, if the application uses the Document Control 
objects, it can have the Document Control create a new display automatically 
whenever a document is opened. (For details about using a Document 
Control to create GenDisplay objects, see "GenDocument," Chapter 13.)

	4.3.3.1	Closing GenDisplays

MSG_GEN_DISPLAY_CLOSE

Most specific UIs provide a way for the user to close windows. For example, 
OSF/Motif lets a user close a window by double-clicking the control button. 
When the user uses the specific UI's close mechanism, the Display or Primary 
is sent MSG_GEN_DISPLAY_CLOSE. 

GenDisplayClass does only one thing when it receives 
MSG_GEN_DISPLAY_CLOSE: it sends MSG_GEN_DOCUMENT_CLOSE to the 
document specified by GDI_document. The GenDisplayClass handler for 
MSG_GEN_DISPLAY_CLOSE does not, in fact, destroy the display. If the 
display is linked to a GenDocument, the GenDocument will respond to 
MSG_GEN_DOCUMENT_CLOSE by closing the application and removing the 
GenDisplay. Otherwise, you will have to remove the GenDisplay yourself by 
writing a handler for MSG_GEN_DISPLAY_CLOSE.

The GenPrimaryClass handler for MSG_GEN_DISPLAY_CLOSE closes the 
application. If you want to add to or replace this behavior, you may have your 
Primary subclass this message.

n	MSG_GEN_DISPLAY_CLOSE



void	MSG_GEN_DISPLAY_CLOSE();

This message is sent to a Display to close it. The system sends it when the 
user uses the specific UI's way of closing a window. The GenDisplayClass 
handler does nothing but send a MSG_GEN_DOCUMENT_CLOSE to the 
Document object specified in GDI_document. The GenPrimaryClass 
handler closes the application.

Source:	Unrestricted.

Destination:	GenDisplay.

Interception:	If the Display is not associated with a GenDocument, you will need to 
subclass this message for it to have any effect at all. If the display is 
associated with a GenDocument object, you should probably subclass 
your Document object's MSG_GEN_DOCUMENT_CLOSE instead. 
Primary objects may subclass this message if they want to alter or 
replace the default behavior (of closing the application).

	4.3.3.2	Menu Bar PopOuts

ATTR_GEN_DISPLAY_MENU_BAR_POPPED_OUT

Some objects contain the ability to "pop out" of their sub-group locations and 
become floating dialog boxes.The menu bar of a GenDisplay is one such 
GenInteraction. If the menu bar of a GenDisplay is currently in the 
"popped-out" state, it will contain the vardata entry 
ATTR_GEN_DISPLAY_MENU_BAR_POPPED_OUT.

	4.3.3.3	Messages sent to GenDisplays

MSG_GEN_DISPLAY_UPDATE_FROM_DOCUMENT, 
MSG_GEN_DISPLAY_GET_DOCUMENT

Many of the messages which can be sent to GenDisplay objects have already 
been discussed above in section 4.1. However, there are a few messages which 
are ordinarily sent to Displays but not to Primaries. These messages are 
discussed here.

GenDisplay objects often work in close conjunction with the Document 
Control objects. It is common for every open document to have its own 
GenDisplay object as well as its own GenDocument. The two objects work in 
conjunction, sending messages back and forth to communicate. You can send 
or intercept these messages yourself to add functionality.

When the document object changes in certain significant ways, the Display 
has to be brought into accord with it. For example, if the name of the file 
changes, the GenDisplay's moniker will have to be changed to reflect this. 
Whenever a significant change takes place, the Document Control objects 
send a MSG_GEN_DISPLAY_UPDATE_FROM_DOCUMENT to the appropriate 
Display. The Display then requests all necessary information from the 
GenDocument and makes any necessary changes to its own instance data. 
You can force this updating by sending the message directly to the Display. 
You can also subclass this message if you want to add special updating 
behavior; however, you should be sure to pass this message to the superclass' 
handler.

You can find out which Document object is associated with a given Display by 
sending MSG_GEN_DISPLAY_GET_DOCUMENT to the Display. The message 
will return an optr to the corresponding Document object.

n	MSG_GEN_DISPLAY_UPDATE_FROM_DOCUMENT



void	MSG_GEN_DISPLAY_UPDATE_FROM_DOCUMENT();

This message instructs a GenDisplay to update its instance data from its 
associated GenDocument object (if any). This message is ordinarily sent by 
the Document Control objects.

Source:	Unrestricted-ordinarily sent only by Document Control objects.

Destination:	GenDisplay.

Interception:	Normally not intercepted. If you subclass this message to add special 
updating behavior, be sure to end with an @callsuper.

n	MSG_GEN_DISPLAY_GET_DOCUMENT



optr	MSG_GEN_DISPLAY_GET_DOCUMENT();

This message returns the optr of the GenDocument associated with a given 
GenDisplay. This is equal to the value of the GenDisplay's GDI_document 
field.

Source:	Unrestricted-ordinarily sent only by Document Control objects.

Destination:	GenDisplay.

Interception:	Normally not intercepted. 

	4.3.3.4	Traveling Objects

ATTR_GEN_DISPLAY_TRAVELLING_OBJECTS

If you use multiple GenDisplay objects, it is sometimes useful to set up a 
group of "traveling objects." Traveling objects are children of whichever 
display is active. When a different GenDisplay is brought to the top, all 
traveling objects will be set "not usable" and removed from the Generic tree. 
They will then be added as children of the new top display and set "usable." 
(Any children of the traveling objects will naturally move with them.) 
Traveling objects are most commonly Toolbox Interactions, but they can be 
any kind of generic object.

Traveling objects can only be used under certain circumstances. Every 
display must belong to its own object block, and all of these object blocks must 
be copies of the same original. This is because the traveling objects are added 
as children to a specified chunk in whichever object block contains the new 
top display. If you want to use traveling objects, you should declare a special 
"template" object block which contains a GenDisplay and its children. 
Whenever you need to create a GenDisplay, you should duplicate this object 
block. The traveling objects should be in another resource altogether. If you 
use the Document Control objects to create displays, the objects will use this 
technique, duplicating an object block for each new display; this will let you 
use traveling objects.

Every traveling object is indicated by a TravelingObjectReference 
structure (see Code Display 4-5). To attach traveling objects to the active 
display, create a chunk which contains a list of TravelingObjectReference 
structures; this chunk must be in the same object block as the active display. 
Then set the Display's ATTR_GEN_DISPLAY_TRAVELING_OBJECTS to the 
ChunkHandle of the list. The list will automatically be moved to the block of 
the active display whenever the traveling objects are moved.

Code Display 4-5 TravelingObjectReference

typedef struct {
    optr		TIR_travelingObject;			/* optr to traveling object whose
					 * reference this is */

    ChunkHandle		TIR_parent;			/* Chunk Handle of object in Display's
					 * block that will be the parent of this
					 * object */

    word		TIR_compChildFlags;			/* CompChildFlags to use when
					 * adding the traveling object */
} TravelingObjectReference;



The TravelingObjectReference structure has the following three fields:

TIR_travelingObject
This field is an optr to the traveling object whose reference this 
is.

TIR_parent	This field holds the chunk handle of an object in the display 
block. When the traveling object is added to a display block, it 
will be made a child of the object whose chunk handle this is.

TIR_compChildFlags
This is the set of CompChildFlags which will be used when 
attaching this object to its new parent.
