Merge from origin/emacs-27

a4e4510ccd Fix handling MS-Windows keyboard input above the BMP
a38bebb0c1 * etc/NEWS: More complete description of rx 'not' changes.
d373647e8f ; * doc/emacs/mini.texi (Yes or No Prompts): Fix last change.
1ca6d15656 * doc/emacs/mini.texi (Yes or No Prompts): 'y-or-n-p' now ...
fe1a447d52 Don't attempt to cache glyph metrics for FONT_INVALID_CODE
b42b894d1d Fix fit-frame-to-buffer for multi-monitor setup
366fd4fd07 (emacs-27) ; * etc/NEWS: Fix typo.
49d3cd90bd rx: Improve 'or' compositionality (bug#37659)
6b48aedb6b * lisp/tab-line.el: Fix auto-hscrolling (bug#39649)
c5f255d681 (tag: emacs-27.0.90) ; Update lisp/ldefs-boot.el
60c84ad992 ; * etc/TODO: Fix last change.
5af9e5baad ; Add an entry to TODO
d424195905 Fix rx charset generation
9908b5a614 Merge branch 'emacs-27' of git.savannah.gnu.org:/srv/git/e...
6dc2ebe00e Fix overquoting in mule.el
5cca73dd82 * src/timefns.c (time_arith): Omit incorrect comment.
d767c357ca Merge branch 'emacs-27' of git.savannah.gnu.org:/srv/git/e...
4dec693f70 * lisp/vc/vc-cvs.el (vc-cvs-ignore): Copy-edit doc string
ff729e3f97 ; bug#39779: Fix some typos in documentation.
696ee02c3a checkdoc: Don't mistake "cf." for sentence end

# Conflicts:
#	etc/NEWS
This commit is contained in:
Glenn Morris 2020-03-04 13:57:58 -08:00
commit 6a0e1c4104
23 changed files with 291 additions and 115 deletions

View file

@ -813,35 +813,23 @@ varieties.
@cindex y or n prompt
For the first type of yes-or-no query, the prompt ends with
@samp{(y or n)}. Such a query does not actually use the minibuffer;
the prompt appears in the echo area, and you answer by typing either
@samp{y} or @samp{n}, which immediately delivers the response. For
example, if you type @kbd{C-x C-w} (@kbd{write-file}) to save a
buffer, and enter the name of an existing file, Emacs issues a prompt
like this:
@w{@samp{(y or n)}}. You answer the query by typing a single key,
either @samp{y} or @samp{n}, which immediately exits the minibuffer
and delivers the response. For example, if you type @kbd{C-x C-w}
(@kbd{write-file}) to save a buffer, and enter the name of an existing
file, Emacs issues a prompt like this:
@smallexample
File foo.el exists; overwrite? (y or n)
@end smallexample
@noindent
Because this query does not actually use the minibuffer, the usual
minibuffer editing commands cannot be used. However, you can perform
some window scrolling operations while the query is active: @kbd{C-l}
recenters the selected window; @kbd{C-v} (or @key{PageDown}, or
@key{next}) scrolls forward; @kbd{M-v} (or @key{PageUp}, or
@key{prior}) scrolls backward; @kbd{C-M-v} scrolls forward in the next
window; and @kbd{C-M-S-v} scrolls backward in the next window. Typing
@kbd{C-g} dismisses the query, and quits the command that issued it
(@pxref{Quitting}).
@cindex yes or no prompt
The second type of yes-or-no query is typically employed if
giving the wrong answer would have serious consequences; it uses the
minibuffer, and features a prompt ending with @samp{(yes or no)}. For
example, if you invoke @kbd{C-x k} (@code{kill-buffer}) on a
file-visiting buffer with unsaved changes, Emacs activates the
minibuffer with a prompt like this:
The second type of yes-or-no query is typically employed if giving
the wrong answer would have serious consequences; it thus features a
longer prompt ending with @samp{(yes or no)}. For example, if you
invoke @kbd{C-x k} (@code{kill-buffer}) on a file-visiting buffer with
unsaved changes, Emacs activates the minibuffer with a prompt like
this:
@smallexample
Buffer foo.el modified; kill anyway? (yes or no)
@ -849,7 +837,12 @@ Buffer foo.el modified; kill anyway? (yes or no)
@noindent
To answer, you must type @samp{yes} or @samp{no} into the minibuffer,
followed by @key{RET}. The minibuffer behaves as described in the
previous sections; you can switch to another window with @kbd{C-x o},
use the history commands @kbd{M-p} and @kbd{M-n}, etc. Type @kbd{C-g}
to quit the minibuffer and the querying command.
followed by @key{RET}.
With both types of yes-or-no query the minibuffer behaves as described
in the previous sections; you can recenter the selected window with
@kbd{C-l}, scroll that window (@kbd{C-v} or @kbd{PageDown} scrolls
forward, @kbd{M-v} or @kbd{PageUp} scrolls backward), switch to
another window with @kbd{C-x o}, use the history commands @kbd{M-p}
and @kbd{M-n}, etc. Type @kbd{C-g} to dismiss the query, and quit the
minibuffer and the querying command (@pxref{Quitting}).

View file

@ -3264,7 +3264,7 @@ that deletion fails for whatever reason, the child frame is made a
top-level frame.
Whether a child frame can have a menu or tool bar is window-system or
window manager dependent. Most window-systems explicitly disallow menus
window manager dependent. Most window-systems explicitly disallow menu
bars for child frames. It seems advisable to disable both, menu and
tool bars, via the frame's initial parameters settings.

View file

@ -1086,8 +1086,9 @@ Corresponding string regexp: @samp{@var{A}@var{B}@dots{}}
@itemx @code{(| @var{rx}@dots{})}
@cindex @code{|} in rx
Match exactly one of the @var{rx}s.
If all arguments are string literals, the longest possible match
will always be used. Otherwise, either the longest match or the
If all arguments are strings, characters, or @code{or} forms
so constrained, the longest possible match will always be used.
Otherwise, either the longest match or the
first (in left-to-right order) will be used.
Without arguments, the expression will not match anything at all.@*
Corresponding string regexp: @samp{@var{A}\|@var{B}\|@dots{}}.

View file

@ -1076,7 +1076,7 @@ package is only activated if all its dependencies have been).
Its format is a list of lists on a single line. The @code{car} of
each sub-list is the name of a package, as a symbol. The @code{cadr}
of each sub-list is the minimum acceptable version number, as a string
that can be parse by @code{version-to-list}. An entry that lacks a
that can be parsed by @code{version-to-list}. An entry that lacks a
version (i.e., an entry which is just a symbol, or a sub-list of one
element) is equivalent to entry with version "0". For instance:

View file

@ -858,7 +858,7 @@ is a buffer if the buffer-local value of the variable is being
changed, @code{nil} otherwise.
@end defun
@defun remove-variable-watch symbol watch-function
@defun remove-variable-watcher symbol watch-function
This function removes @var{watch-function} from @var{symbol}'s list of
watchers.
@end defun

View file

@ -3181,7 +3181,7 @@ For example:
(broken-reply-to . t))))
@end lisp
All clauses that matches the group name will be used, but the last
All clauses that match the group name will be used, but the last
setting ``wins''. So if you have two clauses that both match the
group name, and both set, say @code{display}, the last setting will
override the first.
@ -17874,7 +17874,7 @@ presence of 7 special headers. These headers are of the form
@code{X-Diary-<something>}, @code{<something>} being one of
@code{Minute}, @code{Hour}, @code{Dom}, @code{Month}, @code{Year},
@code{Time-Zone} and @code{Dow}. @code{Dom} means ``Day of Month'', and
@code{dow} means ``Day of Week''. These headers actually behave like
@code{Dow} means ``Day of Week''. These headers actually behave like
crontab specifications and define the event date(s):
@itemize @bullet
@ -30916,7 +30916,7 @@ description = <string>
Believe it or not, but some people who use Gnus haven't really used
Emacs much before they embarked on their journey on the Gnus Love Boat.
If you are one of those unfortunates whom ``@kbd{C-M-a}'', ``kill the
If you are one of those unfortunates to whom ``@kbd{C-M-a}'', ``kill the
region'', and ``set @code{gnus-flargblossen} to an alist where the key
is a regexp that is used for matching on the group name'' are magical
phrases with little or no meaning, then this appendix is for you. If

