From mboxrd@z Thu Jan 1 00:00:00 1970 Path: main.gmane.org!not-for-mail From: Miles Bader Newsgroups: gmane.emacs.devel Subject: reducing defface redundancy Date: 20 Apr 2002 12:12:57 +0900 Sender: emacs-devel-admin@gnu.org Message-ID: <877kn3qczq.fsf@tc-1-100.kawasaki.gol.ne.jp> Reply-To: Miles Bader NNTP-Posting-Host: localhost.gmane.org Mime-Version: 1.0 Content-Type: text/plain; charset=us-ascii X-Trace: main.gmane.org 1019272537 13467 127.0.0.1 (20 Apr 2002 03:15:37 GMT) X-Complaints-To: usenet@main.gmane.org NNTP-Posting-Date: Sat, 20 Apr 2002 03:15:37 +0000 (UTC) Return-path: Original-Received: from quimby.gnus.org ([80.91.224.244]) by main.gmane.org with esmtp (Exim 3.33 #1 (Debian)) id 16ylLd-0003V6-00 for ; Sat, 20 Apr 2002 05:15:37 +0200 Original-Received: from fencepost.gnu.org ([199.232.76.164]) by quimby.gnus.org with esmtp (Exim 3.12 #1 (Debian)) id 16ylfH-0001fi-00 for ; Sat, 20 Apr 2002 05:35:55 +0200 Original-Received: from localhost ([127.0.0.1] helo=fencepost.gnu.org) by fencepost.gnu.org with esmtp (Exim 3.34 #1 (Debian)) id 16ylLD-0003Dp-00; Fri, 19 Apr 2002 23:15:11 -0400 Original-Received: from smtp01.fields.gol.com ([203.216.5.131]) by fencepost.gnu.org with smtp (Exim 3.34 #1 (Debian)) id 16ylJh-00039z-00; Fri, 19 Apr 2002 23:13:37 -0400 Original-Received: from tc-2-213.kawasaki.gol.ne.jp ([203.216.25.213] helo=tc-1-100.kawasaki.gol.ne.jp) by smtp01.fields.gol.com with esmtp (Magnetic Fields) id 16ylJd-0003j7-00; Sat, 20 Apr 2002 12:13:35 +0900 Original-Received: by tc-1-100.kawasaki.gol.ne.jp (Postfix, from userid 1000) id BA4383075; Sat, 20 Apr 2002 12:12:57 +0900 (JST) Original-To: emacs-devel@gnu.org System-Type: i686-pc-linux-gnu Original-Lines: 87 X-Abuse-Complaints: abuse@gol.com Errors-To: emacs-devel-admin@gnu.org X-BeenThere: emacs-devel@gnu.org X-Mailman-Version: 2.0.9 Precedence: bulk List-Help: List-Post: List-Subscribe: , List-Id: Emacs development discussions. List-Unsubscribe: , List-Archive: Xref: main.gmane.org gmane.emacs.devel:2818 X-Report-Spam: http://spam.gmane.org/gmane.emacs.devel:2818 In order to be optimal on disparate display types, many defface clauses end up having a bunch of clauses with almost the same contents, but varying one or two attributes. With the ability to query individual features, this might become even worse. So this is a suggestion on a way to reduce the redundancy of defface specs. The basic idea is to allow using a lisp vector ([...]) as a kind of `or' expression in the attribute part of a defface clause. Each element of vector is an attribute list, and the first one that is entirely `supportable' (that is, `display-capable-p' returns true for all of its attributes) is used. [note that this is one reason why I suggested using face attribute names/values as the argument to `display-capable-p'] This way, in many cases common attributes could be factored out, and the variant parts would become just a vector of possibilities with emacs choosing the first one that works. I think this style is very natural, and might even result in better faces because Currently the grammar of defface specs is something like this: SPECS ::= (CLAUSE ...) CLAUSE ::= (TESTS ATTRIBUTE...) | (TESTS (ATTRIBUTE ...)) ; old style attribute list ATTRIBUTE ::= ATTR-NAME ATTR-VALUE TESTS ::= t | (TEST ...) TEST ::= (TEST-NAME TEST-ARG...) Here's one possibility for a more flexible specification that uses the `or' vector idea above, and I think should be backward compatible: SPECS ::= (CLAUSE ...) CLAUSE ::= ATTRIBUTE | (TESTS CLAUSE...) ; traditional top-level style | [SPECS ...] ; `or' vector style | (TESTS (ATTRIBUTE ...)) ; old style attribute list ATTRIBUTE ::= ATTR-NAME ATTR-VALUE TESTS ::= t | (TEST ...) TEST ::= (TEST-NAME TEST-ARG...) In addition to adding the `or' vectors, this makes defface specs recursive in a way that allows omitting the traditional clause list when it's not necessary (e.g., when currently you just have `t' as the list of tests). Thus _very_ simple defface specs are possible: (defface annoying '(:foreground "red" :background "yellow")) which seems very natural. The `italic' example from my earlier message can become: (defface italic [(:slant italic) (:underline t)]) And if someone wants a face that's both `emphasized' and yellow, he can do: (defface emph-yellow '(:foreground "yellow" [(:bold t) (:slant italic) (:underline t)])) which will make either a bold, italic, or underlined yellow face, depending on what the display is capable of. Since the new specification is recursive, it's possible to put normal defface clauses at sub-levels, if that's desirable for factoring out common attributes; for instance, this is often : (defface subtle-yet-underlined-mode-line '(:inherit mode-line :underline t (((background light) :background "grey90") ((background dark) :background "grey10")))) So what'ya think? It shouldn't be hard to implement, given the existance of `display-capable-p', it's backward-compatible, and whizzy as all hell (well, I think so anyway)... Thanks, -Miles -- "Most attacks seem to take place at night, during a rainstorm, uphill, where four map sheets join." -- Anon. British Officer in WW I