X-Git-Url: https://code.delx.au/gnu-emacs/blobdiff_plain/d213cf0400ee5cad2e7f4626745fd97b942ff5e9..6bd9d697fd6d81726fa684fa86ef7369a1ef93de:/src/doc.c diff --git a/src/doc.c b/src/doc.c index 81b1354668..a9273f0580 100644 --- a/src/doc.c +++ b/src/doc.c @@ -1,6 +1,6 @@ -/* Record indices of function doc strings stored in a file. +/* Record indices of function doc strings stored in a file. -*- coding: utf-8 -*- -Copyright (C) 1985-1986, 1993-1995, 1997-2015 Free Software Foundation, +Copyright (C) 1985-1986, 1993-1995, 1997-2016 Free Software Foundation, Inc. This file is part of GNU Emacs. @@ -31,8 +31,9 @@ along with GNU Emacs. If not, see . */ #include "lisp.h" #include "character.h" +#include "coding.h" #include "buffer.h" -#include "keyboard.h" +#include "disptab.h" #include "keymap.h" /* Buffer used for reading from documentation file. */ @@ -406,10 +407,7 @@ string is passed through `substitute-command-keys'. */) if (NILP (tem) && try_reload) { /* The file is newer, we need to reset the pointers. */ - struct gcpro gcpro1, gcpro2; - GCPRO2 (function, raw); try_reload = reread_doc_file (Fcar_safe (doc)); - UNGCPRO; if (try_reload) { try_reload = 0; @@ -451,10 +449,7 @@ aren't strings. */) if (NILP (tem) && try_reload) { /* The file is newer, we need to reset the pointers. */ - struct gcpro gcpro1, gcpro2, gcpro3; - GCPRO3 (symbol, prop, raw); try_reload = reread_doc_file (Fcar_safe (doc)); - UNGCPRO; if (try_reload) { try_reload = 0; @@ -683,6 +678,34 @@ the same file name is found in the `doc-directory'. */) return unbind_to (count, Qnil); } +/* Return true if text quoting style should default to quote `like this'. */ +static bool +default_to_grave_quoting_style (void) +{ + if (!text_quoting_flag) + return true; + if (! DISP_TABLE_P (Vstandard_display_table)) + return false; + Lisp_Object dv = DISP_CHAR_VECTOR (XCHAR_TABLE (Vstandard_display_table), + LEFT_SINGLE_QUOTATION_MARK); + return (VECTORP (dv) && ASIZE (dv) == 1 + && EQ (AREF (dv, 0), make_number ('`'))); +} + +/* Return the current effective text quoting style. */ +enum text_quoting_style +text_quoting_style (void) +{ + if (NILP (Vtext_quoting_style) + ? default_to_grave_quoting_style () + : EQ (Vtext_quoting_style, Qgrave)) + return GRAVE_QUOTING_STYLE; + else if (EQ (Vtext_quoting_style, Qstraight)) + return STRAIGHT_QUOTING_STYLE; + else + return CURVE_QUOTING_STYLE; +} + DEFUN ("substitute-command-keys", Fsubstitute_command_keys, Ssubstitute_command_keys, 1, 1, 0, doc: /* Substitute key descriptions for command names in STRING. @@ -693,14 +716,15 @@ is not on any keys. Each substring of the form \\=\\{MAPVAR} is replaced by a summary of the value of MAPVAR as a keymap. This summary is similar to the one produced by `describe-bindings'. The summary ends in two newlines -\(used by the helper function `help-make-xrefs' to find the end of the +(used by the helper function `help-make-xrefs' to find the end of the summary). Each substring of the form \\=\\ specifies the use of MAPVAR as the keymap for future \\=\\[COMMAND] substrings. -Each \\=` is replaced by ‘. Each ' preceded by \\=` and without -intervening ' is replaced by ’. +Each \\=‘ and \\=` is replaced by left quote, and each \\=’ and \\=' +is replaced by right quote. Left and right quote characters are +specified by `text-quoting-style'. \\=\\= quotes the following character and is discarded; thus, \\=\\=\\=\\= puts \\=\\= into the output, \\=\\=\\=\\[ puts \\=\\[ into the output, and @@ -712,17 +736,15 @@ Otherwise, return a new string. */) { char *buf; bool changed = false; - bool in_quote = false; unsigned char *strp; char *bufp; ptrdiff_t idx; ptrdiff_t bsize; Lisp_Object tem; Lisp_Object keymap; - unsigned char *start; + unsigned char const *start; ptrdiff_t length, length_byte; Lisp_Object name; - struct gcpro gcpro1, gcpro2, gcpro3, gcpro4; bool multibyte; ptrdiff_t nchars; @@ -733,7 +755,8 @@ Otherwise, return a new string. */) tem = Qnil; keymap = Qnil; name = Qnil; - GCPRO4 (string, tem, keymap, name); + + enum text_quoting_style quoting_style = text_quoting_style (); multibyte = STRING_MULTIBYTE (string); nchars = 0; @@ -891,11 +914,13 @@ Otherwise, return a new string. */) if (NILP (tem)) { name = Fsymbol_name (name); - insert_string ("\nUses keymap `"); + AUTO_STRING (msg_prefix, "\nUses keymap `"); + insert1 (Fsubstitute_command_keys (msg_prefix)); insert_from_string (name, 0, 0, SCHARS (name), SBYTES (name), 1); - insert_string ("', which is not currently defined.\n"); + AUTO_STRING (msg_suffix, "', which is not currently defined.\n"); + insert1 (Fsubstitute_command_keys (msg_suffix)); if (start[-1] == '<') keymap = Qnil; } else if (start[-1] == '<') @@ -932,51 +957,44 @@ Otherwise, return a new string. */) strp = SDATA (string) + idx; } } - else if (EQ (Vhelp_quote_translation, Qprefer_unicode) - && (strp[0] == '`')) + else if ((strp[0] == '`' || strp[0] == '\'') + && quoting_style == CURVE_QUOTING_STYLE) { - in_quote = true; - start = (unsigned char *) "\xE2\x80\x98"; /* ‘ */ - subst_quote: + start = (unsigned char const *) (strp[0] == '`' ? uLSQM : uRSQM); length = 1; - length_byte = 3; + length_byte = sizeof uLSQM - 1; idx = strp - SDATA (string) + 1; goto subst; } - else if (EQ (Vhelp_quote_translation, Qprefer_unicode) - && (strp[0] == '\'' && in_quote)) + else if (strp[0] == '`' && quoting_style == STRAIGHT_QUOTING_STYLE) { - in_quote = false; - start = (unsigned char *) "\xE2\x80\x99"; /* ’ */ - goto subst_quote; + *bufp++ = '\''; + strp++; + nchars++; + changed = true; } - - else if (EQ (Vhelp_quote_translation, Qtraditional) - && (strp[0] == 0xE2) - && (strp[1] == 0x80) - && ((strp[2] == 0x98) /* curly opening quote */ - || (strp[2] == 0x99))) /* curly closing quote */ - { - start = (strp[2] == 0x98) ? "`" : "'"; - length = 1; - length_byte = 1; - idx = strp - SDATA (string) + 3; - goto subst; - } - - else if (! multibyte) /* just copy other chars */ + else if (! multibyte) *bufp++ = *strp++, nchars++; else { int len; - - STRING_CHAR_AND_LENGTH (strp, len); - if (len == 1) - *bufp = *strp; + int ch = STRING_CHAR_AND_LENGTH (strp, len); + if ((ch == LEFT_SINGLE_QUOTATION_MARK + || ch == RIGHT_SINGLE_QUOTATION_MARK) + && quoting_style != CURVE_QUOTING_STYLE) + { + *bufp++ = ((ch == LEFT_SINGLE_QUOTATION_MARK + && quoting_style == GRAVE_QUOTING_STYLE) + ? '`' : '\''); + strp += len; + changed = true; + } else - memcpy (bufp, strp, len); - strp += len; - bufp += len; + { + do + *bufp++ = *strp++; + while (--len != 0); + } nchars++; } } @@ -986,15 +1004,15 @@ Otherwise, return a new string. */) else tem = string; xfree (buf); - RETURN_UNGCPRO (tem); + return tem; } void syms_of_doc (void) { DEFSYM (Qfunction_documentation, "function-documentation"); - DEFSYM (Qtraditional, "traditional"); - DEFSYM (Qprefer_unicode, "prefer-unicode"); + DEFSYM (Qgrave, "grave"); + DEFSYM (Qstraight, "straight"); DEFVAR_LISP ("internal-doc-file-name", Vdoc_file_name, doc: /* Name of file containing documentation strings of built-in symbols. */); @@ -1004,17 +1022,19 @@ syms_of_doc (void) doc: /* A list of files used to build this Emacs binary. */); Vbuild_files = Qnil; - DEFVAR_LISP ("help-quote-translation", Vhelp_quote_translation, - doc: /* How to translate quotes for display in *Help*. -If the value is nil (default), no translation is done. -If it's the symbol `traditional', any occurrences of the curly quotes -are translated to their ASCII "equivalents", GRAVE and APOSTROPHE. -If it's the symbol `prefer-unicode', any matched pairs of GRAVE and -APOSTROPHE will get translated into the "equivalent" curly quotes. - -Note that any translation done is done in a fresh copy of the doc -string, and doesn't overwrite the original characters. */); - Vhelp_quote_translation = Qnil; + DEFVAR_LISP ("text-quoting-style", Vtext_quoting_style, + doc: /* Style to use for single quotes in help and messages. +Its value should be a symbol. +`curve' means quote with curved single quotes \\=‘like this\\=’. +`straight' means quote with straight apostrophes \\='like this\\='. +`grave' means quote with grave accent and apostrophe \\=`like this\\='. +The default value nil acts like `curve' if curved single quotes are +displayable, and like `grave' otherwise. */); + Vtext_quoting_style = Qnil; + + DEFVAR_BOOL ("internal--text-quoting-flag", text_quoting_flag, + doc: /* If nil, a nil `text-quoting-style' is treated as `grave'. */); + /* Initialized by ‘main’. */ defsubr (&Sdocumentation); defsubr (&Sdocumentation_property);