View file

@ -739,9 +739,9 @@ stepping, you will see where the loop starts and ends. Also, examine
the data being used in the loop and try to determine why the loop does
not exit when it should.
On GNU and Unix systems, you can also trying sending Emacs SIGUSR2,
On GNU and Unix systems, you can also try sending Emacs SIGUSR2,
which, if 'debug-on-event' has its default value, will cause Emacs to
attempt to break it out of its current loop and into the Lisp
attempt to break out of its current loop and enter the Lisp
debugger. (See the node "Debugging" in the ELisp manual for the
details about the Lisp debugger.) This feature is useful when a
C-level debugger is not conveniently available.

View file

@ -2323,7 +2323,16 @@ With 'or' and 'not', it can be used to compose character-matching
expressions from simpler parts.
+++
*** 'not' argument can now be a character or single-char string.
*** 'not' now accepts more argument types.
The argument can now also be a character, a single-character string,
an 'intersection' form, or an 'or' form whose arguments each match a
single character.
+++
*** Nested 'or' forms of strings guarantee a longest match.
For example, '(or (or "IN" "OUT") (or "INPUT" "OUTPUT"))' now matches
the whole string "INPUT" if present, not just "IN". Previously, this
was only guaranteed inside a single 'or' form of string literals.
** Frames

