|
6 | 6 | (:import-from :lem-vi-mode/visual |
7 | 7 | :visual-p |
8 | 8 | :visual-line-p |
| 9 | + :visual-block-p |
9 | 10 | :apply-visual-range |
10 | 11 | :vi-visual-end) |
11 | 12 | (:import-from :lem/common/command |
|
89 | 90 | (t (values arg-list '("P") nil)))) |
90 | 91 |
|
91 | 92 | (defmacro define-vi-motion (name arg-list (&key type jump) &body body) |
92 | | - (check-type type (or null (member :inclusive :exclusive :line))) |
| 93 | + (check-type type (or null (member :inclusive :exclusive :line :block))) |
93 | 94 | (check-type jump boolean) |
94 | 95 | (multiple-value-bind (arg-list arg-descriptor default-n-arg) |
95 | 96 | (parse-vi-motion-arg-list arg-list) |
|
125 | 126 | (if (typep command 'vi-motion) |
126 | 127 | (vi-motion-type command) |
127 | 128 | :exclusive))) |
128 | | - (if (visual-p) |
129 | | - (let (start end) |
130 | | - (apply-visual-range |
131 | | - (lambda (vstart vend) |
132 | | - (setf start vstart |
133 | | - end vend))) |
134 | | - (values start |
135 | | - end |
136 | | - (if (visual-line-p) :line :exclusive))) |
137 | | - (with-point ((start (current-point))) |
138 | | - (if motion |
139 | | - (let ((command (get-command motion))) |
140 | | - (call-motion command n) |
141 | | - (values |
142 | | - start |
143 | | - (copy-point (current-point)) |
144 | | - (command-motion-type command))) |
145 | | - (let* ((uarg (or (read-universal-argument) n)) |
146 | | - (command-name (read-command)) |
147 | | - (command (get-command command-name))) |
148 | | - (typecase command |
149 | | - (vi-operator |
150 | | - (if (eq command-name (command-name (this-command))) |
151 | | - ;; Recursive call of the operator like 'dd', 'cc' |
152 | | - (with-point ((end (current-point))) |
153 | | - (line-offset end (1- (or uarg 1))) |
154 | | - (values start end :line)) |
155 | | - ;; Ignore an invalid operator (like 'dJ') |
156 | | - nil)) |
157 | | - (otherwise |
158 | | - (call-motion command uarg) |
159 | | - (values start |
160 | | - (copy-point (current-point)) |
161 | | - (command-motion-type command)))))))))) |
| 129 | + (with-point ((start (current-point))) |
| 130 | + (if motion |
| 131 | + (let ((command (get-command motion))) |
| 132 | + (call-motion command n) |
| 133 | + (values |
| 134 | + start |
| 135 | + (copy-point (current-point)) |
| 136 | + (command-motion-type command))) |
| 137 | + (let* ((uarg (or (read-universal-argument) n)) |
| 138 | + (command-name (read-command)) |
| 139 | + (command (get-command command-name))) |
| 140 | + (typecase command |
| 141 | + (vi-operator |
| 142 | + (if (eq command-name (command-name (this-command))) |
| 143 | + ;; Recursive call of the operator like 'dd', 'cc' |
| 144 | + (with-point ((end (current-point))) |
| 145 | + (line-offset end (1- (or uarg 1))) |
| 146 | + (values start end :line)) |
| 147 | + ;; Ignore an invalid operator (like 'dJ') |
| 148 | + nil)) |
| 149 | + (otherwise |
| 150 | + (call-motion command uarg) |
| 151 | + (values start |
| 152 | + (copy-point (current-point)) |
| 153 | + (command-motion-type command))))))))) |
162 | 154 |
|
163 | 155 | (defun call-vi-operator (n fn &key motion keep-visual restore-point) |
164 | | - (with-point ((*vi-origin-point* (current-point))) |
165 | | - (unwind-protect |
166 | | - (if *vi-operator-arguments* |
167 | | - (apply fn *vi-operator-arguments*) |
168 | | - (multiple-value-bind (start end type) |
169 | | - (vi-operator-region n motion) |
170 | | - (when (point< end start) |
171 | | - (rotatef start end)) |
172 | | - (ecase type |
173 | | - (:line (unless (visual-p) |
174 | | - (line-start start) |
175 | | - (line-end end))) |
176 | | - (:inclusive (character-offset end 1)) |
177 | | - (:exclusive)) |
178 | | - (let ((*vi-operator-arguments* (list start end type))) |
179 | | - (funcall fn start end type)))) |
180 | | - (when restore-point |
181 | | - (move-point (current-point) *vi-origin-point*)) |
182 | | - (unless keep-visual |
183 | | - (when (visual-p) |
184 | | - (vi-visual-end)))))) |
| 156 | + (flet ((call-with-region (fn start end type) |
| 157 | + (when (point< end start) |
| 158 | + (rotatef start end)) |
| 159 | + (ecase type |
| 160 | + (:line (unless (visual-p) |
| 161 | + (line-start start) |
| 162 | + (line-end end))) |
| 163 | + (:block) |
| 164 | + (:inclusive |
| 165 | + (unless (point= start end) |
| 166 | + (character-offset end 1))) |
| 167 | + (:exclusive)) |
| 168 | + (let ((*vi-operator-arguments* (list start end type))) |
| 169 | + (funcall fn start end type)))) |
| 170 | + (with-point ((*vi-origin-point* (current-point))) |
| 171 | + (unwind-protect |
| 172 | + (if *vi-operator-arguments* |
| 173 | + (apply fn *vi-operator-arguments*) |
| 174 | + (if (visual-p) |
| 175 | + (apply-visual-range |
| 176 | + (lambda (start end) |
| 177 | + (call-with-region fn start end |
| 178 | + (cond |
| 179 | + ((visual-line-p) :line) |
| 180 | + ((visual-block-p) :block) |
| 181 | + (t :exclusive))))) |
| 182 | + (multiple-value-bind (start end type) |
| 183 | + (vi-operator-region n motion) |
| 184 | + (call-with-region fn start end type)))) |
| 185 | + (when restore-point |
| 186 | + (move-point (current-point) *vi-origin-point*)) |
| 187 | + (unless keep-visual |
| 188 | + (when (visual-p) |
| 189 | + (vi-visual-end))))))) |
185 | 190 |
|
186 | 191 | (defmacro define-vi-operator (name arg-list (&key motion keep-visual restore-point) &body body) |
187 | 192 | (with-gensyms (n extra-args) |
|
0 commit comments