tips:revmedia:v4i10a11

Overlapping Windows And Window Menus

Published ByDateVersionKnowledge LevelKeywords
Sprezzatura Ltd01 APR 19933.0+EXPERTWINDOW, MENU, OVERLAY

With the new functionality in 3.x of being able to attach a CUA compliant menu to each window individually, a whole new world opened up for lovers of overlapping windows! For those unaccustomed to such delights, imagine having a very large window, elements of which are only used occasionally. Thanks to the kindly auspices of VSPACE, one could just paint everything onto the one window and allow the user to pan to the bits they required. This works, but has the major disadvantage that ALL of the window is calculated before it is displayed, which makes window refresh that much slower.

A better way is to overlay onto the main screen smaller subsets of the main data record in small windows. These overlays can be called from the window menu by a simple click with the mouse.

There are a number of problems associated with this technique, but the largest is convincing the window processor that the record it is trying to call up in the smaller window (which has, of course, the same id as the record displayed in the main window), is not locked. The steps in achieving this can best be described as

  • Make the sub-windows non-locking
  • Pass the record back and forwards in labelled common, ensuring that the integrity of data at different window levels is maintained
  • Update the labelled common areas with replace read/write processes

Remember of course, that the same technique might be used in multiple overlapping windows, so some way of keeping individual records separate must be incorporated. Rather than explain the process in depth, the code below shows just how this would be done. Note that the code is only installed in a Post Init hook on the window and from thereon in it installs itself.

From within the commuter program called by the menu, the labelled common area would be loaded with the current record for the replace read process to pick up, the sub window would be called, and on return @Record would be updated from the labelled common area maintained by the replace write process on the sub window - i.e. (assuming that the labelled common area containing Record@ was declared earlier)

 Description:
   Record@(@Window.Level) = @Record
   Catalyst("W", "SKU_DESCRIPTION " : @Id)
   @Record = Record@(@Window.Level)
 Return
 Subroutine Overlay_Window(Branch)
  /*
   Author    AMcA
   Date      10th April 1993
   Purpose   Generic plug in for overlay windows
   Notes     The labelled common area Overlay is used to pass the record
             between screens. It has been dimensioned to 20 to permit up to
             20 overlapped levels of window.
  */

  $Insert SysInclude, Window_Common%
  Common /Overlay/ Record@(20)
  Declare Subroutine Msg

  Brnchs = "POST_INIT,REP_DEL,REP_QUERY,REP_READ,"
  Brnchs:= "REP_REFRESH,REP_WRITE"
  Locate Branch in Brnchs using ',' setting POS then
     On Pos GoSub POST_INIT,REP_DEL,REP_QUERY,REP_READ,REP_REFRESH,REP_WRITE
  End Else
   Msg('Invalid Branch of %1%|Passed to %2%','','',BRANCH:@FM:WC_TEMPLATE%)
  End
 Return

 Post_Init:
   /*
    Install the rep read/write/delete/refresh automatically. Note that for
    complete safety the program ought to check for pre-existing or
    duplicated processes so as not to overwrite them.
   */
   Wc_Reproc%<3> = "S":@Vm:OVERLAY_WINDOW,REP_READ"
   Wc_Reproc%<4> = "S":@Vm:"OVERLAY_WINDOW,REP_WRITE"
   Wc_Reproc%<5> = "S":@Vm:"OVERLAY_WINDOW,REP_DEL"
   Wc_Reproc%<6> = "S":@Vm:"OVERLAY_WINDOW,REP_QUERY"
   Wc_Reproc%<7> = "S":@Vm:"OVERLAY_WINDOW,REP_REFRESH"
 Return

 Rep_Del:
   /*
    Remove those fields from the record that are contained in the current
    screen page. This is because a delete in a subwindow ought not to delete
    the main record, rather just that data in the subwindow.

    Note, do not attempt to remove key elements as they will be field 0 and
    therefore delete the record in its entirety. The same obtains for
    symbolics.
   */


   For X = 2 To WC_W_Cnt%
    If WC_W%(X)<4> > 0 Then
     @Record<WC_W%(X)<4>> = ""
    End
   Next
   Record@(@Window.Level - 1)  = @Record
   /*
    Now close the window and return to the calling program
   */
   WC_Reset% = 6
 Return

 Rep_Query:
   /*
    Do whatever you want to here
   */
 Return

 Rep_Read:
   /*
    As the labelled common area was loaded at the previous window level,
    grab @Record from the array element one lower than the current window
    level
   */
   @Record = Record@(@Window.Level - 1)
   WC_Orec% = @Record
 Return

 Rep_Refresh:
   /*
    Quit the screen
   */
   WC_Reset% = 6
 Return

 Rep_Write:
   Record@(@Window.Level - 1) = @Record
   WC_Reset% = 6
 Return

(Volume 4, Issue 10, Pages 11-13)

  • tips/revmedia/v4i10a11.txt
  • Last modified: 2024/06/19 20:20
  • by 127.0.0.1