Prima::Window - top-level window management |
Prima::Window - top-level window management
Prima::Window is a descendant of Prima::Widget class. It deals with top-level windows, the windows that are specially treated by the system. Its major difference from Prima::Widget is that instances of Prima::Widget can never be clipped by anything but the screen, and that the system or window manager add decorations to these - usually menus, buttons and title bars. Prima::Window provides methods that communicate with the system and hint these decorations.
A typical program communicates with the user with aid of widgets, collected upon one or more top-level windows. Prima::Widget already has all functionality required for these child-parent operations, so Prima::Window is not special in respect of widget grouping and relationship. Its usage therefore is straightforward:
my $w = Prima::Window-> create( size => [300,300], text => 'Startup window', );
There are more about Prima::Window in areas, that it is specifically designed to - the system window management and the dialog execution.
As noted before, top-level windows are special for the system, not only in their 'look', but also in 'feel': the system adds specific functions to the windows, aiding the user to navigate through the desktop. The system ofter dictates the size and position for windows, and some time these rules are hard or even impossible to circumvent. It will be a long document, describing the features of different window management systems, and the task would be never accomplished - brand new window managers emerge every month, and the old change their behavior in an unpredictable way. The only golden rule is to never rely on the behavior of one window manager, and test programs with as many as possible.
The Prima toolkit provides simple access to buttons, title bar
and borders of a window. Buttons and title bar are managed by
the ::borderIcons
property, and borders by the ::borderStyle
property. These operate with set of predefined constants, bi::XXX
and bs::XXX
, correspondingly. The button constants can be combined with
each other, but not all combinations may be granted by the system.
The same is valid also for the border constant, except that they can
not be combined - the value of ::borderStyle
is one of the constants.
There are other hints, that the toolkit can specify for a window.
The system can be supplied with an icon that a window is bound to; the icon
dimensions are much different, and although can be requested via
sv::XIcon
and sv::YIcon
system values, the ::icon
property
scales the image automatically to the closest system-recognizable
dimension. The window icon is not shown by the toolkit, it is usually
resides in the window decorations and sometimes on a task bar, along
with the window's name. The system can be hinted to not reflect the window
on the task bar, by operating the ::taskListed
property.
Another issue is the window positioning. Usually, if no explicit
position was given, the window is positioned automatically
by the system. The same is valid for the size. But some window
managers bend it to the extreme - for example, default CDE
setup force the user to set newly created windows' positions explicitly.
But there is at least one point of certainty.
Typically, when the initial size and/or position of a top-level window
are expected to be set by the system, the ::originDontCare
and
::sizeDontCare
properties can be set to 1 during window creation.
If these set, the system is asked to size/position a window regarding
its own windowing policy. The reverse is not always true, unfortunately.
Either if these properties set to 0, or explicit size or positions are given,
the system is hinted to use these values instead, but this does not
always happen. Actually, this behavior is expected by the user and often does
not get even noticed as something special. Therefore it is a good practice to test
a top-level windowing code with several window managers.
There are different policies about window positioning and sizing;
some window managers behave best when the position is given to the window
with the system-dependent decorations. It is hardly can be called a good
policy, since it is not possible to calculate the derived window coordinates
with certainty. This problem results in that it is impossible to
be sure about window position and size before these are set explicitly.
The only, not much efficient help the toolkit can provide is the property
pair ::frameOrigin
and ::frameSize
, which along with ::origin
and ::size
reflect the position and size of a window, but taking into
account the system-dependent decorations.
Method of Prima::Window, execute()
brings a window
in a modal state on top of other toolkit windows, and
returns after the window is dismissed in one or another way.
This method is special as it is an implicit event loop,
similar to
run Prima;
code. The event flow is not disrupted, but the windows and widgets that do not belong to the currently executed, the 'modal' window group can not be activated. There can be many modal windows on top of each other, but only one is accessible. As an example a message box can be depicted, a window that prevents the user to work with the application windows until it is closed. There can be other message boxes on top of each other, preventing the lower window from operation as well. This is an exclusive modality.
The toolkit also provides the shared modality model, where
there can be several stacks of modal windows, not interfering
in operation. Each stack is exclusive for its own windows.
An example can be several independent applications with their
message boxes activated. This model, however, can not be achieved
with single execute()-like call without creating interlocking
conditions. The shared model call, execute_shared()
,
activates the window and returns immediately.
The both kinds of modal windows can coexist, but the exclusive windows prevents the shared from operation; while there are exclusive windows, the shared have same rights as the usual windows.
The stacking order for these two models is slightly different.
Any window, called execute()
is set on top of the last exclusive
modal window. The same is valid for the shared model, but since
there can be many shared window stacks, a window enters same stack
as of its owner. Here introduced the 'modal horizon'
term. A modal horizon is a root of the shared window stack,
and the default horizon is $::application's. The boolean ::modalHorizon
property is responsible whether the window serves as a horizon or not.
A window in modal state can return to its normal state by
calling end_modal()
method. The window is then set hidden and disabled,
and the windows below can be operated. If the window was in exclusive
modal state, the execute()
call finished and returns an exit code, which
can be set through ::modalResult
property. This property is an convenience
indicator of how the window was dismissed. There two methods, that
dismiss the window with returning two basic 'ok' and 'not ok' code.
These are ok()
and cancel()
methods; the latter is identical to
when the user closes the modal window by the means of the system.
The values set to ::modalResult
are mb::OK
and mb::Cancel
,
correspondingly. There are more mb::XXX
constants, but these represent
no special meaning; any integer value can be passed. Prima::MsgBox::message
method uses these so the message window can be dismissed in several ways.
A top-level window can be equipped with a menu bar. Its outlook
is system-dependent, but can be controlled by the toolkit up to
a certain level. The ::menuItems
property, that manages the menu items
of a ::menu
object of the Prima::Menu manpage class, arrange the layout
of the menu. The syntax of the items-derived properties is described in
the Prima::Menu manpage, but it must be reiterated that menu item records only
hint, not request their exact representation. The same is valid for
the color and font properties, ::menuColorIndex
and ::menuFont
.
Only one menu at a time can be set on a top-level window, although
a window can be owner for many menu objects. The key property is
Prima::Menu::selected
- if a menu object is selected on a widget
or a window object, it refers to default menu actions.
NB: A window can be owner for several menu objects and still do not have a menu bar, if no menu objects are marked as selected.
Prima::Dialog, a descendant from Prima::Window, introduces no new functionality. It has its default values adjusted so the colors use more appropriate system colors, and hints the system that the outlook of a window is to be different, and resemble the system dialogs - on systems where they are provided.
bi::XXX
constants.
The constants are:
bi::SystemMenu - system menu button and/or close button ( usually with icon ) is shown bi::Minimize - minimize button bi::Maximize - maximize ( and eventual restore ) bi::TitleBar - window title bi::All - all of the above
Not all systems respect these hints, and many systems provide more navigating decoration controls than these.
bs::XXX
constants. The constants are:
bs::None - no border bs::Single - thin border bs::Dialog - thick border bs::Sizeable - thick border with interactive resize capabilities
bs::Sizeable
is an unique window mode. If selected, the user
can resize the window, not only by dragging the window borders with
the mouse but by other system-dependent means. The other border styles
disallow interactive resizing.
Not all systems recognize all these hints, although many recognize interactive resizing flag.
undef
, the system-default icon is assumed.
See also: ownerIcon
::menu
property will be seen as a menu bar.
See also: Prima::Menu
, menuItems
ci::XXX
constants
( see the Prima::Widget manpage, colorIndex section ).
See also: menuItems
, menuFont
, menu
See also: menuItems
, menuColorIndex
, menuFont
, menu
See also: menuItems
, menuColorIndex
, menuFont
, menu
See also: menuItems
, menuColorIndex
, menuFont
, menu
See also: menuItems
, menuColorIndex
, menuFont
, menu
See also: menuItems
, menuColorIndex
, menuFont
, menu
See also: menuItems
, menuColorIndex
, menu
See also: menuItems
, menuColorIndex
, menuFont
, menu
See also: menuItems
, menuColorIndex
, menuFont
, menu
Prima::AbstractMenu::items
and is described in the Prima::Menu manpage.
See also: menu
, menuColorIndex
, menuFont
See also: menuItems
, menuColorIndex
, menuFont
, menu
::modalHorizon
set to 1
in shared modal state groups its children windows in a separate
hierarchy from other shared modal hierarchies. The ::modalHorizon
is therefore useful only when several shared modal window stacks
are needed.
The property also serves as an additional grouping factor for widgets and windows. For example, default keyboard navigation by tab and arrow keys is limited to the windows and widgets of a horizon.
execute()
.
Historically it is one of mb::XXX
constants, but any
integer value can be used. The most useful mb::
constants are:
mb::OK, mb::Ok mb::Cancel mb::Yes mb::No mb::Abort mb::Retry mb::Ignore mb::Help
NB: These constants are defined so they can be bitwise-or'ed,
and Prima::MsgBox package uses this feature, where one
of its functions parameters is a combination of mb::
constants.
::icon
property is explicitly set.
Default value is 1, so assigning an icon to $::application
spawns the icon to all windows.
Default value: 1
ws::XXX
constants:
ws::Normal ws::Minimized ws::Maximized
There can be more or less, or other window states
provided by the system, but these three were chosen as
a 'least common denominator'. The property can be changed
either by explicit set-mode call or by the user. In either case,
a WindowState
notification is triggered.
The property has three convenience wrappers: maximize()
,
minimize()
and restore()
.
See also: WindowState
mb::Cancel
result. The effect of calling this method is equal to when
the user selects a 'close window' action with system-provided
menu, button or other tool.
See also: ok
, modalResult
, execute
, execute_shared
EndModal
notification is activated.
Then the window is returned from the modal state,
gets hidden and disabled.
If the window was on top in the exclusive modal state,
the last called execute()
function finishes.
If the window was not on top in the exclusive modal state,
the corresponding execute()
function finishes after
all subsequent execute()
calls are finished.
Execute
notification is triggered.
The function is returned when a window is dismissed,
or if the system-dependent 'exit'-event is triggered by the
user ( the latter case falls through all execute()
calls
and terminates run Prima;
call, exiting gracefully).
::modalHorizon
. A window with ::modalHorizon
set to 1 starts its own stack, independent of all other
window stacks.
By default, if INSERT_BEFORE object is undef, the window is also put on top of other shared-modal windows in its stack. If INSERT_BEFORE is one of the shared-modal windows in its stack, the window is placed in queue before the INSERT_BEFORE window.
The window is showed and enabled, if necessary, and
Execute
notification is triggered.
The function is returned immediately.
mt::None mt::Shared mt::Exclusive
Value of mt::None
is 0, so result of get_modal()
can be
also treated as a boolean value, if only the fact of modality
is needed to check.
mt::Exclusive
or mt::Shared
. NEXT is a boolean flag, selecting
the lookup direction; if it is 1, the 'upper' window is returned,
if 0, the 'lower' one ( in a simple case when window A is made modal
(executed) after modal window B, the A window is the 'upper' one ).
If a window has no immediate modal relations, undef
is returned.
windowState(ws::Maximized)
.
windowState(ws::Minimized)
.
mb::OK
result. Typically the effect of calling this method is equal to when
the user presses the enter key of a modal window, signaling that
the default action is to be taken.
See also: cancel
, modalResult
, execute
, execute_shared
windowState(ws::Normal)
.
The toolkit does not provide standalone activation
functions; select()
call is used instead.
The toolkit does not provide standalone de-activation
functions; deselect()
call is used instead.
windowState()
call, or by the user.
STATE is the new window state, one of three ws::XXX
constants.
Dmitry Karasik, <dmitry@karasik.eu.org>.
Prima, the Prima::Object manpage, the Prima::Drawable manpage, the Prima::Widget manpage.
Prima::Window - top-level window management |