From mboxrd@z Thu Jan 1 00:00:00 1970 Path: news.gmane.org!not-for-mail From: Keith David Bershatsky Newsgroups: gmane.emacs.bugs Subject: bug#15189: 24.3.50; display-buffer does not work well with custom frames. Date: Wed, 28 Aug 2013 17:21:52 -0700 Message-ID: References: <521C4B77.80107@gmx.at> NNTP-Posting-Host: plane.gmane.org Mime-Version: 1.0 (Apple Message framework v1084) Content-Type: text/plain; charset=us-ascii Content-Transfer-Encoding: quoted-printable X-Trace: ger.gmane.org 1377735733 22376 80.91.229.3 (29 Aug 2013 00:22:13 GMT) X-Complaints-To: usenet@ger.gmane.org NNTP-Posting-Date: Thu, 29 Aug 2013 00:22:13 +0000 (UTC) Cc: 15189@debbugs.gnu.org To: martin rudalics Original-X-From: bug-gnu-emacs-bounces+geb-bug-gnu-emacs=m.gmane.org@gnu.org Thu Aug 29 02:22:16 2013 Return-path: Envelope-to: geb-bug-gnu-emacs@m.gmane.org Original-Received: from lists.gnu.org ([208.118.235.17]) by plane.gmane.org with esmtp (Exim 4.69) (envelope-from ) id 1VEq08-0006va-Ge for geb-bug-gnu-emacs@m.gmane.org; Thu, 29 Aug 2013 02:22:16 +0200 Original-Received: from localhost ([::1]:39186 helo=lists.gnu.org) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1VEq07-0006CY-T7 for geb-bug-gnu-emacs@m.gmane.org; Wed, 28 Aug 2013 20:22:15 -0400 Original-Received: from eggs.gnu.org ([2001:4830:134:3::10]:55647) by lists.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1VEpzz-0006BM-RM for bug-gnu-emacs@gnu.org; Wed, 28 Aug 2013 20:22:12 -0400 Original-Received: from Debian-exim by eggs.gnu.org with spam-scanned (Exim 4.71) (envelope-from ) id 1VEpzv-0002fv-33 for bug-gnu-emacs@gnu.org; Wed, 28 Aug 2013 20:22:07 -0400 Original-Received: from debbugs.gnu.org ([140.186.70.43]:40187) by eggs.gnu.org with esmtp (Exim 4.71) (envelope-from ) id 1VEpzu-0002fq-S5 for bug-gnu-emacs@gnu.org; Wed, 28 Aug 2013 20:22:03 -0400 Original-Received: from Debian-debbugs by debbugs.gnu.org with local (Exim 4.80) (envelope-from ) id 1VEpzu-0002W6-Bj for bug-gnu-emacs@gnu.org; Wed, 28 Aug 2013 20:22:02 -0400 X-Loop: help-debbugs@gnu.org Resent-From: Keith David Bershatsky Original-Sender: "Debbugs-submit" Resent-CC: bug-gnu-emacs@gnu.org Resent-Date: Thu, 29 Aug 2013 00:22:02 +0000 Resent-Message-ID: Resent-Sender: help-debbugs@gnu.org X-GNU-PR-Message: followup 15189 X-GNU-PR-Package: emacs X-GNU-PR-Keywords: Original-Received: via spool by 15189-submit@debbugs.gnu.org id=B15189.13777357209668 (code B ref 15189); Thu, 29 Aug 2013 00:22:02 +0000 Original-Received: (at 15189) by debbugs.gnu.org; 29 Aug 2013 00:22:00 +0000 Original-Received: from localhost ([127.0.0.1]:34503 helo=debbugs.gnu.org) by debbugs.gnu.org with esmtp (Exim 4.80) (envelope-from ) id 1VEpzr-0002Vq-BF for submit@debbugs.gnu.org; Wed, 28 Aug 2013 20:22:00 -0400 Original-Received: from cobb.liquidweb.com ([50.28.13.150]:56546) by debbugs.gnu.org with esmtp (Exim 4.80) (envelope-from ) id 1VEpzn-0002Vf-LN for 15189@debbugs.gnu.org; Wed, 28 Aug 2013 20:21:57 -0400 DKIM-Signature: v=1; a=rsa-sha256; q=dns/txt; c=relaxed/relaxed; d=lawlist.com; s=default; h=To:References:Message-Id:Content-Transfer-Encoding:Cc:Date:In-Reply-To:From:Content-Type:Mime-Version:Subject; bh=+joIX6wzXLa/BOWDxhAF8Ydd7z7IXK3Ol/5CYz74ih0=; b=D41RLB7ouwGsQQHr+MYzgn4+J+sfVoOOzYhcl2M7ATJBBYwI7al06XtzfHEX9v6/uCNOQN4SzrOSMz0mAqKW75OghcRqNKJD1s2+Guk53gzBGcIMAskCT5MtaXFxM/l0; Original-Received: from cpe-75-85-5-102.socal.res.rr.com ([75.85.5.102]:53947 helo=[192.168.0.3]) by cobb.liquidweb.com with esmtpa (Exim 4.80.1) (envelope-from ) id 1VEpzk-0000d7-CT; Wed, 28 Aug 2013 20:21:52 -0400 In-Reply-To: <521C4B77.80107@gmx.at> X-Mailer: Apple Mail (2.1084) X-AntiAbuse: This header was added to track abuse, please include it with any abuse report X-AntiAbuse: Primary Hostname - cobb.liquidweb.com X-AntiAbuse: Original Domain - debbugs.gnu.org X-AntiAbuse: Originator/Caller UID/GID - [47 12] / [47 12] X-AntiAbuse: Sender Address Domain - lawlist.com X-Get-Message-Sender-Via: cobb.liquidweb.com: authenticated_id: lawlist/from_h X-BeenThere: debbugs-submit@debbugs.gnu.org X-Mailman-Version: 2.1.15 Precedence: list X-detected-operating-system: by eggs.gnu.org: GNU/Linux 3.x X-Received-From: 140.186.70.43 X-BeenThere: bug-gnu-emacs@gnu.org List-Id: "Bug reports for GNU Emacs, the Swiss army knife of text editors" List-Unsubscribe: , List-Archive: List-Post: List-Help: List-Subscribe: , Errors-To: bug-gnu-emacs-bounces+geb-bug-gnu-emacs=m.gmane.org@gnu.org Original-Sender: bug-gnu-emacs-bounces+geb-bug-gnu-emacs=m.gmane.org@gnu.org Xref: news.gmane.org gmane.emacs.bugs:77790 Archived-At: Okay, I think I have a better understanding now of how display-buffer = works in conjunction with the display-buffer-alist. There just weren't = any really good examples on the internet or in the official = documentation from which to work from. I've updated my post on = stackoverflow.com, and that should help other novice programmers (like = myself) in the future who Google some of the relevant keywords. I = noticed quite a few comments on the internet about the display-buffer = family of functions being worthy of a doctoral thesis due to the level = of complexity. And with my legal background, I was beginning to think = that this project was similar to understanding the rule against = perpetuities -- something that all law school students fear will be = tested: http://en.wikipedia.org/wiki/Rule_against_perpetuities I recommend that the documentation be updated to include several working = examples of the display-buffer family of functions, which would help to = remove the mysticism surrounding the usage. The level of "perceived" = complexity would be significantly reduced once those working examples = become available. Thank you so much for teaching me a few new things about programming and = the display-buffer family. In case you or anyone else who has been reading these e-mail exchanges = is interested in the project I've been working on, I am resurrecting = Frame-Bufs written by Al Parker a few years ago and marrying it with = Tabbar. It's far from done, but it is working already and is coming = along quite nicely thanks to all the wonderful help from people like you = :) https://github.com/lawlist/tabbar-lawlist Thanks again, Keith ;;;;;;;;;;;;;;;;; DISPLAY-BUFFER-ALIST and DISPLAY-BUFFER = ;;;;;;;;;;;;;;;;;;;;;;;;;;; (defun example () (interactive) ;; condition # 3 | file-visiting buffer (lawlist-find-file "*bar*") (set-frame-height (selected-frame) 20) (set-frame-width (selected-frame) 80) (set-frame-position (selected-frame) 0 0) (message "\*bar\* appears in frame name SYSTEM.") (sit-for 3) ;; condition # 4(a) | no-file-visiting buffer (display-buffer (get-buffer-create "*NO-FILE-special-buffer-regexp*")) (message "NO-FILE buffer existing frame, without other windows.") (sit-for 3) ;; condition # 2(a) | file-visiting buffer (lawlist-find-file "foo.txt") (set-frame-height (selected-frame) 20) (set-frame-width (selected-frame) 80) (set-frame-position (selected-frame) 100 100) (message "\"foo.txt\" appears in frame name MAIN.") (sit-for 3) ;; condition # 1 | file-visiting buffer (lawlist-find-file "doe.org") (set-frame-height (selected-frame) 20) (set-frame-width (selected-frame) 80) (set-frame-position (selected-frame) 200 200) (message "\"doe.org\" appears in frame name ORG.") (sit-for 3) ;; condition # 4(b) | file-visiting buffer (lawlist-find-file "*FILE-special-buffer-regexp*") (message "FILE buffer existing frame, without other windows.") (sit-for 3) ;; condition # 6 | no-file-visiting buffer default display (calendar) (message "Default for no-file-visiting-buffers.") (sit-for 3) ;; condition # 5 | file-visiting buffer with no pre-defined regexp. (lawlist-find-file "*FILE-undefined-regexp*") (set-frame-height (selected-frame) 20) (set-frame-width (selected-frame) 80) (set-frame-position (selected-frame) 300 300) (message "\*IS\* buffer-filename. \*NOT\* defined by any particular = regexp.") (sit-for 3) ;; condition # 2(b) | no-file-visiting buffer (display-buffer (get-buffer-create "*NO-FILE-main-buffer-regexp*")) (set-frame-height (selected-frame) 20) (set-frame-width (selected-frame) 80) (set-frame-position (selected-frame) 400 400) (message "\*NOT\* buffer-filename. \*IS\* defined by = main-buffer-regexp.") (sit-for 3) (kill-buffer "*bar*") (kill-buffer "foo.txt") (kill-buffer "doe.org") (kill-buffer "*FILE-undefined-regexp*") (kill-buffer "*NO-FILE-main-buffer-regexp*") (kill-buffer "*Calendar*") (kill-buffer "*FILE-special-buffer-regexp*") (kill-buffer "*NO-FILE-special-buffer-regexp*") (make-frame) (delete-frame (get-frame "SYSTEM")) (delete-frame (get-frame "MAIN")) (delete-frame (get-frame "ORG")) (delete-frame (get-frame "MISCELLANEOUS")) (message "THE END.")) (defvar regexp-frame-names = "^\\(?:MAIN\\|SYSTEM\\|ORG\\|MISCELLANEOUS\\)$" "Regexp matching frames with specific names.") (defvar system-buffer-regexp nil "Regexp of file / buffer names displayed in frame `SYSTEM`.") (setq system-buffer-regexp '("*scratch*" "*bbdb*" "*bar*")) (defvar main-buffer-regexp nil "Regexp of file / buffer names displayed in frame `MAIN`.") (setq main-buffer-regexp '("\\.txt" "\\.tex" "\\.el" "\\.yasnippet" = "\\*NO-FILE-main-buffer-regexp\\*")) (defvar org-buffer-regexp nil "Regexp of file / buffer names displayed in frame `ORG`.") (setq org-buffer-regexp '("[*]TODO[*]" "[*]Org Agenda[*]" = "\\.org_archive" "\\.org")) (defvar special-buffer-regexp nil "Regexp of file / buffer names that will .") (setq special-buffer-regexp '("[*]NO-FILE-special-buffer-regexp[*]" = "*FILE-special-buffer-regexp*")) (defvar buffer-filename nil) (defun lawlist-find-file (&optional buffer-filename) "With assistance from the display-buffer-alist, locate or create a = specific frame, and then open the file." (interactive) (unless buffer-filename (setq buffer-filename (read-file-name "Select File: " "~/" nil nil nil nil))) ;; If using a version of Emacs built `--with-ns`, then user may = substitute: ;; (unless buffer-filename (setq buffer-filename ;; (ns-read-file-name "Select File:" "~/" t nil nil))) (if buffer-filename (display-buffer (find-file-noselect buffer-filename)))) (setq display-buffer-alist '((".*" . = (lawlist-display-buffer-pop-up-frame)))) (defun lawlist-display-buffer-pop-up-frame (buffer alist) (cond ;; condition # 1 -- either file-visiting or no-file buffers ((regexp-match-p org-buffer-regexp (buffer-name buffer)) (if (frame-exists "ORG") (switch-to-frame "ORG") ;; If unnamed frame exists, then take control of it. (catch 'break (dolist (frame (frame-list)) (if (not (string-match regexp-frame-names (frame-parameter = frame 'name))) (throw 'break (progn (switch-to-frame (frame-parameter frame 'name)) (set-frame-name "ORG")))))) ;; If dolist found no unnamed frame, then create / name it. (if (not (frame-exists "ORG")) (progn (make-frame) (set-frame-name "ORG"))) ) (if (and (featurep 'init-frames) frame-bufs-mode) (frame-bufs-add-buffer (get-buffer buffer) (selected-frame))) (set-window-buffer (frame-selected-window) (buffer-name buffer))) ;; condition # 2 -- either file-visiting or no-file buffers ((regexp-match-p main-buffer-regexp (buffer-name buffer)) (if (frame-exists "MAIN") (switch-to-frame "MAIN") ;; If unnamed frame exists, then take control of it. (catch 'break (dolist (frame (frame-list)) (if (not (string-match regexp-frame-names (frame-parameter = frame 'name))) (throw 'break (progn (switch-to-frame (frame-parameter frame 'name)) (set-frame-name "MAIN")))))) ;; If dolist found no unnamed frame, then create / name it. (if (not (frame-exists "MAIN")) (progn (make-frame) (set-frame-name "MAIN"))) ) (if (and (featurep 'init-frames) frame-bufs-mode) (frame-bufs-add-buffer (get-buffer buffer) (selected-frame))) (set-window-buffer (frame-selected-window) (buffer-name buffer))) ;; condition # 3 -- either file-visiting or no-file buffers ((regexp-match-p system-buffer-regexp (buffer-name buffer)) (if (frame-exists "SYSTEM") (switch-to-frame "SYSTEM") ;; If unnamed frame exists, then take control of it. (catch 'break (dolist (frame (frame-list)) (if (not (string-match regexp-frame-names (frame-parameter = frame 'name))) (throw 'break (progn (switch-to-frame (frame-parameter frame 'name)) (set-frame-name "SYSTEM")))))) ;; If dolist found no unnamed frame, then create / name it. (if (not (frame-exists "SYSTEM")) (progn (make-frame) (set-frame-name "SYSTEM"))) ) (if (and (featurep 'init-frames) frame-bufs-mode) (frame-bufs-add-buffer (get-buffer buffer) (selected-frame))) (set-window-buffer (frame-selected-window) (buffer-name buffer))) ;; condition # 4 ;; display buffer in the existing frame, without other windows ((regexp-match-p special-buffer-regexp (buffer-name buffer)) (if (and (featurep 'init-frames) frame-bufs-mode) (frame-bufs-add-buffer (get-buffer buffer) (selected-frame))) (set-window-buffer (frame-selected-window) (buffer-name buffer))) ;; condition # 5 ;; file-visiting buffers that do NOT match any pre-defined regexp ((and (not (regexp-match-p org-buffer-regexp (buffer-name buffer))) (not (regexp-match-p main-buffer-regexp (buffer-name buffer))) (not (regexp-match-p system-buffer-regexp (buffer-name = buffer))) (not (regexp-match-p special-buffer-regexp (buffer-name = buffer))) buffer-filename ) (if (frame-exists "MISCELLANEOUS") (switch-to-frame "MISCELLANEOUS") ;; If unnamed frame exists, then take control of it. (catch 'break (dolist (frame (frame-list)) (if (not (string-match regexp-frame-names (frame-parameter = frame 'name))) (throw 'break (progn (switch-to-frame (frame-parameter frame 'name)) (set-frame-name "MISCELLANEOUS")))))) ;; If dolist found no unnamed frame, then create / name it. (if (not (frame-exists "MISCELLANEOUS")) (progn (make-frame) (set-frame-name "MISCELLANEOUS")))) (if (and (featurep 'init-frames) frame-bufs-mode) (frame-bufs-add-buffer (get-buffer buffer) (selected-frame))) (set-window-buffer (frame-selected-window) (buffer-name buffer))) ;; condition # 6 ;; default display for no-file-visiting buffers (t nil) )) ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; GENERIC REGEXP FUNCTION = ;;;;;;;;;;;;;;;;;;;;;;;;;;;;; (defun regexp-match-p (regexps string) "Before the lisp function, define the variable like this:\n (defvar example-regexp nil \"Regexps matching `buffer-name buffer` for frame name `SYSTEM`.\") (setq example-regexp '(\"\\(\\*foo\\*\\|\\*bar\\*\\)\")) \nWithin the lisp function, use something like this:\n (regexp-match-p example-regexp (buffer-name buffer)) \nOr, this:\n (regexp-match-p example-regexp buffer-filename)" (catch 'matched (dolist (regexp regexps) (if (string-match regexp string) (throw 'matched t))))) ;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;;; GENERIC FRAME UTILITIES = ;;;;;;;;;;;;;;;;;;;;;;;;;;;; (defun frame-exists (frame-name) (not (eq nil (get-frame frame-name)))) (defun get-frame-name (&optional frame) "Return the string that names FRAME (a frame). Default is selected = frame." (unless frame (setq frame (selected-frame))) (if (framep frame) (cdr (assq 'name (frame-parameters frame))) (error "Function `get-frame-name': Argument not a frame: `%s'" = frame))) (defun get-frame (frame) "Return a frame, if any, named FRAME (a frame or a string). If none, return nil. If FRAME is a frame, it is returned." (cond ((framep frame) frame) ((stringp frame) (catch 'get-a-frame-found (dolist (fr (frame-list)) (when (string=3D frame (get-frame-name fr)) (throw 'get-a-frame-found fr))) nil)) (t (error "Function `get-frame-name': Arg neither a string nor a frame: = `%s'" frame)))) (defun switch-to-frame (frame-name) (let ((frames (frame-list))) (catch 'break (while frames (let ((frame (car frames))) (if (equal (frame-parameter frame 'name) frame-name) (throw 'break (select-frame-set-input-focus frame)) (setq frames (cdr frames)))))))) ;;;;;;;;;;;;;;;;;;;;;;;; IF BUILT --with-ns, THEN ALSO USE = ;;;;;;;;;;;;;;;;;;;;;;;;;; (defalias 'ns-find-file 'lawlist-ns-find-file) (defun lawlist-ns-find-file () "Do a `find-file' with the `ns-input-file' as argument." (interactive) (let* ((f (file-truename (expand-file-name (pop ns-input-file) command-line-default-directory))) (file (find-file-noselect f)) (bufwin1 (get-buffer-window file 'visible)) (bufwin2 (get-buffer-window "*scratch*" 'visible))) (cond (bufwin1 (select-frame (window-frame bufwin1)) (raise-frame (window-frame bufwin1)) (select-window bufwin1)) ((and (eq ns-pop-up-frames 'fresh) bufwin2) (ns-hide-emacs 'activate) (select-frame (window-frame bufwin2)) (raise-frame (window-frame bufwin2)) (select-window bufwin2) (lawlist-find-file f)) (t (ns-hide-emacs 'activate) (lawlist-find-file f)))))=