From mboxrd@z Thu Jan 1 00:00:00 1970 Path: news.gmane.org!not-for-mail From: martin rudalics Newsgroups: gmane.emacs.bugs Subject: bug#3142: 23.0.92; split-window-prefered-function should be able to use split-window-horizontally/split-window-vertically Date: Tue, 05 May 2009 09:02:31 +0200 Message-ID: <49FFE487.5000106@gmx.at> References: <49F6A25B.3050108@gmx.at> <874ow84cp6.fsf_-_@mail.jurta.org> <49F7FE0F.1020107@gmx.at> Reply-To: martin rudalics , 3142@emacsbugs.donarmstrong.com NNTP-Posting-Host: lo.gmane.org Mime-Version: 1.0 Content-Type: multipart/mixed; boundary="------------050801000002030900000804" X-Trace: ger.gmane.org 1241508746 23066 80.91.229.12 (5 May 2009 07:32:26 GMT) X-Complaints-To: usenet@ger.gmane.org NNTP-Posting-Date: Tue, 5 May 2009 07:32:26 +0000 (UTC) Cc: 3142@emacsbugs.donarmstrong.com To: Stefan Monnier Original-X-From: bug-gnu-emacs-bounces+geb-bug-gnu-emacs=m.gmane.org@gnu.org Tue May 05 09:32:16 2009 Return-path: Envelope-to: geb-bug-gnu-emacs@m.gmane.org Original-Received: from lists.gnu.org ([199.232.76.165]) by lo.gmane.org with esmtp (Exim 4.50) id 1M1F8M-00068g-LI for geb-bug-gnu-emacs@m.gmane.org; Tue, 05 May 2009 09:32:16 +0200 Original-Received: from localhost ([127.0.0.1]:39589 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.43) id 1M1F8L-0002xl-F2 for geb-bug-gnu-emacs@m.gmane.org; Tue, 05 May 2009 03:32:09 -0400 Original-Received: from mailman by lists.gnu.org with tmda-scanned (Exim 4.43) id 1M1F8G-0002xg-AA for bug-gnu-emacs@gnu.org; Tue, 05 May 2009 03:32:04 -0400 Original-Received: from exim by lists.gnu.org with spam-scanned (Exim 4.43) id 1M1F8B-0002xK-F3 for bug-gnu-emacs@gnu.org; Tue, 05 May 2009 03:32:03 -0400 Original-Received: from [199.232.76.173] (port=59194 helo=monty-python.gnu.org) by lists.gnu.org with esmtp (Exim 4.43) id 1M1F8B-0002xH-6M for bug-gnu-emacs@gnu.org; Tue, 05 May 2009 03:31:59 -0400 Original-Received: from mx20.gnu.org ([199.232.41.8]:24604) by monty-python.gnu.org with esmtps (TLS-1.0:RSA_AES_256_CBC_SHA1:32) (Exim 4.60) (envelope-from ) id 1M1F8A-00036p-FH for bug-gnu-emacs@gnu.org; Tue, 05 May 2009 03:31:58 -0400 Original-Received: from rzlab.ucr.edu ([138.23.92.77]) by mx20.gnu.org with esmtp (Exim 4.60) (envelope-from ) id 1M1F87-0001s6-Ge for bug-gnu-emacs@gnu.org; Tue, 05 May 2009 03:31:56 -0400 Original-Received: from rzlab.ucr.edu (rzlab.ucr.edu [127.0.0.1]) by rzlab.ucr.edu (8.13.8/8.13.8/Debian-3) with ESMTP id n457VrM6019822; Tue, 5 May 2009 00:31:53 -0700 Original-Received: (from debbugs@localhost) by rzlab.ucr.edu (8.13.8/8.13.8/Submit) id n457F5u1014668; Tue, 5 May 2009 00:15:05 -0700 X-Loop: owner@emacsbugs.donarmstrong.com Resent-From: martin rudalics Resent-To: bug-submit-list@donarmstrong.com Resent-CC: Emacs Bugs Resent-Date: Tue, 05 May 2009 07:15:04 +0000 Resent-Message-ID: Resent-Sender: owner@emacsbugs.donarmstrong.com X-Emacs-PR-Message: followup 3142 X-Emacs-PR-Package: emacs X-Emacs-PR-Keywords: Original-Received: via spool by 3142-submit@emacsbugs.donarmstrong.com id=B3142.124150725313183 (code B ref 3142); Tue, 05 May 2009 07:15:04 +0000 Original-Received: (at 3142) by emacsbugs.donarmstrong.com; 5 May 2009 07:07:33 +0000 X-Spam-Bayes: score:0.5 Bayes not run. spammytokens:Tokens not available. hammytokens:Tokens not available. Original-Received: from mail.gmx.net (mail.gmx.net [213.165.64.20]) by rzlab.ucr.edu (8.13.8/8.13.8/Debian-3) with SMTP id n4577P2X013167 for <3142@emacsbugs.donarmstrong.com>; Tue, 5 May 2009 00:07:27 -0700 Original-Received: (qmail invoked by alias); 05 May 2009 07:07:19 -0000 Original-Received: from 62-47-49-59.adsl.highway.telekom.at (EHLO [62.47.49.59]) [62.47.49.59] by mail.gmx.net (mp040) with SMTP; 05 May 2009 09:07:19 +0200 X-Authenticated: #14592706 X-Provags-ID: V01U2FsdGVkX18jlH4B8iojiGUjRsIh4yUxyNWQhUwDLxA+WVKKpY G3crPEP0aiF3yr User-Agent: Thunderbird 2.0.0.16 (Windows/20080708) In-Reply-To: X-Y-GMX-Trusted: 0 X-FuHaFi: 0.68,0.51 X-Detected-Operating-System: by mx20.gnu.org: GNU/Linux 2.6 (newer, 3) X-detected-operating-system: by monty-python.gnu.org: Genre and OS details not recognized. Resent-Date: Tue, 05 May 2009 03:32:03 -0400 X-BeenThere: bug-gnu-emacs@gnu.org X-Mailman-Version: 2.1.5 Precedence: list List-Id: "Bug reports for GNU Emacs, the Swiss army knife of text editors" List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Original-Sender: bug-gnu-emacs-bounces+geb-bug-gnu-emacs=m.gmane.org@gnu.org Errors-To: bug-gnu-emacs-bounces+geb-bug-gnu-emacs=m.gmane.org@gnu.org Xref: news.gmane.org gmane.emacs.bugs:27709 Archived-At: This is a multi-part message in MIME format. --------------050801000002030900000804 Content-Type: text/plain; charset=ISO-8859-1; format=flowed Content-Transfer-Encoding: 7bit >> Remains the question whether `split-window-preferred-function' should >> always operate on the selected window or have a window argument. AFAICT >> nothing speaks for the window argument but the fact that people may have >> customized this already. Omitting the window argument would allow users >> to put `split-window-vertically' directly as value of >> `split-window-preferred-function' without having to delve any deeper. > > I agree it would make sense to operate on the selected-window rather > than pass an explicit window argument. Unfortunately, this will create the following problem: Suppose a user wants to (1) always split the selected window instead of the largest or LRU one, (2) never split the selected window (as Drew points out in another thread), or (3) base her decision on whether a window shall be split on which window was selected at the time `display-buffer' was called. In any of these cases calling `split-window-preferred-function' with the window to split selected will obscure the identity of the selected window and make the desired customization impossible. So we should probably leave the current behavior alone. The attached patch just makes sure that `split-window-preferred-function' gets always called and provides the standard options requested earlier. martin --------------050801000002030900000804 Content-Type: text/plain; name="window.el.diff" Content-Transfer-Encoding: 7bit Content-Disposition: inline; filename="window.el.diff" *** window.el.~1.179.~ 2009-04-29 07:50:42.078125000 +0200 --- window.el 2009-05-05 08:46:08.390625000 +0200 *************** *** 794,832 **** :type 'boolean :group 'windows) (defcustom split-height-threshold 80 "Minimum height of window to be split vertically. ! If the value is a number, `display-buffer' can split a window ! only if it has at least as many lines. If the value is nil, ! `display-buffer' cannot split a window vertically. ! ! If the window is the only window on its frame, `display-buffer' ! can split it regardless of this value." :type '(choice (const nil) (number :tag "lines")) :version "23.1" :group 'windows) (defcustom split-width-threshold 160 "Minimum width of window to be split horizontally. ! If the value is a number, `display-buffer' can split a window ! only if it has at least as many columns. If the value is nil, ! `display-buffer' cannot split a window horizontally." :type '(choice (const nil) (number :tag "columns")) :version "23.1" :group 'windows) - (defcustom split-window-preferred-function nil - "Function used by `display-buffer' to split windows. - If non-nil, a function called with a window as single argument - supposed to split that window and return the new window. If the - function returns nil the window is not split. - - If nil, `display-buffer' will split the window respecting the - values of `split-height-threshold' and `split-width-threshold'." - :type '(choice (const nil) (function :tag "Function")) - :version "23.1" - :group 'windows) - (defun window--splittable-p (window &optional horizontal) "Return non-nil if WINDOW can be split evenly. Optional argument HORIZONTAL non-nil means check whether WINDOW --- 794,865 ---- :type 'boolean :group 'windows) + (defcustom split-window-preferred-function 'split-window-sensibly + "Function called by `display-buffer' to split a window. + The function is called with a window as single argument and is + supposed to either split that window and return the new window or + return nil if the window can (or shall) not be split. + + The default is to split the window \"sensibly\". This calls the + function `split-window-sensibly' which tries to split the window + in a way which seems most suitable. A second standard option is + \"vertically\" to split the window into two windows one above the + other. The third standard option is \"horizontally\" which tries + to split the window into two windows side by side. All three + standard options examine the values of `split-height-threshold' + and/or `split-width-threshold' before they apply the split. + + If you set this to any other function, bear in mind that it may + be called two times: The argument of the first call is the + largest window on its frame. If that call fails to provide a + suitable window, it gets called again with the least recently + used window as argument. If neither of these calls produces a + suitable window, `display-buffer' will use an existing one to + display its buffer. + + The window selected at the time `display-buffer' was invoked is + selected when `split-window-preferred-function' gets called. + Hence you can compare WINDOW with the value of `selected-window' + if you always want to split the selected window instead of WINDOW + or if you never want to split the currently selected window." + :type '(choice + (const :tag "sensibly" split-window-sensibly) + (const :tag "vertically" + (lambda (window) + (when (window--splittable-p window) + (with-selected-window window + (split-window-vertically))))) + (const :tag "horizontally" + (lambda (window) + (when (window--splittable-p window t) + (with-selected-window window + (split-window-horizontally))))) + (function :tag "Function")) + :version "23.1" + :group 'windows) + (defcustom split-height-threshold 80 "Minimum height of window to be split vertically. ! If the value is a number, the standard functions specified for ! `split-window-preferred-function' are allowed to split a window ! vertically only if it has at least this many lines. If the value ! is nil, they do not split a window vertically. If a window is ! the only window on its frame, they can split it disregarding the ! value of this variable." :type '(choice (const nil) (number :tag "lines")) :version "23.1" :group 'windows) (defcustom split-width-threshold 160 "Minimum width of window to be split horizontally. ! If the value is a number, the standard functions specified for ! `split-window-preferred-function' are allowed to split a window ! horizontally only if it has at least this many columns. If the ! value is nil, they do not split a window horizontally." :type '(choice (const nil) (number :tag "columns")) :version "23.1" :group 'windows) (defun window--splittable-p (window &optional horizontal) "Return non-nil if WINDOW can be split evenly. Optional argument HORIZONTAL non-nil means check whether WINDOW *************** *** 882,911 **** (* 2 (max window-min-height (if mode-line-format 2 1)))))))))) (defun window--try-to-split-window (window) ! "Split WINDOW if it is splittable. ! See `window--splittable-p' for how to determine whether a window ! is splittable. If WINDOW can be split, return the value returned ! by `split-window' (or `split-window-preferred-function')." ! (when (and (window-live-p window) ! (not (frame-parameter (window-frame window) 'unsplittable))) ! (if (functionp split-window-preferred-function) ! ;; `split-window-preferred-function' is specified, so use it. ! (funcall split-window-preferred-function window) ! (or (and (window--splittable-p window) ! ;; Split window vertically. ! (split-window window)) ! (and (window--splittable-p window t) ! ;; Split window horizontally. ! (split-window window nil t)) ! (and (eq window (frame-root-window (window-frame window))) ! (not (window-minibuffer-p window)) ! ;; If WINDOW is the only window on its frame and not the ! ;; minibuffer window, attempt to split it vertically ! ;; disregarding the value of `split-height-threshold'. ! (let ((split-height-threshold 0)) ! (and (window--splittable-p window) ! (split-window window)))))))) (defun window--frame-usable-p (frame) "Return FRAME if it can be used to display a buffer." --- 915,964 ---- (* 2 (max window-min-height (if mode-line-format 2 1)))))))))) + (defun split-window-sensibly (window) + "Split WINDOW \"sensibly\". + If WINDOW has at least `split-height-threshold' lines, split it + into two windows one above the other and return the lower one. + Otherwise, if WINDOW is at least `split-width-threshold' columns + wide, split it into two windows side by side and return the one + on the right. If this does not produce a suitable window either + and WINDOW is the only window on its frame, try to split WINDOW + vertically and return the lower one. Return nil if that fails as + well. + + The default value of `split-window-preferred-function' is set to + this function." + (or (and (window--splittable-p window) + ;; Split window vertically. + (with-selected-window window + (split-window-vertically))) + (and (window--splittable-p window t) + ;; Split window horizontally. + (with-selected-window window + (split-window-horizontally))) + (and (eq window (frame-root-window (window-frame window))) + (not (window-minibuffer-p window)) + ;; If WINDOW is the only window on its frame and is not the + ;; minibuffer window, try to split it vertically disregarding + ;; the value of `split-height-threshold'. + (let ((split-height-threshold 0)) + (when (window--splittable-p window) + (with-selected-window window + (split-window-vertically))))))) + (defun window--try-to-split-window (window) ! "Split WINDOW if it can be split. ! Return value returned by `split-window-preferred-function' if it ! represents a live window, nil otherwise." ! (and (window-live-p window) ! (not (frame-parameter (window-frame window) 'unsplittable)) ! (let ((new-window ! ;; Since `split-window-preferred-function' might ! ;; throw an error use `condition-case'. ! (condition-case nil ! (funcall split-window-preferred-function window) ! (error nil)))) ! (and (window-live-p new-window) new-window)))) (defun window--frame-usable-p (frame) "Return FRAME if it can be used to display a buffer." --------------050801000002030900000804--