elisp: Recombining Windows

 
 27.8 Recombining Windows
 ========================
 
 When deleting the last sibling of a window W, its parent window is
 deleted too, with W replacing it in the window tree.  This means that W
 must be recombined with its parent’s siblings to form a new window
 combination (SeeWindows and Frames).  In some occasions, deleting a
 live window may even entail the deletion of two internal windows.
 
           ______________________________________
          | ______  ____________________________ |
          ||      || __________________________ ||
          ||      ||| ___________  ___________ |||
          ||      ||||           ||           ||||
          ||      ||||____W6_____||_____W7____||||
          ||      |||____________W4____________|||
          ||      || __________________________ ||
          ||      |||                          |||
          ||      |||                          |||
          ||      |||____________W5____________|||
          ||__W2__||_____________W3_____________ |
          |__________________W1__________________|
 
 
 Deleting W5 in this configuration normally causes the deletion of W3 and
 W4.  The remaining live windows W2, W6 and W7 are recombined to form a
 new horizontal combination with parent W1.
 
    Sometimes, however, it makes sense to not delete a parent window like
 W4.  In particular, a parent window should not be removed when it was
 used to preserve a combination embedded in a combination of the same
 type.  Such embeddings make sense to assure that when you split a window
 and subsequently delete the new window, Emacs reestablishes the layout
 of the associated frame as it existed before the splitting.
 
    Consider a scenario starting with two live windows W2 and W3 and
 their parent W1.
 
           ______________________________________
          | ____________________________________ |
          ||                                    ||
          ||                                    ||
          ||                                    ||
          ||                                    ||
          ||                                    ||
          ||                                    ||
          ||_________________W2_________________||
          | ____________________________________ |
          ||                                    ||
          ||                                    ||
          ||_________________W3_________________||
          |__________________W1__________________|
 
 
 Split W2 to make a new window W4 as follows.
 
           ______________________________________
          | ____________________________________ |
          ||                                    ||
          ||                                    ||
          ||_________________W2_________________||
          | ____________________________________ |
          ||                                    ||
          ||                                    ||
          ||_________________W4_________________||
          | ____________________________________ |
          ||                                    ||
          ||                                    ||
          ||_________________W3_________________||
          |__________________W1__________________|
 
 
 Now, when enlarging a window vertically, Emacs tries to obtain the
 corresponding space from its lower sibling, provided such a window
 exists.  In our scenario, enlarging W4 will steal space from W3.
 
           ______________________________________
          | ____________________________________ |
          ||                                    ||
          ||                                    ||
          ||_________________W2_________________||
          | ____________________________________ |
          ||                                    ||
          ||                                    ||
          ||                                    ||
          ||                                    ||
          ||_________________W4_________________||
          | ____________________________________ |
          ||_________________W3_________________||
          |__________________W1__________________|
 
 
 Deleting W4 will now give its entire space to W2, including the space
 earlier stolen from W3.
 
           ______________________________________
          | ____________________________________ |
          ||                                    ||
          ||                                    ||
          ||                                    ||
          ||                                    ||
          ||                                    ||
          ||                                    ||
          ||                                    ||
          ||                                    ||
          ||_________________W2_________________||
          | ____________________________________ |
          ||_________________W3_________________||
          |__________________W1__________________|
 
 
 This can be counterintuitive, in particular if W4 were used for
 displaying a buffer only temporarily (SeeTemporary Displays), and
 you want to continue working with the initial layout.
 
    The behavior can be fixed by making a new parent window when
 splitting W2.  The variable described next allows that to be done.
 
  -- User Option: window-combination-limit
      This variable controls whether splitting a window shall make a new
      parent window.  The following values are recognized:
 
      ‘nil’
           This means that the new live window is allowed to share the
           existing parent window, if one exists, provided the split
           occurs in the same direction as the existing window
           combination (otherwise, a new internal window is created
           anyway).
 
      ‘window-size’
           In this case ‘display-buffer’ makes a new parent window if it
           is passed a ‘window-height’ or ‘window-width’ entry in the
           ALIST argument (SeeDisplay Action Functions).
 
      ‘temp-buffer’
           This value causes the creation of a new parent window when a
           window is split for showing a temporary buffer (See
           Temporary Displays) only.
 
      ‘display-buffer’
           This means that when ‘display-buffer’ (SeeChoosing
           Window) splits a window it always makes a new parent window.
 
      ‘t’
           In this case a new parent window is always created when
           splitting a window.  Thus, if the value of this variable is at
           all times ‘t’, then at all times every window tree is a binary
           tree (a tree where each window except the root window has
           exactly one sibling).
 
      The default is ‘nil’.  Other values are reserved for future use.
 
      If, as a consequence of this variable’s setting, ‘split-window’
      makes a new parent window, it also calls
      ‘set-window-combination-limit’ (see below) on the newly-created
      internal window.  This affects how the window tree is rearranged
      when the child windows are deleted (see below).
 
    If ‘window-combination-limit’ is ‘t’, splitting W2 in the initial
 configuration of our scenario would have produced this:
 
           ______________________________________
          | ____________________________________ |
          || __________________________________ ||
          |||                                  |||
          |||________________W2________________|||
          || __________________________________ ||
          |||                                  |||
          |||________________W4________________|||
          ||_________________W5_________________||
          | ____________________________________ |
          ||                                    ||
          ||                                    ||
          ||_________________W3_________________||
          |__________________W1__________________|
 
 
 A new internal window W5 has been created; its children are W2 and the
 new live window W4.  Now, W2 is the only sibling of W4, so enlarging W4
 will try to shrink W2, leaving W3 unaffected.  Observe that W5
 represents a vertical combination of two windows embedded in the
 vertical combination W1.
 
  -- Function: set-window-combination-limit window limit
      This function sets the “combination limit” of the window WINDOW to
      LIMIT.  This value can be retrieved via the function
      ‘window-combination-limit’.  See below for its effects; note that
      it is only meaningful for internal windows.  The ‘split-window’
      function automatically calls this function, passing it ‘t’ as
      LIMIT, provided the value of the variable
      ‘window-combination-limit’ is ‘t’ when it is called.
 
  -- Function: window-combination-limit window
      This function returns the combination limit for WINDOW.
 
      The combination limit is meaningful only for an internal window.
      If it is ‘nil’, then Emacs is allowed to automatically delete
      WINDOW, in response to a window deletion, in order to group the
      child windows of WINDOW with its sibling windows to form a new
      window combination.  If the combination limit is ‘t’, the child
      windows of WINDOW are never automatically recombined with its
      siblings.
 
      If, in the configuration shown at the beginning of this section,
      the combination limit of W4 (the parent window of W6 and W7) is
      ‘t’, deleting W5 will not implicitly delete W4 too.
 
    Alternatively, the problems sketched above can be avoided by always
 resizing all windows in the same combination whenever one of its windows
 is split or deleted.  This also permits splitting windows that would be
 otherwise too small for such an operation.
 
  -- User Option: window-combination-resize
      If this variable is ‘nil’, ‘split-window’ can only split a window
      (denoted by WINDOW) if WINDOW’s screen area is large enough to
      accommodate both itself and the new window.
 
      If this variable is ‘t’, ‘split-window’ tries to resize all windows
      that are part of the same combination as WINDOW, in order to
      accommodate the new window.  In particular, this may allow
      ‘split-window’ to succeed even if WINDOW is a fixed-size window or
      too small to ordinarily split.  Furthermore, subsequently resizing
      or deleting WINDOW may resize all other windows in its combination.
 
      The default is ‘nil’.  Other values are reserved for future use.  A
      specific split operation may ignore the value of this variable if
      it is affected by a non-‘nil’ value of ‘window-combination-limit’.
 
    To illustrate the effect of ‘window-combination-resize’, consider the
 following frame layout.
 
           ______________________________________
          | ____________________________________ |
          ||                                    ||
          ||                                    ||
          ||                                    ||
          ||                                    ||
          ||_________________W2_________________||
          | ____________________________________ |
          ||                                    ||
          ||                                    ||
          ||                                    ||
          ||                                    ||
          ||_________________W3_________________||
          |__________________W1__________________|
 
 
 If ‘window-combination-resize’ is ‘nil’, splitting window W3 leaves the
 size of W2 unchanged:
 
           ______________________________________
          | ____________________________________ |
          ||                                    ||
          ||                                    ||
          ||                                    ||
          ||                                    ||
          ||_________________W2_________________||
          | ____________________________________ |
          ||                                    ||
          ||_________________W3_________________||
          | ____________________________________ |
          ||                                    ||
          ||_________________W4_________________||
          |__________________W1__________________|
 
 
 If ‘window-combination-resize’ is ‘t’, splitting W3 instead leaves all
 three live windows with approximately the same height:
 
           ______________________________________
          | ____________________________________ |
          ||                                    ||
          ||                                    ||
          ||_________________W2_________________||
          | ____________________________________ |
          ||                                    ||
          ||                                    ||
          ||_________________W3_________________||
          | ____________________________________ |
          ||                                    ||
          ||                                    ||
          ||_________________W4_________________||
          |__________________W1__________________|
 
 
 Deleting any of the live windows W2, W3 or W4 will distribute its space
 proportionally among the two remaining live windows.