This example is a very simple demonstration of how to set up a cascading menu in Win32lib, and how to create secondary, or 'child' windows in a program. The parent window will allow you to open one of two secondary windows with slightly different styles. The cascading menu is contained within one of these secondary windows, and actually allows you to exit the whole program from within it's menu.
--
childwin.exw
-- Wolf/Jan.26/99
include win32lib.ew
without warning
constant
-- first, create the parent window, and it's menu.
ParentWin = create( Window, "Parent window", 0, 0, 0, 320, 110, 0 ),
List1 = create( List, "", ParentWin, 2, 2, 308, 60, 0 ),
ParentCloseMenu = create( Menu, "&Close", ParentWin, 0, 0, 0, 0, 0 ),
CloseParentMenu = create( MenuItem, "Parent window", ParentCloseMenu, 0, 0, 0, 0, 0 ),
ParentCreateMenu = create( Menu, "C&reate", ParentWin, 0, 0, 0, 0, 0 ),
CreateChildMenu = create( MenuItem, "&Child Window", ParentCreateMenu, 0, 0, 0, 0, 0 ),
CreateEntryMenu = create( MenuItem, "&Entry Window", ParentCreateMenu, 0, 0, 0, 0, 0 ),
-- then create the first secondary window, and it's menu.
ChildWin = create( Window, "Child window", ParentWin, 30, 30, 320, 100, {WS_CAPTION,WS_SYSMENU,WS_THICKFRAME} ),
ChildCloseMenu = create( Menu, "&Close", ChildWin, 0, 0, 0, 0, 0 ),
EitherMenu = create( Menu, "Either", ChildCloseMenu, 0, 0, 0, 0, 0 ),
-- here is our menu cascade. Note that they are both 'linked'
-- to EitherMenu, which is a Menu, NOT a MenuItem.
CloseChildMenu = create( MenuItem, "C&hild window,", EitherMenu, 0, 0, 0, 0, 0 ),
CloseBothMenu = create( MenuItem, "or &Parent + Child.", EitherMenu, 0, 0, 0, 0, 0 ),
-- here we create the second 'child', with buttons only.
EntryWindow = create( Window, "Entry Window", ChildWin, 30, 30, 402, 85, {#C40000} ),
Label1 = create( LText, "enter something!", EntryWindow, 1, 4, 110, 20, 0) ,
Entry1 = create( EditText, "", EntryWindow, 115, 2, 277, 20, 32 ),
btnAdd = create( PushButton,"Add to List", EntryWindow, 2, 28, 90, 25, 0 ),
btnQuit = create( PushButton, "QUIT", EntryWindow, 302, 28, 90, 25, 0 )
-- change the color of the second 'child', just to emphasize!
setWindowBackColor(EntryWindow, rgb(0,255,0))
-- this quits everything, since shutting down a parent
-- takes the children away too.
procedure onMenu_Exit( integer self, integer event, sequence params )
closeWindow(ParentWin)
end procedure
-- kill the first 'child'.
procedure onMenu_Exit_Child( integer self, integer event, sequence params )
closeWindow(ChildWindow)
end procedure
-- this procedure 'writes' our text to the 'child' window
-- every time it is 'opened'
procedure paint_child()
setPenPos(ChildWindow,0,0)
wPuts(ChildWindow,"this child is MODAL, without min/max buttons.")
setPenPos(ChildWindow,0,20)
wPuts(ChildWindow," ..just perfect for entry forms!")
end procedure
procedure show_child( integer self, integer event, sequence params)
openWindow(ChildWindow,Modal)
-- Modal, here, means you can't get back to the parent,
-- without closing the child.
paint_child()
end procedure
-- this opens the second child window.
procedure show_entry_form( integer self, integer event, sequence params)
openWindow(EntryWindow,Modal)
setFocus(Entry1)
end procedure
-- this adds the item from the entry form window,
-- to the list in the parent, and clears the entry sle
-- for new input.
procedure onClick_btnAdd( integer self, integer event, sequence params)
if length(getText(Entry1)) != 0 then -- anything there ?
addItem(List1,getText(Entry1)) -- if so, add it.
end if
setFocus(Entry1) -- go back to entry sle,
setText(Entry1,{}) -- and clear it.
end procedure
procedure onClick_btnQuit()
closeWindow(EntryWindow)
if getCount(List1) > 0 then -- is anything there ?
setIndex(List1,getCount(List1)) -- if so, focus on last item.
end if
setFocus(List1)
end procedure
The next three procedures add some keyboard handling routines to three of our 'control' windows. I should mention that most of the 'keyboard' values are now defined in Win32lib, so the numbers, ( 13, and 27 ), are actually equivalent to Win32lib's global constants VK_RETURN and VK_ESCAPE.
-- let the ENTER key work for all entry window items. !
procedure onKey_Entry1( integer self, integer event, sequence params)
integer key = params[1]
if key=13 then onClick_btnAdd( self, event, params )
elsif key=27 then onClick_btnQuit( self, event, params )
end if
end procedure
procedure onKey_btnAdd( integer self, integer event, sequence params)
integer key = params[1]
if key=13 then onClick_btnAdd( self, event, params ) else end if
end procedure
procedure onKey_btnQuit( integer self, integer event, sequence params)
integer key = params[1]
if key=13 then onClick_btnQuit( self, event, params ) else end if
end procedure
-- all the event handlers
setHandler( CloseParentMenu, w32HClick, routine_id("onMenu_Exit") )
setHandler( CreateChildMenu, w32HClick, routine_id("show_child") )
setHandler( CloseChildMenu, w32HClick, routine_id("onMenu_Exit_Child") )
setHandler( CloseBothMenu, w32HClick, routine_id("onMenu_Exit") )
setHandler( CreateEntryMenu, w32HClick, routine_id("show_entry_form") )
setHandler( btnAdd, w32HClick, routine_id("onClick_btnAdd") )
setHandler( btnQuit, w32HClick, routine_id("onClick_btnQuit") )
setHandler( Entry1, w32HKeyDown, routine_id("onKey_Entry1") )
setHandler( btnAdd, w32HKeyDown, routine_id("onKey_btnAdd") )
setHandler( btnQuit, w32HKeyDown, routine_id("onKey_btnQuit") )
WinMain( ParentWin,Normal )
-- end --
About Window Styles:
The last parameter in create(Window, ... can determine some of
the style attributes of the window.
The default style ( 0 ) is
already defined by Mr. Cuny in Win32lib.ew,s createWindow() procedure
as the following:
WS_OVERLAPPEDWINDOW = hex value #CF0000
or_all({ WS_OVERLAPPED, #000000
WS_CAPTION, #C00000 -- the title bar
WS_SYSMENU, #080000 -- 'menu' in icon
WS_THICKFRAME, #040000 -- a nice border
WS_MINIMIZEBOX, #020000 -- minimize button
WS_MAXIMIZEBOX}), #010000 -- maximize button
I have changed the default styles in the two
secondary windows to show some of the options you can use.
In the
first secondary window ( Child ), I have removed the
minimize/maximize buttons, since there is obviously no need for them.
The hexadecimal value is just the or_all() of the desired options. In
this case I have just removed WS_MINIMIZEBOX, and WS_MAXIMIZEBOX, to
get the value #CC0000.
In the secondary entry window I have also removed WS_SYSMENU, so there is no program icon in the caption bar, and therefore no active 'x' to exit button. This gave me the #C40000 value.
The *magic* number ( #C40000 ), can, obviously, just be replaced by calling the function:
or_all( {WS_CAPTION, WS_THICKFRAME} ),
as the last 'create' parameter.
You can play around with all the options listed in Win32lib.ew under -- Window Styles, to get whatever you might prefer. Just be careful with WS_DISABLED , as it does what it says ;-)
I should mention that some of these style
parameters are not necessarily *individual* style parameters. For
example:
... the WS_CAPTION style already includes the WS_BORDER
style,
... you cannot combine the WS_CHILD and WS_POPUP
styles,
... and, if you want to use WS_SYSMENU, you must use
WS_CAPTION as well.
You should also be aware that all these windows are created on startup, but only the primary window is shown at first. Try opening a secondary window, dragging it somewhere else, closing it, and then opening it again! Guess what, it re-appears where you left it, in spite of the 'location' variables in it's create() function.
... my little trick !
The entry window's SLE, of course, does NOT display what you have typed, displaying just asterisks ( *** ), instead, because of it's last create() attribute (ES_PASSWORD). More of these EditText control 'attributes' are described in the last "Addressbook" lesson further on.
... tidbits !
A 'control' is a window that can respond to the user in some fashion.
A 'window caption bar' is also often referred to as a 'titlebar'.
An 'EditText' control is often referred to as an SLE, or 'single-line-entry' window.
..end of lesson.
CONTENTS