The class
interface
is the top level window class, which contains both menus and a hierarchy of panes and layouts. Interfaces can also themselves be contained within a layout, in which case they appear without their menu bar.
The title of the interface.
The layout of the interface.
A flag controlling the automatic addition of system menu objects.
A callback done on creating the window.
A callback done on closing the window.
A function to verify closing of the window.
The best x position for the interface.
The best y position for the interface.
The best width of the interface.
The best height of the interface.
A function called when the interface geometry changes.
A function called when the interface is activated or deactivated.
A function called when the interface is iconified or restored.
A cursor that takes precedence over the cursors of panes inside the interface.
A boolean determining whether the interface has a message area.
A boolean determining whether Pointer Documentation is enabled.
A boolean determining whether Tooltip Help is enabled.
A function called when a user gesture requests help.
A function called around the top level event handler.
A pane, a symbol naming a pane, or
nil
.
One of the keywords
:normal
,
:maximized
,
:iconic
and
:hidden
.
A real number in the inclusive range [0,1], used on Cocoa and later versions of Microsoft Windows.
interface-title
pane-layout
interface-menu-bar-items
interface-create-callback
interface-destroy-callback
interface-confirm-destroy-function
interface-geometry-change-callback
interface-activate-callback
interface-iconify-callback
interface-override-cursor
interface-message-area
interface-pointer-documentation-enabled
interface-tooltips-enabled
interface-help-callback
top-level-interface-external-border
top-level-interface-transparency
Every interface can have a title title which when it is a top level interface is shown as a title on its window, and when it is contained within another layout is displayed as a decoration (see the class titled-object for more details).
The argument
layout
specifies a layout object that contains the children of the interface. To change this layout you can either use the writer
pane-layout
, or you can use the layout switchable-layout which allows you to easily switch the currently visible child.
The argument menu-bar-items specifies a list of menus to appear on the interface's menu bar.
auto-menus
defaults to
t
, which means that an interface may have some automatic menus created by the environment in which it is running (for example the
Works
menu in the Common LispWorks environment). To switch these automatic menus off, pass
:auto-menus
nil
.
When you have an instance of an interface, you can display it either as an ordinary window or as a dialog using respectively display and display-dialog. The CAPI calls
create-callback
(if supplied) with the interface as its single argument, after all the widgets have been created but before the interface appears on screen. Then to remove the interface from the display, you use quit-interface and either exit-dialog or
abort-dialog respectively. When the interface is about to be closed, the CAPI calls the
confirm-destroy-function
(if there is one) with the interface, and if this function returns non-
nil
the interface is closed. Once the interface is closed, the
destroy-callback
is called with the interface.
Note: as well as create-callback , you can also add code to run just before or just after displaying the interface as an ordinary window by adding appropriate methods on interface-display.
The interface also accepts a number of hints as to the size and position of the interface for when it is first displayed. The arguments
best-x
and
best-y
must be the position as an integer or
nil
(meaning anywhere), while the arguments
best-width
and
best-height
can be any hints accepted by
:visible-max-width
and
:visible-max-height
for elements.
Whether or not an interface window is resizable is indicated as allowed by the window system. For non-resizable windows on Cocoa the interface window's maximize button is disabled and the resize indicator is not shown, and on Microsoft Windows the maximize box is disabled.
geometry-change-callback
may be
nil
, meaning there is no callback. This is the default value. Otherwise
geometry-change-callback
is a function of five arguments: the interface and the geometry. Its signature is:
geometry-change-callback interface x y width height
activate-callback
may be
nil
, meaning there is no callback. This is the default value. Otherwise
activate-callback
is a function of two arguments: the interface and a boolean
activatep
which is true on activation and false on deactivation. Its signature is:
activate-callback interface activatep
inconify-callback
may be
nil
, meaning there is no callback. This is the default value. Otherwise
inconify-callback
is a function of two arguments: the interface and a boolean
iconify
which is true when
interface
is iconified and and false when it is restored. Its signature is:
iconify-callback interface iconifyp
override-cursor
, if non-
nil
, specifies a cursor that is used instead of the cursor of each pane inside the interface. The default value of
override-cursor
is
nil
. See below for an example of setting and unsetting the override cursor.
If
message-area
is true, then the interface has a message area at the bottom. The text of the message area can be accessed using the titled-object accessor
titled-object-message
. The default value of
message-area
is
nil
.
enable-pointer-documentation
is a boolean controlling whether Pointer Documentation is enabled. The default value is
t
. The actual action is done by the
help-callback
.
enable-tooltips
is a boolean controlling whether Tooltip Help is enabled. The default value is
t
. The actual action is done by the
help-callback
.
help-callback
may be
nil
, meaning there is no callback. This is the default value. Otherwise
help-callback
is a function of four arguments: the interface, the pane inside interface where help is requested, the type of help requested, and the help key of the pane. Its signature is:
help-callback interface pane type help-key
The cursor entered the pane. The function should set the pointer documentation.
The cursor left the pane. The function needs to reset the pointer documentation.
A tooltip is requested. The function needs to return a string to display in the tooltip, or
nil
if no tooltip should be displayed.
The function should display a detailed, asynchronous help. This value is passed when the user presses the
F1
key (not implemented on Cocoa).
:help
is also passed when the user clicks the '?' box in the title bar of a Microsoft Windows dialog with window style
:contexthelp
(see
window-styles
below).
help-key
is the
help-key
of
pane
, as described in element. There is an example illustrating
help-callback
in
examples/capi/elements/help.lisp
and there is another example below.
top-level-hook
can be used on Microsoft Windows and Motif to specify a hook function that is called around the interface's top level event handler. The hook is passed two arguments: a continuation function (with no arguments) and the interface. The hook must call the continuation, which normally does not return.
top-level-hook
is designed especially for error handling (see below for an example). It can also be used for other purposes, for instance to bind special variables around the top level function.
:top-level-hook
is not supported on Cocoa.
external-border
controls how close to the edge of the screen the interface can be placed with explicit positioning using the
best-x
,
best-y
,
best-height
and
best-width
initargs or implicit positioning when a dialog is centered within its owner. The value
nil
allows the window to be anywhere, on or off the screen. The value 0 allows the window can be anywhere on the screen. If
external-border
is a positive integer then the window can be anywhere within
external-border
pixels from the edge of the screen. If
external-border
is a negative integer then the window be anywhere on the screen or up to
external-border
pixels off the edge of the screen. This does not affect whether the use can move the window after it has been displayed. It also does not affect the default positioning of interfaces, where the window system chooses the position.The default value of
external-border
is 0.
initial-focus specifies a pane which has the input focus when the interface is first displayed. See pane-initial-focus for more information about the initial focus pane.
display-state controls the initial display of the interface window, as described for top-level-interface-display-state.
transparency
is the overall transparency of the whole interface, where 0 is fully transparent and 1 is fully opaque. This has no effect on whether the user can click on the window. This is implemented for Cocoa and for Microsoft Windows, excluding Windows 98, Millennium Edition and NT 4.0.
:transparency
should only be used for top-level interfaces.
window-styles is a list of keywords controlling various aspects of the top level window's appearance and behavior. Each keyword is supported only on the Window systems explicitly mentioned below.
The following keywords apply to ordinary windows:
Cocoa: Programmatic changes to window geometry happen without animation.
Cocoa: The window is only visible when the application is the current application.
Microsoft Windows: The window is only visible when it is the active window.
Cocoa and Microsoft Windows: A window with a small title bar. This window style is used in docking-layout.
Cocoa, Microsoft Windows and Motif: A window with no external decoration or frame.
Cocoa and Motif: Remove the default border between the window's edge and its contents.
Cocoa, Microsoft Windows and Motif: The window cannot be minimized.
Cocoa and Microsoft Windows: The user can move the window by grabbing at any point not in an inner pane.
Cocoa: Force a shadow on windows with window style
:borderless
. (Other windows have a shadow by default.)
Windows XP (and later): The window has a shadow.
Cocoa: The window has no shadow.
Cocoa: The window has a textured background (like the Finder).
Cocoa and Microsoft Windows: The window is always above all other windows. Such a window is also known as a windoid.
Cocoa: The window cannot be given the focus for keyboard input.
Cocoa: The Special Characters... menu item is not inserted automatically. (This menu item is added to the Edit menu by default.)
Cocoa: output-panes in the window will see
:motion
input model events even if the output pane does not have the focus. This is the same behavior as on Microsoft Windows.
The following keywords are supported in window-styles when the interface is displayed as a dialog:
Microsoft Windows: The dialog has a border to allow resizing. (Generally Windows dialogs do not allowing resizing.)
Microsoft Windows: A '?' box appears in the window's title bar that sends
help-callback
type
:help
.
Note: even though
interface
is a subclass of titled-object, the accessor
titled-object-message-font
cannot be used to get and set the font of the interface's message.
interface-iconize-callback
is deprecated. Use the synonym
interface-iconify-callback
instead.
(capi:display (make-instance 'capi:interface
:title "Test Interface"))
(capi:display (make-instance
'capi:interface
:title "Test Interface"
:destroy-callback
#'(lambda (interface)
(capi:display-message
"Quitting ~S"
interface))))
(capi:display (make-instance
'capi:interface
:title "Test Interface"
:confirm-destroy-function
#'(lambda (interface)
(capi:confirm-yes-or-no
"Really quit ~S"
interface))))
(capi:display (make-instance
'capi:interface
:menu-bar-items
(list
(make-instance 'capi:menu
:title "Menu"
:items '(1 2 3)))
:title "Menu Test"))
(setq interface
(capi:display
(make-instance
'capi:interface
:title "Test Interface"
:layout
(make-instance 'capi:simple-layout
:description
(list (make-instance
'capi:text-input-pane
:text "Text Pane"))))))
(capi:execute-with-interface interface
#'(setf capi:pane-layout) (make-instance
'capi:simple-layout
:description
(list (make-instance
'capi:editor-pane
:text "Editor Pane")))
interface)
(capi:display
(make-instance
'capi:interface
:title "Test"
:best-x 200
:best-y 200
:best-width '(/ :screen-width 2)
:best-height 300))
The following forms illustrate the use of help-callback :
(capi:define-interface my-interface ()
()
(:panes
(a-pane
capi:text-input-pane
:help-key 'input)
(another-pane
capi:display-pane
:help-key 'output
:text "some text"))
(:menu-bar a-menu)
(:menus
(A-menu
"A menu"
(("An item" :help-key "item 1")
("Another item" :help-key "item 2"))
:help-key "a menu"))
(:layouts
(main-layout
capi:column-layout
'(a-pane another-pane)))
(:default-initargs
:help-callback 'my-help-callback
:message-area t))
(defun do-detailed-help (interface)
(capi:contain
(make-instance
'capi:display-pane
:text "Detailed help for my interface")
:title
(format nil "Help for ~a"
(capi:capi-object-name interface))))
(defun my-help-callback (interface pane type key)
(declare (ignore pane))
(case type
(:tooltip (if (eq key 'input)
"enter something"
(when (stringp key) key)))
(:pointer-documentation-enter
(when (stringp key)
(setf (capi:titled-object-message interface)
key)))
(:pointer-documentation-leave
(setf (capi:titled-object-message interface)
"Something else"))
(:help (do-detailed-help interface ))))
(capi:display
(make-instance 'my-interface :name "Helpful"))
The following forms illustrate the use of override-cursor to set and then remove an override cursor.
Create an interface with panes that have various different cursors. Move the pointer across each pane.
(setf interface
(capi:element-interface
(car
(capi:contain
(loop for cursor
in '(:crosshair :hand :v-double-arrow)
collect
(make-instance 'capi:editor-pane
:cursor cursor
:text
(format nil "~A CURSOR"
cursor)))))))
Override the pane cursors by setting the override cursor on the interface, and move the pointer across each pane again.
(setf (capi:interface-override-cursor interface)
:i-beam)
(setf (capi:interface-override-cursor interface)
:default)
This example illustrates
top-level-hook
. Evaluate this form and then get an error by
Meta+Control+C
(on Motif) or
Control+Break
(on Microsoft Windows) in the editor pane. Then select the Destroy Interface restart.
(capi:display
(capi:make-container
(make-instance
'capi:editor-pane)
:top-level-hook
#'(lambda (func interface)
(restart-case (funcall func)
(nil ()
:report
(list "Destroy Interface ~a" interface)
(capi:destroy interface))))))
This example illustrates the use of
:create-callback
:
(defun get-children (self)
(let (children)
(capi:map-pane-descendant-children
self #'(lambda (x)
(push x children)))
(with-slots (lp) self
(setf (capi:collection-items lp) children))))
(defun get-children-data (x)
(list (class-name (class-of x))
(format nil "~X" (sys:object-address x))))
(capi:define-interface created-data () ()
(:panes
(title
capi:title-pane
:text "A list populated via :CREATE-CALLBACK")
(lp
capi:multi-column-list-panel
:visible-min-height '(:character 3)
:column-function 'get-children-data))
(:layouts
(main
capi:column-layout
'(title lp)))
(:default-initargs
:create-callback 'get-children
:title ":CREATE-CALLBACK Example Interface"
:width 300))
(capi:display (make-instance 'created-data))
layout
switchable-layout
menu
display
display-dialog
interface-display
quit-interface
define-interface
activate-pane
titled-object