View file

@ -244,6 +244,23 @@ populate composition-function-table with those rules. See
composite.el for examples of this, and also grep lisp/language/*.el
for references to composition-function-table.
One problem with character compositions that will need to be solved is
that composition-function-table, the char-table which holds the
composition rules, is a global variable, whereas use of ligatures is
inherently specific to buffer-local stuff like the major mode and the
script or language in use. So there should be a buffer-local variable
to augment/customize/override the global composition rules.
Another problem is that ligatures are frequently composed of ASCII
characters, and some of those ASCII characters are present in the mode
line, for example "--". Since displaying a ligature instead of 2
separate '-' characters on a mode line is not right, there should be a
way of preventing the ligation from happening. One possibility is to
have a ZWNJ character separate these ASCII characters; another
possibility is to introduce a special text property that prevents
character composition, and place that property on the relevant parts
of the mode line.
The prettify-symbols-mode should be deprecated once ligature support
is in place.
@ -267,6 +284,60 @@ should invoke the 'shape' method. 'hbfont_shape' should be extended
to pass to 'hb_shape_full' the required array of features, as
mentioned in the above HarfBuzz discussion.
** Better support for displaying Emoji
Emacs is capable of displaying Emoji and some of the Emoji sequences,
provided that its fontsets are configured with a suitable font. To
make this easier out of the box, the following should be done:
*** Populate composition-function-table with Emoji rules
The Unicode Character Database (UCD) includes several data files that
define the valid Emoji sequences. These files should be imported into
the Emacs tree, and should be converted by some script at Emacs build
time to Lisp code that populates composition-function-table with the
corresponding composition rules.
*** Augment the default fontsets with Emoji-capable fonts
The default fontsets set up by fontest.el should include known free
fonts that provide good support for displaying Emoji sequences. In
addition, the rule that the default face's font is used for symbol and
punctuation characters, disregarding the fontsets, should be modified
to exempt Emoji from this rule (since Emoji characters belong to the
'symbol' script in Emacs), so that use-default-font-for-symbols would
not have to be tweaked to have Emoji display by default with a capable
font.
*** Consider changing the default display of Variation Selectors
Emacs by default displays the Variation Selector (VS) codepoints not
composed with base characters as hex codes in a box. The Unicode FAQ
says that if variation sequences cannot be supported, the VS
characters should not be shown, leaving just the base character of the
sequence visible. This could be handled via glyphless-char-display,
by changing the entries for VS codepoints to 'zero-width'. Or we
could display them as a thin 1-pixel space, as we do with format
control characters, by using 'thin-space' there.
*** Special face for displaying text presentation of Emoji
Emoji-capable fonts support Emoji sequences with the U+FE0F VARIATION
SELECTOR-16 (VS16) for emoji-style display, but usually don't support
the U+FE0F VARIATION SELECTOR-15 (VS15) for text-style display. There
are other fonts which support the text-style sequences, but not
emoji-style. Since Emacs selects a font based on a single character,
it cannot choose 2 different fonts for displaying both styles of the
same base character. To display both styles in the same buffer, one
could use a special face, placing a 'face' text property on portions
of the text. This special face could specify a specific font known to
support text-style Emoji sequences. Emacs could have such a face
built-in.
See the discussion of bug#39799 for more details about this task.
Another relevant resource is the Unicode Technical Standard #51
"Unicode Emoji" (http://www.unicode.org/reports/tr51/).
** Extend text-properties and overlays
*** Several text-property planes
This would get us rid of font-lock-face property (and I'd be happy to

View file

@ -2073,7 +2073,7 @@ If the offending word is in a piece of quoted text, then it is skipped."
;; piece of an abbreviation
;; FIXME etc
(looking-at
"\\([a-zA-Z]\\|[iI]\\.?e\\|[eE]\\.?g\\)\\."))
"\\([a-zA-Z]\\|[iI]\\.?e\\|[eE]\\.?g\\|[cC]f\\)\\."))
(error t))))
(if (checkdoc-autofix-ask-replace
b e

View file

@ -254,22 +254,39 @@ Left-fold the list L, starting with X, by the binary function F."
(setq l (cdr l)))
x)
(defun rx--normalise-or-arg (form)
"Normalise the `or' argument FORM.
Characters become strings, user-definitions and `eval' forms are expanded,
and `or' forms are normalised recursively."
(cond ((characterp form)
(char-to-string form))
((and (consp form) (memq (car form) '(or |)))
(cons (car form) (mapcar #'rx--normalise-or-arg (cdr form))))
((and (consp form) (eq (car form) 'eval))
(rx--normalise-or-arg (rx--expand-eval (cdr form))))
(t
(let ((expanded (rx--expand-def form)))
(if expanded
(rx--normalise-or-arg expanded)
form)))))
(defun rx--all-string-or-args (body)
"If BODY only consists of strings or such `or' forms, return all the strings.
Otherwise throw `rx--nonstring'."
(mapcan (lambda (form)
(cond ((stringp form) (list form))
((and (consp form) (memq (car form) '(or |)))
(rx--all-string-or-args (cdr form)))
(t (throw 'rx--nonstring nil))))
body))
(defun rx--translate-or (body)
"Translate an or-pattern of zero or more rx items.
Return (REGEXP . PRECEDENCE)."
;; FIXME: Possible improvements:
;;
;; - Turn single characters to strings: (or ?a ?b) -> (or "a" "b"),
;; so that they can be candidates for regexp-opt.
;;
;; - Translate compile-time strings (`eval' forms), again for regexp-opt.
;;
;; - Flatten sub-patterns first: (or (or A B) (or C D)) -> (or A B C D)
;; in order to improve effectiveness of regexp-opt.
;; This would also help composability.
;;
;; - Use associativity to run regexp-opt on contiguous subsets of arguments
;; if not all of them are strings. Example:
;; Then call regexp-opt on runs of string arguments. Example:
;; (or (+ digit) "CHARLIE" "CHAN" (+ blank))
;; -> (or (+ digit) (or "CHARLIE" "CHAN") (+ blank))
;;
@ -279,33 +296,32 @@ Return (REGEXP . PRECEDENCE)."
;; so that (or "@" "%" digit (any "A-Z" space) (syntax word))
;; -> (any "@" "%" digit "A-Z" space word)
;; -> "[A-Z@%[:digit:][:space:][:word:]]"
;;
;; Problem: If a subpattern is carefully written to be
;; optimizable by regexp-opt, how do we prevent the transforms
;; above from destroying that property?
;; Example: (or "a" (or "abc" "abd" "abe"))
(cond
((null body) ; No items: a never-matching regexp.
(rx--empty))
((null (cdr body)) ; Single item.
(rx--translate (car body)))
((rx--every #'stringp body) ; All strings.
(cons (list (regexp-opt body nil))
t))
((rx--every #'rx--charset-p body) ; All charsets.
(rx--translate-union nil body))
(t
(cons (append (car (rx--translate (car body)))
(mapcan (lambda (item)
(cons "\\|" (car (rx--translate item))))
(cdr body)))
nil))))
(let* ((args (mapcar #'rx--normalise-or-arg body))
(all-strings (catch 'rx--nonstring (rx--all-string-or-args args))))
(cond
(all-strings ; Only strings.
(cons (list (regexp-opt all-strings nil))
t))
((rx--every #'rx--charset-p args) ; All charsets.
(rx--translate-union nil args))
(t
(cons (append (car (rx--translate (car args)))
(mapcan (lambda (item)
(cons "\\|" (car (rx--translate item))))
(cdr args)))
nil)))))))
(defun rx--charset-p (form)
"Whether FORM looks like a charset, only consisting of character intervals
and set operations."
(or (and (consp form)
(or (and (memq (car form) '(any 'in 'char))
(or (and (memq (car form) '(any in char))
(rx--every (lambda (x) (not (symbolp x))) (cdr form)))
(and (memq (car form) '(not or | intersection))
(rx--every #'rx--charset-p (cdr form)))))
@ -450,6 +466,10 @@ classes."
(not negated))
(cons (list (regexp-quote (char-to-string (caar items))))
t))
;; Negated newline.
((and (equal items '((?\n . ?\n)))
negated)
(rx--translate-symbol 'nonl))
;; At least one character or class, possibly negated.
(t
(cons
@ -836,11 +856,15 @@ Return (REGEXP . PRECEDENCE)."
(cons (list (list 'regexp-quote arg)) 'seq))
(t (error "rx `literal' form with non-string argument")))))
(defun rx--translate-eval (body)
"Translate the `eval' form. Return (REGEXP . PRECEDENCE)."
(defun rx--expand-eval (body)
"Expand `eval' arguments. Return a new rx form."
(unless (and body (null (cdr body)))
(error "rx `eval' form takes exactly one argument"))
(rx--translate (eval (car body))))
(eval (car body)))
(defun rx--translate-eval (body)
"Translate the `eval' form. Return (REGEXP . PRECEDENCE)."
(rx--translate (rx--expand-eval body)))
(defvar rx--regexp-atomic-regexp nil)

View file

@ -7774,11 +7774,11 @@ also be Lisp expression evaluating to a string),
BUTTON: is the number of the regexp grouping actually matching the button,
FORM: is a Lisp expression which must eval to true for the button to
be added,
CALLBACK: is the function to call when the user push this button, and each
CALLBACK: is the function to call when the user pushes this button, and each
PAR: is a number of a regexp grouping whose text will be passed to CALLBACK.
CALLBACK can also be a variable, in that case the value of that
variable it the real callback function."
CALLBACK can also be a variable, in which case the value of that
variable is the real callback function."
:group 'gnus-article-buttons
:type '(repeat (list (choice regexp variable sexp)
(integer :tag "Button")

View file

@ -174,7 +174,7 @@ no effect when spam-stat is invoked through spam.el."
(defcustom spam-stat-score-buffer-user-functions nil
"List of additional scoring functions.
Called one by one on the buffer.
Called one by one on the buffer.
If all of these functions return non-nil answers, these numerical
answers are added to the computed spam stat score on the buffer. If

View file

@ -2601,7 +2601,7 @@ This function is intended to be added to `auto-coding-functions'."
(detect-coding-region (point-min) size t)))))
;; Pure ASCII always comes back as undecided.
(if (memq detected
'(utf-8 'utf-8-with-signature 'utf-8-hfs undecided))
'(utf-8 utf-8-with-signature utf-8-hfs undecided))
'utf-8
(warn "File contents detected as %s.
Consider adding an encoding attribute to the xml declaration,

View file

@ -446,17 +446,19 @@ variable `tab-line-tabs-function'."
(setq hscroll nil)
(set-window-parameter nil 'tab-line-hscroll hscroll))
(list separator
(when (and (integerp hscroll) (not (zerop hscroll)))
(when (and (numberp hscroll) (not (zerop hscroll)))
tab-line-left-button)
(when (if (integerp hscroll)
(< (abs hscroll) (1- (length strings)))
(when (if (numberp hscroll)
(< (truncate hscroll) (1- (length strings)))
(> (length strings) 1))
tab-line-right-button)))
(if hscroll (nthcdr (abs hscroll) strings) strings)
(if hscroll (nthcdr (truncate hscroll) strings) strings)
(when (eq tab-line-tabs-function #'tab-line-tabs-window-buffers)
(list (concat separator (when tab-line-new-tab-choice
tab-line-new-button)))))))
(defvar tab-line-auto-hscroll)
(defun tab-line-format ()
"Template for displaying tab line for selected window."
(let* ((tabs (funcall tab-line-tabs-function))
@ -464,6 +466,13 @@ variable `tab-line-tabs-function'."
(window-buffer)
(window-parameter nil 'tab-line-hscroll)))
(cache (window-parameter nil 'tab-line-cache)))
;; Enable auto-hscroll again after it was disabled on manual scrolling.
;; The moment to enable it is when the window-buffer was updated.
(when (and tab-line-auto-hscroll ; if auto-hscroll was enabled
(integerp (nth 2 cache-key)) ; integer on manual scroll
cache ; window-buffer was updated
(not (equal (nth 1 (car cache)) (nth 1 cache-key))))
(set-window-parameter nil 'tab-line-hscroll (float (nth 2 cache-key))))
(or (and cache (equal (car cache) cache-key) (cdr cache))
(cdr (set-window-parameter
nil 'tab-line-cache
@ -478,24 +487,27 @@ the selected tab visible."
:group 'tab-line
:version "27.1")
(defvar tab-line-auto-hscroll-buffer (generate-new-buffer " *tab-line-hscroll*"))
(defun tab-line-auto-hscroll (strings hscroll)
(with-temp-buffer
(with-current-buffer tab-line-auto-hscroll-buffer
(let ((truncate-partial-width-windows nil)
(inhibit-modification-hooks t)
show-arrows)
(setq truncate-lines nil)
(erase-buffer)
(apply 'insert strings)
(goto-char (point-min))
(add-face-text-property (point-min) (point-max) 'tab-line)
;; Continuation means tab-line doesn't fit completely,
;; thus scroll arrows are needed for scrolling.
(setq show-arrows (> (vertical-motion 1) 0))
;; Try to auto-scroll only when scrolling is needed,
;; Try to auto-hscroll only when scrolling is needed,
;; but no manual scrolling was performed before.
(when (and tab-line-auto-hscroll
show-arrows
;; Do nothing when scrolled manually
(not (and (integerp hscroll) (>= hscroll 0))))
(not (integerp hscroll)))
(let ((selected (seq-position strings 'selected
(lambda (str prop)
(get-pos-property 1 prop str)))))
@ -503,7 +515,7 @@ the selected tab visible."
((null selected)
;; Do nothing if no tab is selected
)
((or (not (integerp hscroll)) (< selected (abs hscroll)))
((or (not (numberp hscroll)) (< selected (truncate hscroll)))
;; Selected is scrolled to the left, or no scrolling yet
(erase-buffer)
(apply 'insert (reverse (seq-subseq strings 0 (1+ selected))))
@ -520,14 +532,14 @@ the selected tab visible."
(lambda (str tab)
(eq (get-pos-property 1 'tab str) tab))))))
(when new-hscroll
(setq hscroll (- new-hscroll))
(setq hscroll (float new-hscroll))
(set-window-parameter nil 'tab-line-hscroll hscroll)))
(setq hscroll nil)
(set-window-parameter nil 'tab-line-hscroll hscroll)))
(t
;; Check if the selected tab is already visible
(erase-buffer)
(apply 'insert (seq-subseq strings (abs hscroll) (1+ selected)))
(apply 'insert (seq-subseq strings (truncate hscroll) (1+ selected)))
(goto-char (point-min))
(add-face-text-property (point-min) (point-max) 'tab-line)
(when (> (vertical-motion 1) 0)
@ -547,7 +559,7 @@ the selected tab visible."
(lambda (str tab)
(eq (get-pos-property 1 'tab str) tab))))))
(when new-hscroll
(setq hscroll (- new-hscroll))
(setq hscroll (float new-hscroll))
(set-window-parameter nil 'tab-line-hscroll hscroll)))))))))
(list show-arrows hscroll))))
@ -559,7 +571,7 @@ the selected tab visible."
(funcall tab-line-tabs-function))))
(set-window-parameter
window 'tab-line-hscroll
(max 0 (min (+ (if (integerp hscroll) (abs hscroll) 0) (or arg 1))
(max 0 (min (+ (if (numberp hscroll) (truncate hscroll) 0) (or arg 1))
(1- (length tabs)))))
(when window
(force-mode-line-update t))))

View file

@ -1222,23 +1222,24 @@ is non-nil."
(defun vc-cvs-ignore (file &optional directory _remove)
"Ignore FILE under CVS.
FILE is either absolute or relative to DIRECTORY. The basename
of FILE is written unmodified into the ignore file and is
FILE is either absolute or relative to DIRECTORY. The non-directory
part of FILE is written unmodified into the ignore file and is
therefore evaluated by CVS as an ignore pattern which follows
glob(7) syntax. If the pattern should match any of the special
characters ?*[\\\ literally, they must be escaped with a
characters `?*[\\' literally, they must be escaped with a
backslash.
CVS processes one ignore file for each subdirectory. Patterns
are separated by whitespace and only match files in the same
directory. Since FILE can be a relative filename with leading
diretories, FILE is expanded against DIRECTORY to determine the
correct absolute filename. The directory name of this path is
then used to determine the location of the ignore file. The base
name of this path is used as pattern for the ignore file.
directories, FILE is expanded against DIRECTORY to determine the
correct absolute filename. The directory part of the resulting name
is then used to determine the location of the ignore file. The
non-directory part of the name is used as pattern for the ignore file.
Since patterns are whitespace sparated, it is usually better to
replace spaces in filenames with question marks ?."
Since patterns are whitespace-separated, filenames containing spaces
cannot be represented directly. A work-around is to replace such
spaces with question marks."
(setq file (directory-file-name (expand-file-name file directory)))
(vc-cvs-append-to-ignore (file-name-directory file) (file-name-nondirectory file)))

View file

@ -8806,8 +8806,7 @@ parameters of FRAME."
(parent (frame-parent frame))
(monitor-attributes
(unless parent
(car (display-monitor-attributes-list
(frame-parameter frame 'display)))))
(frame-monitor-attributes frame)))
;; FRAME'S parent or display sizes. Used in connection
;; with margins.
(geometry
@ -8816,11 +8815,11 @@ parameters of FRAME."
(parent-or-display-width
(if parent
(frame-native-width parent)
(- (nth 2 geometry) (nth 0 geometry))))
(nth 2 geometry)))
(parent-or-display-height
(if parent
(frame-native-height parent)
(- (nth 3 geometry) (nth 1 geometry))))
(nth 3 geometry)))
;; FRAME's parent or workarea sizes. Used when no margins
;; are specified.
(parent-or-workarea
@ -8882,13 +8881,15 @@ parameters of FRAME."
(window--sanitize-margin
(nth 2 margins) left-margin
parent-or-display-width))
(nth 2 parent-or-workarea)))
(+ (nth 0 parent-or-workarea)
(nth 2 parent-or-workarea))))
(bottom-margin (if (nth 3 margins)
(- parent-or-display-height
(window--sanitize-margin
(nth 3 margins) top-margin
parent-or-display-height))
(nth 3 parent-or-workarea)))
(+ (nth 1 parent-or-workarea)
(nth 3 parent-or-workarea))))
;; Minimum and maximum sizes specified for FRAME.
(sizes (or (frame-parameter frame 'fit-frame-to-buffer-sizes)
fit-frame-to-buffer-sizes))

View file

@ -818,6 +818,11 @@ fill_gstring_body (Lisp_Object gstring)
Lisp_Object header = AREF (gstring, 0);
ptrdiff_t len = LGSTRING_CHAR_LEN (gstring);
ptrdiff_t i;
struct font *font = NULL;
unsigned int code;
if (FONT_OBJECT_P (font_object))
font = XFONT_OBJECT (font_object);
for (i = 0; i < len; i++)
{
@ -832,10 +837,15 @@ fill_gstring_body (Lisp_Object gstring)
LGLYPH_SET_FROM (g, i);
LGLYPH_SET_TO (g, i);
LGLYPH_SET_CHAR (g, c);
if (FONT_OBJECT_P (font_object))
{
font_fill_lglyph_metrics (g, font_object);
}
if (font != NULL)
code = font->driver->encode_char (font, LGLYPH_CHAR (g));
else
code = FONT_INVALID_CODE;
if (code != FONT_INVALID_CODE)
{
font_fill_lglyph_metrics (g, font, code);
}
else
{
int width = XFIXNAT (CHAR_TABLE_REF (Vchar_width_table, c));

View file

@ -4416,10 +4416,8 @@ DEFUN ("clear-font-cache", Fclear_font_cache, Sclear_font_cache, 0, 0, 0,
void
font_fill_lglyph_metrics (Lisp_Object glyph, Lisp_Object font_object)
font_fill_lglyph_metrics (Lisp_Object glyph, struct font *font, unsigned int code)
{
struct font *font = XFONT_OBJECT (font_object);
unsigned code = font->driver->encode_char (font, LGLYPH_CHAR (glyph));
struct font_metrics metrics;
LGLYPH_SET_CODE (glyph, code);

View file

@ -886,7 +886,7 @@ extern Lisp_Object font_update_drivers (struct frame *f, Lisp_Object list);
extern Lisp_Object font_range (ptrdiff_t, ptrdiff_t, ptrdiff_t *,
struct window *, struct face *,
Lisp_Object);
extern void font_fill_lglyph_metrics (Lisp_Object, Lisp_Object);
extern void font_fill_lglyph_metrics (Lisp_Object, struct font *, unsigned int);
extern Lisp_Object font_put_extra (Lisp_Object font, Lisp_Object prop,
Lisp_Object val);

View file

@ -1039,9 +1039,7 @@ lispint_arith (Lisp_Object a, Lisp_Object b, bool subtract)
}
/* Given Lisp operands A and B, add their values, and return the
result as a Lisp timestamp that is in (TICKS . HZ) form if either A
or B are in that form or are floats, (HI LO US PS) form otherwise.
Subtract instead of adding if SUBTRACT. */
result as a Lisp timestamp. Subtract instead of adding if SUBTRACT. */
static Lisp_Object
time_arith (Lisp_Object a, Lisp_Object b, bool subtract)
{

View file

@ -4701,6 +4701,10 @@ static short temp_buffer[100];
/* Temporarily store lead byte of DBCS input sequences. */
static char dbcs_lead = 0;
/* Temporarily store pending UTF-16 high surrogate unit and the modifiers. */
static unsigned short utf16_high;
static DWORD utf16_high_modifiers;
/**
mouse_or_wdesc_frame: When not dropping and the mouse was grabbed
for DPYINFO, return the frame where the mouse was seen last. If
@ -4912,9 +4916,45 @@ w32_read_socket (struct terminal *terminal,
XSETFRAME (inev.frame_or_window, f);
inev.timestamp = msg.msg.time;
if (utf16_high
&& (msg.msg.message != WM_UNICHAR
|| UTF_16_HIGH_SURROGATE_P (msg.msg.wParam)))
{
/* Flush the pending high surrogate if the low one
isn't coming. (This should never happen, but I
have paranoia about this stuff.) */
struct input_event inev1;
inev1.modifiers = utf16_high_modifiers;
inev1.code = utf16_high;
inev1.timestamp = inev.timestamp;
inev1.arg = Qnil;
kbd_buffer_store_event_hold (&inev1, hold_quit);
utf16_high = 0;
utf16_high_modifiers = 0;
}
if (msg.msg.message == WM_UNICHAR)
{
inev.code = msg.msg.wParam;
/* Handle UTF-16 encoded codepoint above the BMP.
This is needed to support Emoji input from input
panel popped up by "Win+." shortcut. */
if (UTF_16_HIGH_SURROGATE_P (msg.msg.wParam))
{
utf16_high = msg.msg.wParam;
utf16_high_modifiers = inev.modifiers;
inev.kind = NO_EVENT;
break;
}
else if (UTF_16_LOW_SURROGATE_P (msg.msg.wParam)
&& utf16_high)
{
inev.code = surrogates_to_codepoint (msg.msg.wParam,
utf16_high);
utf16_high = 0;
utf16_high_modifiers = 0;
}
else
inev.code = msg.msg.wParam;
}
else if (msg.msg.wParam < 256)
{

View file

@ -42,13 +42,24 @@
(ert-deftest rx-or ()
(should (equal (rx (or "ab" (| "c" nonl) "de"))
"ab\\|c\\|.\\|de"))
(should (equal (rx (or "ab" "abc" "a"))
(should (equal (rx (or "ab" "abc" ?a))
"\\(?:a\\(?:bc?\\)?\\)"))
(should (equal (rx (or "ab" (| (or "abcd" "abcde")) (or "a" "abc")))
"\\(?:a\\(?:b\\(?:c\\(?:de?\\)?\\)?\\)?\\)"))
(should (equal (rx (or "a" (eval (string ?a ?b))))
"\\(?:ab?\\)"))
(should (equal (rx (| nonl "a") (| "b" blank))
"\\(?:.\\|a\\)\\(?:b\\|[[:blank:]]\\)"))
(should (equal (rx (|))
"\\`a\\`")))
(ert-deftest rx-def-in-or ()
(rx-let ((a b)
(b (or "abc" c))
(c ?a))
(should (equal (rx (or a (| "ab" "abcde") "abcd"))
"\\(?:a\\(?:b\\(?:c\\(?:de?\\)?\\)?\\)?\\)"))))
(ert-deftest rx-char-any ()
"Test character alternatives with `]' and `-' (Bug#25123)."
(should (equal
@ -130,7 +141,10 @@
(should (equal (rx (any "") (not (any "")))
"\\`a\\`[^z-a]"))
(should (equal (rx (any space ?a digit space))
"[a[:space:][:digit:]]")))
"[a[:space:][:digit:]]"))
(should (equal (rx (not "\n") (not ?\n) (not (any "\n")) (not-char ?\n)
(| (not (in "a\n")) (not (char ?\n (?b . ?b)))))
".....")))
(ert-deftest rx-pcase ()
(should (equal (pcase "a 1 2 3 1 1 b"
@ -298,7 +312,11 @@
(not (any "a-k"))))
"[^abh-k]"))
(should (equal (rx (or ?f (any "b-e") "a") (not (or ?x "y" (any "s-w"))))
"[a-f][^s-y]")))
"[a-f][^s-y]"))
(should (equal (rx (not (or (in "abc") (char "bcd"))))
"[^a-d]"))
(should (equal (rx (or (not (in "abc")) (not (char "bcd"))))
"[^bc]")))
(ert-deftest rx-def-in-charset-or ()
(rx-let ((a (any "badc"))