Configuring a Yasnippet for two scenarios -- (1) region is active; (2) region is not active

StackOverflow https://stackoverflow.com/questions/22735895

  •  23-06-2023
  •  | 
  •  

Question

In conjunction with a user-configuration of (delete-selection-mode 1), is there a way to consolidate the two following Yasnippets into just one snippet so that it will work differently depending upon whether the region is active. For example: (if (region-active-p) (yas/selected-text) "$1")

Active region -- surround the active region with the snippet:

# -*- mode: snippet -*-
# contributor: lawlist
# key: bold_selected
# name: bold_selected
# binding: C-I b b s
# --
{\bf `yas/selected-text`}

Non-active region -- insert the snippet and place the cursor at the position of $1:

# -*- mode: snippet -*-
# contributor: lawlist
# key: bold
# name: bold
# binding: C-I b b b
# --
{\bf $1}
Was it helpful?

Solution

Back-ticks surrounding the elisp code to be evaluated are required. The built-in variable yas-selected-text stores the text of the selected region, which can be used to reinsert the same text during the snippet creation. Four (4) backslashes are needed for every one (1) backslash.

# -*- mode: snippet -*-
# contributor: lawlist
# key: bold
# name: bold
# binding: TAB <f6>
# --
`(if (region-active-p)
   (concat
     "{\\\\bf "
     yas-selected-text
     "}")
   "{\\\\bf $1}")`

OTHER TIPS

# -*- mode: snippet -*-
# name: bold
# key: bold
# type: command
# --
(if (region-active-p)
    (yas-expand-snippet "{\\bf `yas-selected-text`}")
  (yas-expand-snippet "{\\bf $0}"))

I am using this snippet to conditionally wrap variables in JavaScript template literals.

If there is selected text, then $1 uses that. Otherwise it uses the default value var which the user can overtype to replace the mirrored instance of $1.

# -*- coding: utf-8; mode: snippet -*-
# name: wrap variable in string template to log its value `var=${var}`
# expand-env : ((yas-wrap-around-region nil))
# --
${1:`(if (region-active-p) (yas-selected-text) "var")`}=\${$1}$0

For your problem, this snippet seems to work

# -*- coding: utf-8; mode: snippet -*-
# name: wrap selected text, or user provided text, in bold font
# expand-env: ((yas-wrap-around-region nil))
# --
{\bf ${1:`(if (region-active-p) (yas-selected-text) "text-to-bold")`}}$0
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top