{Begin SubSec Attached Windows} {Title Attached Windows} {Text {index *PRIMARY* Attached windows} The attached window facility makes it easy to manipulate a group of window as a unit. Standard window operations like moving, reshaping, opening, and closing can be done so that it appears to the user as if the windows are a single entity. Each collection of attached windows has one main window and any number of other windows that are "attached" to it. Moving or reshaping the main window causes all of the attached windows to be moved or reshaped as well. Moving or reshaping an attached window does not affect the main window. Attached windows can have other windows attached to them. Thus, it is possible to attach window A to window B when B is already attached to window C. Similarly, if A has other windows attached to it, it can still be attached to B. {FnDef {Name ATTACHWINDOW} {Args WINDOWTOATTACH MAINWINDOW EDGE POSITIONONEDGE WINDOWCOMACTION} {Text Associates {arg WINDOWTOATTACH} with {arg MAINWINDOW} so that window operations done to {arg MAINWINDOW} are also done to {arg WINDOWTOATTACH} (the exact set of window operations passed between main windows and attached windows is described on {PageRef (Window Property) PASSTOMAINCOMS}). {fn ATTACHWINDOW} moves {arg WINDOWTOATTACH} to the correct position relative to {arg MAINWINDOW}. Note: A window can be attached to only one other window. Attaching a window to a second window will detach it from the first. Attachments can not form loops. That is, a window cannot be attached to itself or to a window that is attached to it. {fn ATTACHWINDOW} will generate an error if this is attempted. {arg EDGE} determines which edge of {arg MAINWINDOW} the attached window is positioned along: it should be one of {lisp TOP}, {lisp BOTTOM}, {lisp LEFT}, or {lisp RIGHT}. If {arg EDGE} is {lisp NIL}, it defaults to {lisp TOP}. {arg POSITIONONEDGE} determines where along {arg EDGE} the attached window is positioned. It should be one of the following: {Begin LabeledList} {Label {lisp LEFT}} {Text The attached window is placed on the left (of a {lisp TOP} or {lisp BOTTOM} edge).} {Label {lisp RIGHT}} {Text The attached window is placed on the right (of a {lisp TOP} or {lisp BOTTOM} edge).} {Label {lisp BOTTOM}} {Text The attached window is placed on the bottom (of a {lisp LEFT} or {lisp RIGHT} edge).} {Label {lisp TOP}} {Text The attached window is placed on the top (of a {lisp LEFT} or {lisp RIGHT} edge).} {Label {lisp CENTER}} {Text The attached window is placed in the center of the edge.} {Label {lisp JUSTIFY}} {Label or {lisp NIL}} {Text The attached window is placed to fill the entire edge. {fn ATTACHWINDOW} reshapes the window if necessary. Note: The width or height used to justify an attached window includes any other windows that have already been attached to {arg MAINWINDOW}. Thus {lisp (ATTACHWINDOW BBB AAA 'RIGHT 'JUSTIFY)} followed by {lisp (ATTACHWINDOW CCC AAA 'TOP 'JUSTIFY)} will put {lisp CCC} across the top of both {lisp BBB} and {lisp AAA}: xKџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџќ8pџџџџџџџџџџџџћзЏџџџџџџџџџџџћїяџџџџџџџџџџџџћїяџџџџџџџџџџџџћзЏџџџџџџџџџџџќ8pџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџРРРРРРРРРРРРРРРРРРРРРРРРџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџў§ћџџџџјpсџџџџџ§zѕџџџџћЗnџџџџџ§zѕџџџџјpсџџџџџћЗnџџџџћЗnџџџџџј0`џџџџћЗnџџџџџїЯŸџџџјpсџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџРРРРРРРРРРРРРРРРРРРРРРРРРРРРРРРРРРРРРРРРРРРРРРРРРРџџџџџџџџџџџџџџџџџџџџџџџџџџџџџџ} {End LabeledList} {arg WINDOWCOMACTION} provides a convenient way of specifying how {arg WINDOWTOATTACH} responds to right button menu commands. The window property {lisp PASSTOMAINCOMS} determines which right button menu commands are directly applied to the attached window, and which are passed to the main window (see {PageRef (Window Property) PASSTOMAINCOMS}). Depending on the value of {arg WINDOWCOMACTION}, the {lisp PASSTOMAINCOMS} window property of {arg WINDOWTOATTACH} is set as follows: {Begin LabeledList WINDOWCOMACTION values} {Label {Lisp NIL}} {Text {lisp PASSTOMAINCOMS} is set to {lisp (CLOSEW MOVEW SHAPEW SHRINKW BURYW)}, so right button menu commands to close, move, shape, shrink, and bury are passed to the main window, and all others are applied to the attached window.} {Label {Lisp LOCALCLOSE}} {Text {lisp PASSTOMAINCOMS} is set to {lisp (MOVEW SHAPEW SHRINKW BURYW)}, which is the same as when {arg WINDOWCOMACTION} is {lisp NIL}, except that the attached window can be closed independently.} {Label {Lisp HERE}} {Text {lisp PASSTOMAINCOMS} is set to {lisp NIL}, so all right button menu commands are applied to the attached window.} {Label {Lisp MAIN}} {Text {lisp PASSTOMAINCOMS} is set to {lisp T}, so all right button menu commands are passed to the main window.} {End LabeledList WINDOWCOMACTION values} Note: If the user wants to set the {lisp PASSTOMAINCOMS} window property of an attached window to something else, it must be done {it after} the window is attached, since {fn ATTACHWINDOW} modifies this window property. }} {FnDef {Name DETACHWINDOW} {Args WINDOWTODETACH} {Text Detaches {arg WINDOWTODETACH} from its main window. Returns a dotted pair {lisp ({arg EDGE} . {arg POSITIONONEDGE})} if {arg WINDOWTODETACH} was an attached window, {lisp NIL} otherwise. This does not close {arg WINDOWTODETACH}. }} {FnDef {Name DETACHALLWINDOWS} {Args MAINWINDOW} {Text Detaches and closes all windows attached to {arg MAINWINDOW}. }} {FnDef {Name FREEATTACHEDWINDOW} {Args WINDOW} {Text Detaches the attached window {arg WINDOW}. In addition, other attached windows above (in the case of a {lisp TOP} attached window) or below (in the case of a {lisp BOTTOM} attached window) are moved closer to the main window to fill the gap. Note: Attached windows that "reject" the move operation (see {lisp REJECTMAINCOMS}, {PageRef (Window Property) REJECTMAINCOMS}) are not moved. Note: {fn FREEATTACHEDWINDOW} currently doesn't handle {lisp LEFT} or {lisp RIGHT} attached windows. }} {FnDef {Name REMOVEWINDOW} {Args WINDOW} {Text Closes {arg WINDOW}, and calls {fn FREEATTACHEDWINDOW} to move other attached windows to fill any gaps. }} {FnDef {Name REPOSITIONATTACHEDWINDOWS} {Args WINDOW} {Text Repositions every window attached to {arg WINDOW}, in the order that they were attached. This is useful as a {lisp RESHAPEFN} for main windows with attached window that don't want to be reshaped, but do want to keep their position relative to the main window when the main window is reshaped. Note: Attached windows that "reject" the move operation (see {lisp REJECTMAINCOMS}, {PageRef (Window Property) REJECTMAINCOMS}) are not moved. }} {FnDef {Name MAINWINDOW} {Args WINDOW RECURSEFLG} {Text If {arg WINDOW} is not a window, it generates an error. If {arg WINDOW} is closed, it returns {arg WINDOW}. If {arg WINDOW} is not attached to another window, it returns {arg WINDOW} itself. If {arg RECURSEFLG} is {lisp NIL} and {arg WINDOW} is attached to a window, it returns that window. If {arg RECURSEFLG} is {lisp T}, it returns the first window up the "main window" chain starting at {arg WINDOW} that is not attached to any other window. }} {FnDef {Name ATTACHEDWINDOWS} {Args WINDOW COM} {Text Returns the list of windows attached to {arg WINDOW}. If {arg COM} is non-{lisp NIL}, only those windows attached to {arg WINDOW} that do not reject the window operation {arg COM} are returned (see {lisp REJECTMAINCOMS}, {PageRef (Window Property) REJECTMAINCOMS}). }} {FnDef {Name ALLATTACHEDWINDOWS} {Args WINDOW} {Text Returns a list of all of the windows attached to {arg WINDOW} or attached to a window attached to it. }} {FnDef {Name WINDOWREGION} {Args WINDOW COM} {Text Returns the screen region occupied by {arg WINDOW} and its attached windows, if it has any. If {arg COM} is non-{lisp NIL}, only those windows attached to {arg WINDOW} that do not reject the window operation {arg COM} are considered in the calculation (see {lisp REJECTMAINCOMS}, {PageRef (Window Property) REJECTMAINCOMS}). }} {FnDef {Name WINDOWSIZE} {Args WINDOW} {Text Returns the size of {arg WINDOW} and its attached windows (if any), as a dotted pair {lisp ({arg WIDTH} . {arg HEIGHT})}. }} {FnDef {Name MINATTACHEDWINDOWEXTENT} {Args WINDOW} {Text Returns the minimum size that {arg WINDOW} and its attached windows (if any) will accept, as a dotted pair {lisp ({arg WIDTH} . {arg HEIGHT})}. }} {Begin SubSec Attaching Menus To Windows} {Title Attaching Menus To Windows} {Text The following functions are provided to associate menus to windows. {FnDef {Name MENUWINDOW} {Args MENU VERTFLG} {Text Returns a closed window that has the menu {arg MENU} in it. If {arg MENU} is a list, a menu is created with {arg MENU} as its {lisp ITEMS} menu field (see {PageRef (Menu Field) ITEMS}). Otherwise, {arg MENU} should be a menu. The returned window has the appropriate {lisp RESHAPEFN}, {lisp MINSIZE} and {lisp MAXSIZE} window properties to allow its use in a window group. If both the {lisp MENUROWS} and {lisp MENUCOLUMNS} fields of {arg MENU} are {lisp NIL}, {arg VERTFLG} is used to set the default menu shape. If {arg VERTFLG} is non-{lisp NIL}, the {lisp MENUCOLUMNS} field of {arg MENU} will be set to 1 (the menu items will be listed vertically); otherwise the {lisp MENUROWS} field of {arg MENU} will be set to 1 (the menu items will be listed horizontally). }} {FnDef {Name ATTACHMENU} {Args MENU MAINWINDOW EDGE POSITIONONEDGE NOOPENFLG} {Text Creates a window that contains the menu {arg MENU} (by calling {fn MENUWINDOW}) and attaches it to the window {arg MAINWINDOW} on edge {arg EDGE} at position {arg POSITIONONEDGE}. The menu window is opened unless {arg MAINWINDOW} is closed, or {arg NOOPENFLG} is {lisp T}. If {arg EDGE} is either {lisp LEFT} or {lisp RIGHT}, {fn MENUWINDOW} will be called with {arg VERTFLG}={lisp T}, so the menu items will be listed vertically; otherwise the menu items will be listed horizontally. These defaults can be overridden by specifying the {lisp MENUROWS} or {lisp MENUCOLUMNS} fields in {arg MENU}. }} {FnDef {Name CREATEMENUEDWINDOW} {Args MENU WINDOWTITLE LOCATION WINDOWSPEC} {Text Creates a window with an attached menu and returns the main window. {arg MENU} is the only required argument, and may be a menu or a list of menu items. {arg WINDOWTITLE} is a string specifying the title of the main window. {arg LOCATION} specifies the edge on which to place the menu; the default is {lisp TOP}. {arg WINDOWSPEC} is a region specifying a region for the aggregate window; if {lisp NIL}, the user is prompted for a region. }} Examples: {lispcode (SETQ MENUW (MENUWINDOW (create MENU ITEMS _ '(smaller LARGER) MENUFONT _ '(MODERN 12) TITLE _ "zoom controls" CENTERFLG _ T WHENSELECTEDFN _ (FUNCTION ZOOMMAINWINDOW))))} creates (but does not open) a menu window that contains the two items "{lisp smaller}" and "{lisp LARGER}" with the title "{lisp zoom controls}" and that calls the function {lisp ZOOMMAINWINDOW} when an item is selected. Note that the menu items will be listed horizontally, because {fn MENUWINDOW} is called with {arg VERTFLG}={lisp NIL}, and the menu does not specify either a {lisp MENUROWS} or {lisp MENUCOLUMNS} field. {lispcode (ATTACHWINDOW MENUW (CREATEW '(50 50 150 50)) 'TOP 'JUSTIFY)} creates a window on the screen and attaches the above created menu window to its top: –KџџџџџџџџџџџџџџџџџџќџџџџџџџџџџџџџџџџџџќџџџџџџџџџџџпўџџџџџќџџџџџУ<щ?žtŠЮуџџџџќџџџџџілdПmВиЖпџџџџќџџџџџюлmП}ЖлЖчџџџџќџџџџџолmПmЖлЖћџџџџќџџџџџУ<эПžvЫЮЧџџџџќџџџџџџџџџџџџџџџџџџќџџџџџџџџџџџџџџџџџџќ€€$€$<>x€$"! D€Г$q`"@ D€ Ь$‰€<@"A D€ˆ“$A"! D€8ˆ$yA!>B€€€€џџџџџџџџџџџџџџџџџџќџџџџџџџџџџџџџџџџџџќџџџџџџџџџџџџџџџџџџќР Р Р Р Р Р Р Р Р Р Р Р Р Р Р Р Р Р Р Р Р Р Р Р Р Р Р Р Р Р Р Р Р Р Р Р Р Р Р Р Р Р Р Р Р Р џџџџџџџџџџџџџџџџџџќџџџџџџџџџџџџџџџџџџќ {lispcode (CREATEMENUEDWINDOW (create MENU ITEMS _ '(smaller LARGER) MENUFONT _ '(MODERN 12) TITLE _ "zoom controls" CENTERFLG _ T WHENSELECTEDFN _ (FUNCTION ZOOMMAINWINDOW))))} creates the same sort of window in one step, prompting the user for a region. }{End SubSec Attaching Menus To Windows} {Begin SubSec Attached Prompt Windows} {Title Attached Prompt Windows} {Text Many packages have a need to display status information or prompt for small amounts of user input in a place outside their standard window. A convenient way to do this is to attach a small window to the top of the program's main window. The following functions do so in a uniform way that can be depended on among diverse applications. {FnDef {Name GETPROMPTWINDOW} {Args MAINWINDOW #LINES FONT DONTCREATE} {Text Returns the attached prompt window associated with {arg MAINWINDOW}, creating it if necessary. The window is always attached to the top of {arg MAINWINDOW}, has {lisp DSPSCROLL} set to {lisp T}, and has a {lisp PAGEFULLFN} of {fn NILL} to inhibit page holding. The window is at least {arg #LINES} lines high (default 1); if a pre-existing window is shorter than that, it is reshaped to make it large enough. {arg FONT} is the font to give the prompt window (defaults to the font of {arg MAINWINDOW}), and applies only when the window is first created. If {arg DONTCREATE} is true, returns the window if it exists, otherwise {lisp NIL} without creating any prompt window. }} {FnDef {Name REMOVEPROMPTWINDOW} {Args MAINWINDOW} {Text Detaches the attached prompt window associated with {arg MAINWINDOW} (if any), and closes it. }} }{End SubSec Attached Prompt Windows} {Begin SubSec Window Operations And Attached Windows} {Title Window Operations And Attached Windows} {Text When a window operation, such as moving or clearing, is performed on a window, there is a question about whether or not that operation should also be performed on the windows attached to it or performed on the window it is attached to. The "right" thing to do depends on the window operation: it makes sense to independently redisplay a single window in a collection of windows, whereas moving a single window usually implies moving the whole group of windows. The interpretation of window operations also depends on the application that the window group is used for. For some applications, it may be desirable to have a window group where individual windows can be moved away from the group, but still be conceptually attached to the group for other operations. The attached window facility is flexible enough to allow all of these possibilities. The operation of window operations can be specified by each attached window, by setting the following two window properties: {Def {Name PASSTOMAINCOMS} {Type (Window Property)} {Text Value is a list of window commands (e.g. {lisp CLOSEW}, {lisp MOVEW}) which, when selected from the attached window's right-button menu, are actually applied to the central window in the group, instead of being applied to the attached window itself. The "central window" is the first window up the "main window" chain that is not attached to any other window. If {lisp PASSTOMAINCOMS} is {lisp NIL}, all window operations are directly applied to the attached window. If {lisp PASSTOMAINCOMS} is {lisp T}, all window operations are passed to the central window. Note: {fn ATTACHWINDOW} ({PageRef Fn ATTACHWINDOW}) allows this window property to be set to commonly-used values by using its {arg WINDOWCOMACTION} argument. {fn ATTACHWINDOW} always sets this window property, so users must modify it directly only {it after} attaching the window to another window. }} {Def {Name REJECTMAINCOMS} {Type (Window Property)} {Text Value is a list of window commands that the attached window will not allow the main window to apply to it. This is how a window can say "leave me out of this group operation." If {lisp REJECTMAINCOMS} is {lisp NIL}, all window commands may be applied to this attached window. If {lisp REJECTMAINCOMS} is {lisp T}, no window commands may be applied to this attached window. }} Note: The {lisp PASSTOMAINCOMS} and {lisp REJECTMAINCOMS} window properties affect right-button menu operations applied to main windows or attached windows, and the action of programmatic window functions ({fn SHAPEW}, {fn MOVEW}, etc.) applied to main windows. However, these window properties do {it not} affect the action of window functions applied to attached windows. The following list describes the behavior of main and attached windows under the window operations, assuming that all attached windows have their {lisp REJECTMAINCOMS} window property set to {lisp NIL} and {lisp PASSTOMAINCOMS} set to {lisp (CLOSEW MOVEW SHAPEW SHRINKW BURYW)} (the default if {fn ATTACHWINDOW} is called with {arg WINDOWCOMACTION}={lisp NIL}, see {PageRef Fn ATTACHWINDOW}). The behavior for any particular operation can be changed for particular attached windows by setting the standard window properties (e.g., {lisp MOVEFN} or {lisp CLOSEFN}) of the attached window. An exception is the {lisp TOTOPFN} property of an attached window, that is set to bring the whole window group to the top and should not be set by the user (although users can {it add} functions to the {lisp TOTOPFN} window property). {Begin Labeledlist} {Label Move} {Text If the main window moves, all attached windows move with it, and the relative positioning between the main window and the attached windows is maintained. If the region is determined interactively, the prompt region for the move is the union of the extent of the main window and all attached windows (excluding those with {lisp MOVEW} in their {lisp REJECTMAINCOMS} window property). If an attached window is moved by calling the function {fn MOVEW}, it is moved without affecting the main window. If the right-button window menu command {lisp Move} is called on an attached window, it is passed on to the main window, so that all windows in the group move. } {Label Reshape} {Text If the main window is reshaped, the minimum size of it and all of its attached windows is used as the minimum of the space for the result. Any space greater than the minimum is distributed among the main window and its attached windows. Attached windows with {lisp SHAPEW} on their {lisp REJECTMAINCOMS} window property are ignored when finding the minimum size, creating a "ghost" region, or distributing space after a reshape. If an attached window is reshaped by calling the function {fn SHAPEW}, it is reshaped independently. If the right-button window menu command {lisp Shape} is called on an attached window, it is passed on to the main window, so the whole group is reshaped. Note: Reshaping the main window will restore the conditions established by the call to {fn ATTACHWINDOW}, whereas moving the main window does not. Thus, if {lisp A} is attached to the top of {lisp B} and then moved by the user, its new position relative to {lisp B} will be maintained if {lisp B} is moved. If {lisp B} is reshaped, {lisp A} will be reshaped to the top of {lisp B}. Additionally, if, while {lisp A} is moved away from the top of {lisp B}, {lisp C} is attached to the top of {lisp B}, {lisp C} will position itself above where {lisp A} used to be. } {Label Close} {Text If the main window is closed, all of the attached windows are closed also and the links from the attached windows to the main window are broken. This is necessary for the windows to be garbage collected. If an attached window is closed by calling the function {fn CLOSEW}, it is closed without affecting the main window. If the right-button window menu command {lisp Close} is called on an attached window, it is passed on to the main window. Note that closing an attached window detaches it. } {Label Open} {Text If the main window is opened, it opens all attached windows and reestablishes links from them to the main window. Attached windows can be opened independently and this does not affect the main window. Note that it is possible to reopen a closed attached window and not have it linked to its main window. } {Label Shrink} {Text The collection of windows shrinks as a group. The {lisp SHRINKFN}s of the attached windows are evaluated but the only icon displayed is the one for the main window. } {Label Redisplay} {Text The main or attached windows can be redisplayed independently. } {Label Totop} {Text If any main or attached window is brought to the top, all of the other windows are brought to the top also. } {Label Expand} {Text Expanding any of the windows expands the whole collection. } {Label Scrolling} {Text All of the windows involved in the group scroll independently. } {Label Clear} {Text All windows clear independently of each other. } {End Labeledlist} }{End SubSec Window Operations And Attached Windows} {Begin SubSec Window Properties Of Attached Windows} {Title Window Properties Of Attached Windows} {Text Windows that are involved in a collection either as a main window or as an attached window have properties stored on them. The only properties that are intended to be set be set by the user are the {lisp MINSIZE}, {lisp MAXSIZE}, {lisp PASSTOMAINCOMS}, and {lisp REJECTMAINCOMS} window properties. The other properties should be considered read only. {Def {Type (Window Property)} {Name MINSIZE}} {Def {Type (Window Property)} {Name MAXSIZE} {Text Each of these window properties should be a dotted pair {lisp ({arg WIDTH} . {arg HEIGHT})} or a function to apply to the window that returns a dotted pair. The numbers are used when the main window is reshaped. The {lisp MINSIZE} is used to determine the size of the smallest region acceptable during reshaping. Any amount greater than the collective minimum is spread evenly among the windows until each reaches {lisp MAXSIZE}. Any excess is given to the main window. Note: If you give the main window of an attached window group a {lisp MINSIZE} or {lisp MAXSIZE} property, its value is moved to the {index MAINWINDOWMINSIZE (Window Property)}{lisp MAINWINDOWMINSIZE} or {index MAINWINDOWMAXSIZE (Window Property)}{lisp MAINWINDOWMAXSIZE} property, so that the main window can be given a size function that computes the minimum or maximum size of the entire group. Thus, if you want to change the main window's minimum or maximum size after attaching windows to it, you should change the {lisp MAINWINDOWMINSIZE} or {lisp MAINWINDOWMAXSIZE} property instead. Note: This doesn't address the hard problem of overlapping attached windows side to side, for example if window {lisp A} was attached as [{lisp TOP}, {lisp LEFT}] and {lisp B} as [{lisp TOP}, {lisp RIGHT}]. Currently, the attached window functions do not worry about the overlap. The default {lisp MAXSIZE} is {lisp NIL}, which will let the region grow indefinitely. }} {Def {Type (Window Property)} {Name MAINWINDOW} {Text Pointer from attached windows to the main window of the group. This link is not available if the main window is closed. The function {fn MAINWINDOW} ({PageRef Fn MAINWINDOW}) is the preferred way to access this property. }} {Def {Type (Window Property)} {Name ATTACHEDWINDOWS} {Text Pointer from a window to its attached windows. The function {fn ATTACHEDWINDOWS} ({PageRef Fn ATTACHEDWINDOWS}) is the preferred way to access this property. }} {Def {Type (Window Property)} {Name WHEREATTACHED} {Text For attached windows, a dotted pair {lisp ({arg EDGE} . {arg POSITIONONEDGE})} giving the edge and position on the edge that determine how the attached window is placed relative to its main window. }} The {lisp TOTOPFN} window property on attached windows and the properties {lisp TOTOPFN}, {lisp DOSHAPEFN}, {lisp MOVEFN}, {lisp CLOSEFN}, {lisp OPENFN}, {lisp SHRINKFN}, {lisp EXPANDFN} and {lisp CALCULATEREGIONFN} on main windows contain functions that implement the attached window manipulation facilities. Care should be used in modifying or replacing these properties. }{End SubSec Window Properties Of Attached Windows} }{End SubSec Attached Windows} ?1(DEFAULTFONT 1 (GACHA 10) (GACHA 8) (TERMINAL 8)) ?1(DEFAULTFONT 1 (GACHA 10) (GACHA 8) (TERMINAL 8)) К BMOBJ.GETFN29ц BMOBJ.GETFN2/‚e\zК