From mboxrd@z Thu Jan 1 00:00:00 1970 Path: news.gmane.io!.POSTED.blaine.gmane.org!not-for-mail From: Philip Kaludercic Newsgroups: gmane.emacs.bugs Subject: bug#69097: [PATCH] Add 'kill-region-or-word' command Date: Fri, 03 May 2024 19:41:43 +0000 Message-ID: <874jbe65u0.fsf@posteo.net> References: <871q9g8z8k.fsf@posteo.net> <87wmob73ds.fsf@posteo.net> <861q6jji0i.fsf@gnu.org> <87o79n6uj6.fsf@posteo.net> <86v83vi2kr.fsf@gnu.org> <86seyzi2by.fsf@gnu.org> <87cyq26bt8.fsf@posteo.net> <864jbeixkt.fsf@gnu.org> Mime-Version: 1.0 Content-Type: multipart/mixed; boundary="=-=-=" Injection-Info: ciao.gmane.io; posting-host="blaine.gmane.org:116.202.254.214"; logging-data="4718"; mail-complaints-to="usenet@ciao.gmane.io" Cc: rms@gnu.org, 69097@debbugs.gnu.org To: Eli Zaretskii Original-X-From: bug-gnu-emacs-bounces+geb-bug-gnu-emacs=m.gmane-mx.org@gnu.org Fri May 03 21:42:50 2024 Return-path: Envelope-to: geb-bug-gnu-emacs@m.gmane-mx.org Original-Received: from lists.gnu.org ([209.51.188.17]) by ciao.gmane.io with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.92) (envelope-from ) id 1s2ynv-0000xn-LS for geb-bug-gnu-emacs@m.gmane-mx.org; Fri, 03 May 2024 21:42:47 +0200 Original-Received: from localhost ([::1] helo=lists1p.gnu.org) by lists.gnu.org with esmtp (Exim 4.90_1) (envelope-from ) id 1s2ynp-0000TW-OE; Fri, 03 May 2024 15:42:41 -0400 Original-Received: from eggs.gnu.org ([2001:470:142:3::10]) by lists.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_256_GCM_SHA384:256) (Exim 4.90_1) (envelope-from ) id 1s2yno-0000PP-4I for bug-gnu-emacs@gnu.org; Fri, 03 May 2024 15:42:40 -0400 Original-Received: from debbugs.gnu.org ([2001:470:142:5::43]) by eggs.gnu.org with esmtps (TLS1.2:ECDHE_RSA_AES_128_GCM_SHA256:128) (Exim 4.90_1) (envelope-from ) id 1s2ynn-0006gU-S1 for bug-gnu-emacs@gnu.org; Fri, 03 May 2024 15:42:39 -0400 Original-Received: from Debian-debbugs by debbugs.gnu.org with local (Exim 4.84_2) (envelope-from ) id 1s2yoA-0006c6-3G for bug-gnu-emacs@gnu.org; Fri, 03 May 2024 15:43:02 -0400 X-Loop: help-debbugs@gnu.org Resent-From: Philip Kaludercic Original-Sender: "Debbugs-submit" Resent-CC: bug-gnu-emacs@gnu.org Resent-Date: Fri, 03 May 2024 19:43:02 +0000 Resent-Message-ID: Resent-Sender: help-debbugs@gnu.org X-GNU-PR-Message: followup 69097 X-GNU-PR-Package: emacs X-GNU-PR-Keywords: patch Original-Received: via spool by 69097-submit@debbugs.gnu.org id=B69097.171476534125404 (code B ref 69097); Fri, 03 May 2024 19:43:02 +0000 Original-Received: (at 69097) by debbugs.gnu.org; 3 May 2024 19:42:21 +0000 Original-Received: from localhost ([127.0.0.1]:48396 helo=debbugs.gnu.org) by debbugs.gnu.org with esmtp (Exim 4.84_2) (envelope-from ) id 1s2ynV-0006bg-3v for submit@debbugs.gnu.org; Fri, 03 May 2024 15:42:21 -0400 Original-Received: from mout01.posteo.de ([185.67.36.65]:45107) by debbugs.gnu.org with esmtp (Exim 4.84_2) (envelope-from ) id 1s2ynP-0006bY-Af for 69097@debbugs.gnu.org; Fri, 03 May 2024 15:42:19 -0400 Original-Received: from submission (posteo.de [185.67.36.169]) by mout01.posteo.de (Postfix) with ESMTPS id 0A79524002A for <69097@debbugs.gnu.org>; Fri, 3 May 2024 21:41:46 +0200 (CEST) DKIM-Signature: v=1; a=rsa-sha256; c=relaxed/simple; d=posteo.net; s=2017; t=1714765307; bh=bu8itpycT4mOOuFSNyB5iaFKdhKjWMyUSXTBYTlYR4E=; h=From:To:Cc:Subject:OpenPGP:Date:Message-ID:MIME-Version: Content-Type:From; b=Jy0rIIi8AlTBatXsN1/f7tF54ZGZ17gUYa2KQxhFNH/MVSEebCuoHPkDirwc3Vw1z HrJeij8ki9/Wv0PMp6OYGAn2YinZ+aeoTWAsAnbkWq5Q1U8HypsbWfQfkDN/K2C8QQ YSv6t2g1SWx5UXeE4ON9V69c5WaCH1YmMrJKrtSa/OUiOAVL84P+zU0ErZBVBo8htf GDLXTciNAUvmq/OVC27/E+0ECrFjtw6EWC3XU6NCaZfk03sn4+M3vjLnwmozOBR6f0 6NK8c7G1lfDzgWe3Zq4FYC9iFIDtDnxsYmOjPiMv9eJAaVxuSNLMY2Asuqdh7ZyAGE veJDbOWTE0ovQ== Original-Received: from customer (localhost [127.0.0.1]) by submission (posteo.de) with ESMTPSA id 4VWLls5Zvpz6tyK; Fri, 3 May 2024 21:41:45 +0200 (CEST) In-Reply-To: <864jbeixkt.fsf@gnu.org> (Eli Zaretskii's message of "Fri, 03 May 2024 21:01:38 +0300") OpenPGP: id=7126E1DE2F0CE35C770BED01F2C3CC513DB89F66; url="https://keys.openpgp.org/vks/v1/by-fingerprint/7126E1DE2F0CE35C770BED01F2C3CC513DB89F66"; preference=signencrypt X-BeenThere: debbugs-submit@debbugs.gnu.org X-Mailman-Version: 2.1.18 Precedence: list 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-mx.org@gnu.org Original-Sender: bug-gnu-emacs-bounces+geb-bug-gnu-emacs=m.gmane-mx.org@gnu.org Xref: news.gmane.io gmane.emacs.bugs:284394 Archived-At: --=-=-= Content-Type: text/plain Eli Zaretskii writes: >> From: Philip Kaludercic >> Cc: rms@gnu.org, 69097@debbugs.gnu.org >> Date: Fri, 03 May 2024 17:32:35 +0000 >> >> Eli Zaretskii writes: >> >> >> Cc: rms@gnu.org, 69097@debbugs.gnu.org >> >> Date: Fri, 03 May 2024 13:59:00 +0300 >> >> From: Eli Zaretskii >> >> >> >> > From: Philip Kaludercic >> >> > Cc: 69097@debbugs.gnu.org, Richard Stallman >> >> > Date: Fri, 03 May 2024 10:48:13 +0000 >> >> > >> >> > > More to the point, can you explain why we need this, given the >> >> > > existence of kill-word? >> >> > > >> >> > > Also, this kills backward, something that is not evident, neither from >> >> > > the name of the command nor from the doc string (and the obscure >> >> > > reference to Unix doesn't help, IMO). >> >> > > >> >> > > Finally, having another command that kills the region doesn't seem >> >> > > justified, or is it? >> >> > >> >> > The motivation is sort of the same as with generalising `upcase-word' to >> >> > `upcase-dwim'. If there is no active region, it behaves like >> >> > `backward-kill-word' (which is what C-w does in a terminal as well), but >> >> > if there is an active region it reverts to `kill-ring-save'. >> >> >> >> If so, then (assuming we decide to accept this change), the name of >> >> the command should be something like kill-word-dwim, and the doc >> >> string should mention the two commands you refer to above. >> >> >> >> > I have this in my personal configuration for ages, and it is always >> >> > one of the first things I re-implement when using an Emacs without a >> >> > custom init.el. >> >> >> >> Any reason why you need this command and cannot settle for the two >> >> commands it replaces heuristically? Are you using Emacs with >> >> transient-mark-mode on or off? >> > >> > And one more question: currently C-w signals an error if there's no >> > region. So another idea is to extend C-w to delete the word at point >> > if there's no region (where "no region" means "no active region" if >> > transient-mark-mode is ON, otherwise it means "no mark set"). >> >> That is basically what my command does (with the difference that I don't >> just check if (mark) is non-nil but also if (use-region-p) is non-nil), >> just not part of kill-region. I don't know if this is too invasive, if >> users are used to this error being signalled. Perhaps it can be >> protected by a user option? > > I don't think anyone wants the error, so doing something useful in > that case should be a no-brainer. How does this look like: --=-=-= Content-Type: text/x-patch Content-Disposition: attachment; filename=0001-Allow-kill-region-to-delete-the-last-word.patch >From c64fa2065e88c4e4848bf8a15161c82ae6d1c2bd Mon Sep 17 00:00:00 2001 From: Philip Kaludercic Date: Fri, 3 May 2024 21:38:51 +0200 Subject: [PATCH] Allow 'kill-region' to delete the last word * lisp/simple.el (kill-word-if-no-region): Add new user option to allow 'kill-region' to kill the last word if no region is active. The intention is to mirror the conventional C-w binding found in many Unix shells. (kill-region): Respect 'kill-word-if-no-region'. * etc/NEWS: Mention the change. (Bug#69097) --- etc/NEWS | 6 ++++++ lisp/simple.el | 43 ++++++++++++++++++++++++++++++------------- 2 files changed, 36 insertions(+), 13 deletions(-) diff --git a/etc/NEWS b/etc/NEWS index d4177d759f3..a0f2472ab67 100644 --- a/etc/NEWS +++ b/etc/NEWS @@ -416,6 +416,12 @@ When visiting a script that invokes 'env -S INTERPRETER ARGS...' in its shebang line, Emacs will now skip over 'env -S' and deduce the major mode based on the interpreter after 'env -S'. +--- +*** New user option 'kill-word-if-no-region'. +This option will modify the fall-back behaviour of 'kill-region' if no +region is active, and will kill the last word instead of raising an +error. + ** Emacs Server and Client --- diff --git a/lisp/simple.el b/lisp/simple.el index a459f6ecfd2..7fade562909 100644 --- a/lisp/simple.el +++ b/lisp/simple.el @@ -5790,6 +5790,11 @@ kill-read-only-ok :type 'boolean :group 'killing) +(defcustom kill-word-if-no-region nil + "Non-nil means that `kill-region' without a region will kill the last word." + :type 'boolean + :group 'killing) + (defun kill-region (beg end &optional region) "Kill (\"cut\") text between point and mark. This deletes the text from the buffer and saves it in the kill ring. @@ -5812,25 +5817,36 @@ kill-region the text, but put the text in the kill ring anyway. This means that you can use the killing commands to copy text from a read-only buffer. -Lisp programs should use this function for killing text. - (To delete text, use `delete-region'.) -Supply two arguments, character positions BEG and END indicating the - stretch of text to be killed. If the optional argument REGION is - non-nil, the function ignores BEG and END, and kills the current - region instead. Interactively, REGION is always non-nil, and so - this command always kills the current region." +Lisp programs should use this function for killing text. (To delete +text, use `delete-region'.) Supply two arguments, character positions +BEG and END indicating the stretch of text to be killed. If the +optional argument REGION is non-nil, the function ignores BEG and END, +and kills the current region instead. If REGION has the special value +`kill-word', then it will kill the previous word, as with +`backward-kill-word'. Interactively, REGION is always non-nil, and so +this command always kills the current region." ;; Pass mark first, then point, because the order matters when ;; calling `kill-append'. (interactive (progn (let ((beg (mark)) (end (point))) - (unless (and beg end) - (user-error "The mark is not set now, so there is no region")) - (list beg end 'region)))) + (cond + ((and beg end (use-region-p)) + (list beg end 'region)) + (kill-word-if-no-region + (list beg end 'kill-word)) + ((user-error "The mark is not set now, so there is no region")))))) + (condition-case nil - (let ((string (if region - (funcall region-extract-function 'delete) - (filter-buffer-substring beg end 'delete)))) + (let ((string (cond + ((eq region 'kill-word) + (let ((end (point))) + (save-excursion + (forward-word -1) + (filter-buffer-substring (point) end 'delete)))) + (region + (funcall region-extract-function 'delete)) + ((filter-buffer-substring beg end 'delete))))) (when string ;STRING is nil if BEG = END ;; Add that string to the kill ring, one way or another. (if (eq last-command 'kill-region) @@ -5857,6 +5873,7 @@ kill-region ;; If the buffer isn't read-only, the text is. (signal 'text-read-only (list (current-buffer))))))) + ;; copy-region-as-kill no longer sets this-command, because it's confusing ;; to get two copies of the text when the user accidentally types M-w and ;; then corrects it with the intended C-w. -- 2.44.0 --=-=-= Content-Type: text/plain -- Philip Kaludercic on peregrine --=-=-=--