diff options
| author | Simon Marshall | 1996-11-16 13:33:51 +0000 |
|---|---|---|
| committer | Simon Marshall | 1996-11-16 13:33:51 +0000 |
| commit | d7606d13d94051ec47ec9509ba6e721edaecc0eb (patch) | |
| tree | 81b48973b5ec14cd9477e4f5846723eebf9cd078 | |
| parent | 098de8c9f92100efbf6dce5bc8e9151119c56fc7 (diff) | |
| download | emacs-d7606d13d94051ec47ec9509ba6e721edaecc0eb.tar.gz emacs-d7606d13d94051ec47ec9509ba6e721edaecc0eb.zip | |
(a) split lazy-lock-defer-time into lazy-lock-defer-time and lazy-lock-defer-on-the-fly, (b) add lazy-lock-defer-on-scrolling, (c) use these to choose one of lazy-lock-defer-line-after-change, lazy-lock-defer-rest-after-change, lazy-lock-fontify-line-after-change, lazy-lock-fontify-rest-after-change to add to after-change-functions, (d) use with-current-buffer rather than save-excursion, (e) avoid integer overflow in lazy-lock-percent-fontified.
| -rw-r--r-- | lisp/lazy-lock.el | 566 |
1 files changed, 394 insertions, 172 deletions
diff --git a/lisp/lazy-lock.el b/lisp/lazy-lock.el index d1c3d9e9d99..fffb0204c77 100644 --- a/lisp/lazy-lock.el +++ b/lisp/lazy-lock.el | |||
| @@ -4,7 +4,7 @@ | |||
| 4 | 4 | ||
| 5 | ;; Author: Simon Marshall <simon@gnu.ai.mit.edu> | 5 | ;; Author: Simon Marshall <simon@gnu.ai.mit.edu> |
| 6 | ;; Keywords: faces files | 6 | ;; Keywords: faces files |
| 7 | ;; Version: 2.06 | 7 | ;; Version: 2.07 |
| 8 | 8 | ||
| 9 | ;;; This file is part of GNU Emacs. | 9 | ;;; This file is part of GNU Emacs. |
| 10 | 10 | ||
| @@ -25,11 +25,10 @@ | |||
| 25 | 25 | ||
| 26 | ;;; Commentary: | 26 | ;;; Commentary: |
| 27 | 27 | ||
| 28 | ;; Purpose: | 28 | ;; Lazy Lock mode is a Font Lock support mode. |
| 29 | ;; | 29 | ;; It makes visiting buffers in Font Lock mode faster by making fontification |
| 30 | ;; To make visiting buffers in `font-lock-mode' faster by making fontification | 30 | ;; be demand-driven, deferred and stealthy, so that fontification only occurs |
| 31 | ;; be demand-driven, deferred and stealthy. | 31 | ;; when, and where, necessary. |
| 32 | ;; Fontification only occurs when, and where, necessary. | ||
| 33 | ;; | 32 | ;; |
| 34 | ;; See caveats and feedback below. | 33 | ;; See caveats and feedback below. |
| 35 | ;; See also the fast-lock package. (But don't use them at the same time!) | 34 | ;; See also the fast-lock package. (But don't use them at the same time!) |
| @@ -106,10 +105,11 @@ | |||
| 106 | ;; implemented by placing a function on `window-scroll-functions'. However, | 105 | ;; implemented by placing a function on `window-scroll-functions'. However, |
| 107 | ;; not all scrolling occurs when `window-start' has changed. A change in | 106 | ;; not all scrolling occurs when `window-start' has changed. A change in |
| 108 | ;; window size, e.g., via C-x 1, or a significant deletion, e.g., of a number | 107 | ;; window size, e.g., via C-x 1, or a significant deletion, e.g., of a number |
| 109 | ;; of lines, causes `window-end' to change without changing `window-start'. | 108 | ;; of lines, causes text previously invisible (i.e., after `window-end') to |
| 110 | ;; Arguably, these events are not scrolling events, but fontification must | 109 | ;; become visible without changing `window-start'. Arguably, these events are |
| 111 | ;; occur for lazy-lock.el to work. Hooks `window-size-change-functions' and | 110 | ;; not scrolling events, but fontification must occur for lazy-lock.el to work. |
| 112 | ;; `redisplay-end-trigger-functions' were added for these circumstances. | 111 | ;; Hooks `window-size-change-functions' and `redisplay-end-trigger-functions' |
| 112 | ;; were added for these circumstances. | ||
| 113 | ;; | 113 | ;; |
| 114 | ;; Ben Wing thinks these hooks are "horribly horribly kludgy", and implemented | 114 | ;; Ben Wing thinks these hooks are "horribly horribly kludgy", and implemented |
| 115 | ;; a `pre-idle-hook', a `mother-of-all-post-command-hooks', for XEmacs 19.14. | 115 | ;; a `pre-idle-hook', a `mother-of-all-post-command-hooks', for XEmacs 19.14. |
| @@ -147,16 +147,14 @@ | |||
| 147 | ;; or after given amounts of idle time. Thus, the feature deals with the above | 147 | ;; or after given amounts of idle time. Thus, the feature deals with the above |
| 148 | ;; problems (a), (b) and (c). Version 2 deferral and stealth are implemented | 148 | ;; problems (a), (b) and (c). Version 2 deferral and stealth are implemented |
| 149 | ;; by functions on Idle Timers. (A function on XEmacs' `pre-idle-hook' is | 149 | ;; by functions on Idle Timers. (A function on XEmacs' `pre-idle-hook' is |
| 150 | ;; similar to an Emacs Idle Timer function with a fixed zero second timeout. | 150 | ;; similar to an Emacs Idle Timer function with a fixed zero second timeout.) |
| 151 | ;; Hey, maybe I could stop using `window-scroll-functions' for demand-driven | ||
| 152 | ;; fontification and use a zero second Emacs Idle Timer instead? Only joking!) | ||
| 153 | 151 | ||
| 154 | ;; Caveats: | 152 | ;; Caveats: |
| 155 | ;; | 153 | ;; |
| 156 | ;; Lazy Lock mode does not work efficiently with Outline mode. This is because | 154 | ;; Lazy Lock mode does not work efficiently with Outline mode. |
| 157 | ;; when in Outline mode, although text may be hidden (not visible in the | 155 | ;; This is because when in Outline mode, although text may be not visible to |
| 158 | ;; window), the text is visible to Emacs Lisp code (not surprisingly) and Lazy | 156 | ;; you in the window, the text is visible to Emacs Lisp code (not surprisingly) |
| 159 | ;; Lock fontifies it mercilessly. Maybe it will be fixed one day. | 157 | ;; and Lazy Lock fontifies it mercilessly. Maybe it will be fixed one day. |
| 160 | ;; | 158 | ;; |
| 161 | ;; Because buffer text is not necessarily fontified, other packages that expect | 159 | ;; Because buffer text is not necessarily fontified, other packages that expect |
| 162 | ;; buffer text to be fontified in Font Lock mode either might not work as | 160 | ;; buffer text to be fontified in Font Lock mode either might not work as |
| @@ -174,13 +172,6 @@ | |||
| 174 | ;; | 172 | ;; |
| 175 | ;; Currently XEmacs does not have the features to support this version of | 173 | ;; Currently XEmacs does not have the features to support this version of |
| 176 | ;; lazy-lock.el. Maybe it will one day. | 174 | ;; lazy-lock.el. Maybe it will one day. |
| 177 | |||
| 178 | ;; Feedback: | ||
| 179 | ;; | ||
| 180 | ;; Feedback is welcome. | ||
| 181 | ;; To submit a bug report (or make comments) please use the mechanism provided: | ||
| 182 | ;; | ||
| 183 | ;; M-x lazy-lock-submit-bug-report RET | ||
| 184 | 175 | ||
| 185 | ;; History: | 176 | ;; History: |
| 186 | ;; | 177 | ;; |
| @@ -226,11 +217,22 @@ | |||
| 226 | ;; - Added `do-while' macro | 217 | ;; - Added `do-while' macro |
| 227 | ;; - Renamed `lazy-lock-let-buffer-state' macro to `save-buffer-state' | 218 | ;; - Renamed `lazy-lock-let-buffer-state' macro to `save-buffer-state' |
| 228 | ;; - Returned `lazy-lock-fontify-after-install' hack (Darren Hall hint) | 219 | ;; - Returned `lazy-lock-fontify-after-install' hack (Darren Hall hint) |
| 229 | ;; - Added `lazy-lock-defer-driven' functionality (Scott Byer hint) | 220 | ;; - Added `lazy-lock-defer-on-scrolling' functionality (Scott Byer hint) |
| 230 | ;; - Made `lazy-lock-mode' wrap `font-lock-support-mode' | 221 | ;; - Made `lazy-lock-mode' wrap `font-lock-support-mode' |
| 231 | ;; 2.05--2.06: | 222 | ;; 2.05--2.06: |
| 232 | ;; - Made `lazy-lock-fontify-after-defer' swap correctly (Scott Byer report) | 223 | ;; - Made `lazy-lock-fontify-after-defer' swap correctly (Scott Byer report) |
| 224 | ;; 2.06--2.07: | ||
| 225 | ;; - Added `lazy-lock-stealth-load' functionality (Rob Hooft hint) | ||
| 226 | ;; - Made `lazy-lock-unstall' call `lazy-lock-fontify-region' if needed | ||
| 227 | ;; - Made `lazy-lock-mode' call `lazy-lock-unstall' only if needed | ||
| 228 | ;; - Made `lazy-lock-defer-after-scroll' do `set-window-redisplay-end-trigger' | ||
| 229 | ;; - Added `lazy-lock-defer-contextually' functionality | ||
| 230 | ;; - Added `lazy-lock-defer-on-the-fly' from `lazy-lock-defer-time' | ||
| 231 | ;; - Renamed `lazy-lock-defer-driven' to `lazy-lock-defer-on-scrolling' | ||
| 232 | ;; - Removed `lazy-lock-submit-bug-report' and bade farewell | ||
| 233 | 233 | ||
| 234 | ;;; Code: | ||
| 235 | |||
| 234 | (require 'font-lock) | 236 | (require 'font-lock) |
| 235 | 237 | ||
| 236 | ;; Make sure lazy-lock.el is supported. | 238 | ;; Make sure lazy-lock.el is supported. |
| @@ -275,7 +277,38 @@ | |||
| 275 | The order of execution is thus BODY, TEST, BODY, TEST and so on | 277 | The order of execution is thus BODY, TEST, BODY, TEST and so on |
| 276 | until TEST returns nil." | 278 | until TEST returns nil." |
| 277 | (` (while (progn (,@ body) (, test))))) | 279 | (` (while (progn (,@ body) (, test))))) |
| 278 | (put 'do-while 'lisp-indent-function (get 'while 'lisp-indent-function))) | 280 | (put 'do-while 'lisp-indent-function (get 'while 'lisp-indent-function)) |
| 281 | ;; | ||
| 282 | ;; We use this for clarity and speed. Borrowed from a future Emacs. | ||
| 283 | (or (fboundp 'with-current-buffer) | ||
| 284 | (defmacro with-current-buffer (buffer &rest body) | ||
| 285 | "Execute the forms in BODY with BUFFER as the current buffer. | ||
| 286 | The value returned is the value of the last form in BODY." | ||
| 287 | (` (save-excursion (set-buffer (, buffer)) (,@ body))))) | ||
| 288 | (put 'with-current-buffer 'lisp-indent-function 1)) | ||
| 289 | |||
| 290 | ;(defun lazy-lock-submit-bug-report () | ||
| 291 | ; "Submit via mail a bug report on lazy-lock.el." | ||
| 292 | ; (interactive) | ||
| 293 | ; (let ((reporter-prompt-for-summary-p t)) | ||
| 294 | ; (reporter-submit-bug-report "simon@gnu.ai.mit.edu" "lazy-lock 2.07" | ||
| 295 | ; '(lazy-lock-minimum-size lazy-lock-defer-on-the-fly | ||
| 296 | ; lazy-lock-defer-on-scrolling lazy-lock-defer-contextually | ||
| 297 | ; lazy-lock-defer-time lazy-lock-stealth-time | ||
| 298 | ; lazy-lock-stealth-load lazy-lock-stealth-nice lazy-lock-stealth-lines | ||
| 299 | ; lazy-lock-stealth-verbose) | ||
| 300 | ; nil nil | ||
| 301 | ; (concat "Hi Si., | ||
| 302 | ; | ||
| 303 | ;I want to report a bug. I've read the `Bugs' section of `Info' on Emacs, so I | ||
| 304 | ;know how to make a clear and unambiguous report. To reproduce the bug: | ||
| 305 | ; | ||
| 306 | ;Start a fresh editor via `" invocation-name " -no-init-file -no-site-file'. | ||
| 307 | ;In the `*scratch*' buffer, evaluate:")))) | ||
| 308 | |||
| 309 | (defvar lazy-lock-mode nil) | ||
| 310 | (defvar lazy-lock-buffers nil) ; for deferral | ||
| 311 | (defvar lazy-lock-timers (cons nil nil)) ; for deferral and stealth | ||
| 279 | 312 | ||
| 280 | ;; User Variables: | 313 | ;; User Variables: |
| 281 | 314 | ||
| @@ -291,8 +324,21 @@ for buffers in Rmail mode, and size is irrelevant otherwise. | |||
| 291 | 324 | ||
| 292 | The value of this variable is used when Lazy Lock mode is turned on.") | 325 | The value of this variable is used when Lazy Lock mode is turned on.") |
| 293 | 326 | ||
| 294 | (defvar lazy-lock-defer-driven nil | 327 | (defvar lazy-lock-defer-on-the-fly t |
| 295 | "*If non-nil, means fontification should be defer-driven. | 328 | "*If non-nil, means fontification after a change should be deferred. |
| 329 | If nil, means on-the-fly fontification is performed. This means when changes | ||
| 330 | occur in the buffer, those areas are immediately fontified. | ||
| 331 | If a list, it should be a list of `major-mode' symbol names for which deferred | ||
| 332 | fontification should occur. The sense of the list is negated if it begins with | ||
| 333 | `not'. For example: | ||
| 334 | (c-mode c++-mode) | ||
| 335 | means that on-the-fly fontification is deferred for buffers in C and C++ modes | ||
| 336 | only, and deferral does not occur otherwise. | ||
| 337 | |||
| 338 | The value of this variable is used when Lazy Lock mode is turned on.") | ||
| 339 | |||
| 340 | (defvar lazy-lock-defer-on-scrolling nil | ||
| 341 | "*If non-nil, means fontification after a scroll should be deferred. | ||
| 296 | If nil, means demand-driven fontification is performed. This means when | 342 | If nil, means demand-driven fontification is performed. This means when |
| 297 | scrolling into unfontified areas of the buffer, those areas are immediately | 343 | scrolling into unfontified areas of the buffer, those areas are immediately |
| 298 | fontified. Thus scrolling never presents unfontified areas. However, since | 344 | fontified. Thus scrolling never presents unfontified areas. However, since |
| @@ -307,22 +353,32 @@ defer-driven. Thus scrolling never presents unfontified areas until the buffer | |||
| 307 | is first fontified, after which subsequent scrolling may present future buffer | 353 | is first fontified, after which subsequent scrolling may present future buffer |
| 308 | insertions momentarily unfontified. However, since fontification does not | 354 | insertions momentarily unfontified. However, since fontification does not |
| 309 | occur during scrolling after the buffer is first fontified, scrolling will | 355 | occur during scrolling after the buffer is first fontified, scrolling will |
| 310 | become faster. | 356 | become faster. (But, since contextual changes continually occur, such a value |
| 357 | makes little sense if `lazy-lock-defer-contextually' is non-nil.) | ||
| 358 | |||
| 359 | The value of this variable is used when Lazy Lock mode is turned on.") | ||
| 360 | |||
| 361 | (defvar lazy-lock-defer-contextually 'syntax-driven | ||
| 362 | "*If non-nil, means deferred fontification should be syntactically true. | ||
| 363 | If nil, means deferred fontification occurs only on those lines modified. This | ||
| 364 | means where modification on a line causes syntactic change on subsequent lines, | ||
| 365 | those subsequent lines are not refontified to reflect their new context. | ||
| 366 | If t, means deferred fontification occurs on those lines modified and all | ||
| 367 | subsequent lines. This means those subsequent lines are refontified to reflect | ||
| 368 | their new syntactic context, either immediately or when scrolling into them. | ||
| 369 | If any other value, e.g., `syntax-driven', means deferred syntactically true | ||
| 370 | fontification occurs only if syntactic fontification is performed using the | ||
| 371 | buffer mode's syntax table, i.e., only if `font-lock-keywords-only' is nil. | ||
| 311 | 372 | ||
| 312 | The value of this variable is used when Lazy Lock mode is turned on.") | 373 | The value of this variable is used when Lazy Lock mode is turned on.") |
| 313 | 374 | ||
| 314 | (defvar lazy-lock-defer-time | 375 | (defvar lazy-lock-defer-time |
| 315 | (if (featurep 'lisp-float-type) (/ (float 1) (float 4)) 1) | 376 | (if (featurep 'lisp-float-type) (/ (float 1) (float 3)) 1) |
| 316 | "*Time in seconds to delay before beginning deferred fontification. | 377 | "*Time in seconds to delay before beginning deferred fontification. |
| 317 | Deferred fontification occurs if there is no input within this time. | 378 | Deferred fontification occurs if there is no input within this time. |
| 318 | If nil, means fontification is never deferred. However, fontification occurs | 379 | If nil, means fontification is never deferred, regardless of the values of the |
| 319 | on-the-fly or during scrolling, which may be slow. | 380 | variables `lazy-lock-defer-on-the-fly', `lazy-lock-defer-on-scrolling' and |
| 320 | If a list, it should be of the form (MAJOR-MODES . TIME), where MAJOR-MODES is | 381 | `lazy-lock-defer-contextually'. |
| 321 | a list of `major-mode' symbols for which deferred fontification should occur. | ||
| 322 | The sense of the list is negated if it begins with `not'. For example: | ||
| 323 | ((c-mode c++-mode) . 0.25) | ||
| 324 | means that the deferral time is 0.25s for buffers in C or C++ modes, and | ||
| 325 | deferral does not occur otherwise. | ||
| 326 | 382 | ||
| 327 | The value of this variable is used when Lazy Lock mode is turned on.") | 383 | The value of this variable is used when Lazy Lock mode is turned on.") |
| 328 | 384 | ||
| @@ -339,19 +395,31 @@ Each iteration of stealth fontification can fontify this number of lines. | |||
| 339 | To speed up input response during stealth fontification, at the cost of stealth | 395 | To speed up input response during stealth fontification, at the cost of stealth |
| 340 | taking longer to fontify, you could reduce the value of this variable.") | 396 | taking longer to fontify, you could reduce the value of this variable.") |
| 341 | 397 | ||
| 398 | (defvar lazy-lock-stealth-load | ||
| 399 | (when (condition-case nil (load-average) (error)) 200) | ||
| 400 | "*Load in percentage above which stealth fontification is suspended. | ||
| 401 | Stealth fontification pauses when the system short-term load average (as | ||
| 402 | returned by the function `load-average' if supported) goes above this level, | ||
| 403 | thus reducing the demand that stealth fontification makes on the system. | ||
| 404 | If nil, means stealth fontification is never suspended. | ||
| 405 | To reduce machine load during stealth fontification, at the cost of stealth | ||
| 406 | taking longer to fontify, you could reduce the value of this variable. | ||
| 407 | See also `lazy-lock-stealth-nice'.") | ||
| 408 | |||
| 342 | (defvar lazy-lock-stealth-nice | 409 | (defvar lazy-lock-stealth-nice |
| 343 | (if (featurep 'lisp-float-type) (/ (float 1) (float 8)) 1) | 410 | (if (featurep 'lisp-float-type) (/ (float 1) (float 8)) 1) |
| 344 | "*Time in seconds to pause between chunks of stealth fontification. | 411 | "*Time in seconds to pause between chunks of stealth fontification. |
| 345 | Each iteration of stealth fontification is separated by this amount of time. | 412 | Each iteration of stealth fontification is separated by this amount of time, |
| 413 | thus reducing the demand that stealth fontification makes on the system. | ||
| 414 | If nil, means stealth fontification is never paused. | ||
| 346 | To reduce machine load during stealth fontification, at the cost of stealth | 415 | To reduce machine load during stealth fontification, at the cost of stealth |
| 347 | taking longer to fontify, you could increase the value of this variable.") | 416 | taking longer to fontify, you could increase the value of this variable. |
| 417 | See also `lazy-lock-stealth-load'.") | ||
| 348 | 418 | ||
| 349 | (defvar lazy-lock-stealth-verbose (not (null font-lock-verbose)) | 419 | (defvar lazy-lock-stealth-verbose |
| 420 | (when (featurep 'lisp-float-type) | ||
| 421 | (and font-lock-verbose (not lazy-lock-defer-contextually))) | ||
| 350 | "*If non-nil, means stealth fontification should show status messages.") | 422 | "*If non-nil, means stealth fontification should show status messages.") |
| 351 | |||
| 352 | (defvar lazy-lock-mode nil) | ||
| 353 | (defvar lazy-lock-buffers nil) ; for deferral | ||
| 354 | (defvar lazy-lock-timers (cons nil nil)) ; for deferral and stealth | ||
| 355 | 423 | ||
| 356 | ;; User Functions: | 424 | ;; User Functions: |
| 357 | 425 | ||
| @@ -365,65 +433,63 @@ automatically in your `~/.emacs' by: | |||
| 365 | 433 | ||
| 366 | When Lazy Lock mode is enabled, fontification can be lazy in a number of ways: | 434 | When Lazy Lock mode is enabled, fontification can be lazy in a number of ways: |
| 367 | 435 | ||
| 368 | - Demand-driven buffer fontification if `lazy-lock-minimum-size' is non-nil. | 436 | - Demand-driven buffer fontification if `lazy-lock-minimum-size' is non-nil. |
| 369 | This means initial fontification does not occur if the buffer is greater | 437 | This means initial fontification does not occur if the buffer is greater than |
| 370 | than `lazy-lock-minimum-size' characters in length. Instead, fontification | 438 | `lazy-lock-minimum-size' characters in length. Instead, fontification occurs |
| 371 | occurs when necessary, such as when scrolling through the buffer would | 439 | when necessary, such as when scrolling through the buffer would otherwise |
| 372 | otherwise reveal unfontified areas. This is useful if buffer fontification | 440 | reveal unfontified areas. This is useful if buffer fontification is too slow |
| 373 | is too slow for large buffers. | 441 | for large buffers. |
| 374 | 442 | ||
| 375 | - Defer-driven buffer fontification if `lazy-lock-defer-driven' is non-nil. | 443 | - Deferred scroll fontification if `lazy-lock-defer-on-scrolling' is non-nil. |
| 376 | This means all fontification is deferred, such as fontification that occurs | 444 | This means demand-driven fontification does not occur as you scroll. |
| 377 | when scrolling through the buffer would otherwise reveal unfontified areas. | 445 | Instead, fontification is deferred until after `lazy-lock-defer-time' seconds |
| 378 | Instead, these areas are seen momentarily unfontified. This is useful if | 446 | of Emacs idle time, while Emacs remains idle. This is useful if |
| 379 | demand-driven fontification is too slow to keep up with scrolling. | 447 | fontification is too slow to keep up with scrolling. |
| 380 | 448 | ||
| 381 | - Deferred on-the-fly fontification if `lazy-lock-defer-time' is non-nil. | 449 | - Deferred on-the-fly fontification if `lazy-lock-defer-on-the-fly' is non-nil. |
| 382 | This means on-the-fly fontification does not occur as you type. Instead, | 450 | This means on-the-fly fontification does not occur as you type. Instead, |
| 383 | fontification is deferred until after `lazy-lock-defer-time' seconds of | 451 | fontification is deferred until after `lazy-lock-defer-time' seconds of Emacs |
| 384 | Emacs idle time, while Emacs remains idle. This is useful if on-the-fly | 452 | idle time, while Emacs remains idle. This is useful if fontification is too |
| 385 | fontification is too slow to keep up with your typing. | 453 | slow to keep up with your typing. |
| 386 | 454 | ||
| 387 | - Stealthy buffer fontification if `lazy-lock-stealth-time' is non-nil. | 455 | - Deferred context fontification if `lazy-lock-defer-contextually' is non-nil. |
| 388 | This means remaining unfontified areas of buffers are fontified if Emacs has | 456 | This means fontification updates the buffer corresponding to true syntactic |
| 389 | been idle for `lazy-lock-stealth-time' seconds, while Emacs remains idle. | 457 | context, after `lazy-lock-defer-time' seconds of Emacs idle time, while Emacs |
| 390 | This is useful if any buffer has demand- or defer-driven fontification. | 458 | remains idle. Otherwise, fontification occurs on modified lines only, and |
| 391 | 459 | subsequent lines can remain fontified corresponding to previous syntactic | |
| 392 | See also variables `lazy-lock-stealth-lines', `lazy-lock-stealth-nice' and | 460 | contexts. This is useful where strings or comments span lines. |
| 393 | `lazy-lock-stealth-verbose' for stealth fontification. | 461 | |
| 394 | 462 | - Stealthy buffer fontification if `lazy-lock-stealth-time' is non-nil. | |
| 395 | Use \\[lazy-lock-submit-bug-report] to send bug reports or feedback." | 463 | This means remaining unfontified areas of buffers are fontified if Emacs has |
| 464 | been idle for `lazy-lock-stealth-time' seconds, while Emacs remains idle. | ||
| 465 | This is useful if any buffer has any deferred fontification. | ||
| 466 | |||
| 467 | Basic Font Lock mode on-the-fly fontification behaviour fontifies modified | ||
| 468 | lines only. Thus, if `lazy-lock-defer-contextually' is non-nil, Lazy Lock mode | ||
| 469 | on-the-fly fontification may fontify differently, albeit correctly. In any | ||
| 470 | event, to refontify some lines you can use \\[font-lock-fontify-block]. | ||
| 471 | |||
| 472 | Stealth fontification only occurs while the system remains unloaded. | ||
| 473 | If the system load rises above `lazy-lock-stealth-load' percent, stealth | ||
| 474 | fontification is suspended. Stealth fontification intensity is controlled via | ||
| 475 | the variable `lazy-lock-stealth-nice' and `lazy-lock-stealth-lines', and | ||
| 476 | verbosity is controlled via the variable `lazy-lock-stealth-verbose'." | ||
| 396 | (interactive "P") | 477 | (interactive "P") |
| 397 | (set (make-local-variable 'lazy-lock-mode) | 478 | (let* ((was-on lazy-lock-mode) |
| 398 | (and (not (memq 'lazy-lock-mode font-lock-inhibit-thing-lock)) | 479 | (now-on (unless (memq 'lazy-lock-mode font-lock-inhibit-thing-lock) |
| 399 | (if arg (> (prefix-numeric-value arg) 0) (not lazy-lock-mode)))) | 480 | (if arg (> (prefix-numeric-value arg) 0) (not was-on))))) |
| 400 | (cond ((and lazy-lock-mode (not font-lock-mode)) | 481 | (cond ((and now-on (not font-lock-mode)) |
| 401 | ;; Turned on `lazy-lock-mode' rather than `font-lock-mode'. | 482 | ;; Turned on `lazy-lock-mode' rather than `font-lock-mode'. |
| 402 | (let ((font-lock-support-mode 'lazy-lock-mode)) | 483 | (let ((font-lock-support-mode 'lazy-lock-mode)) |
| 403 | (font-lock-mode t))) | 484 | (font-lock-mode t))) |
| 404 | (lazy-lock-mode | 485 | (now-on |
| 405 | ;; Turn ourselves on. | 486 | ;; Turn ourselves on. |
| 406 | (lazy-lock-install)) | 487 | (set (make-local-variable 'lazy-lock-mode) t) |
| 407 | (t | 488 | (lazy-lock-install)) |
| 408 | ;; Turn ourselves off. | 489 | (was-on |
| 409 | (lazy-lock-unstall)))) | 490 | ;; Turn ourselves off. |
| 410 | 491 | (set (make-local-variable 'lazy-lock-mode) nil) | |
| 411 | (defun lazy-lock-submit-bug-report () | 492 | (lazy-lock-unstall))))) |
| 412 | "Submit via mail a bug report on lazy-lock.el." | ||
| 413 | (interactive) | ||
| 414 | (let ((reporter-prompt-for-summary-p t)) | ||
| 415 | (reporter-submit-bug-report "simon@gnu.ai.mit.edu" "lazy-lock 2.06" | ||
| 416 | '(lazy-lock-minimum-size lazy-lock-defer-driven lazy-lock-defer-time | ||
| 417 | lazy-lock-stealth-time lazy-lock-stealth-nice lazy-lock-stealth-lines | ||
| 418 | lazy-lock-stealth-verbose) | ||
| 419 | nil nil | ||
| 420 | (concat "Hi Si., | ||
| 421 | |||
| 422 | I want to report a bug. I've read the `Bugs' section of `Info' on Emacs, so I | ||
| 423 | know how to make a clear and unambiguous report. To reproduce the bug: | ||
| 424 | |||
| 425 | Start a fresh Emacs via `" invocation-name " -no-init-file -no-site-file'. | ||
| 426 | In the `*scratch*' buffer, evaluate:")))) | ||
| 427 | 493 | ||
| 428 | ;;;###autoload | 494 | ;;;###autoload |
| 429 | (defun turn-on-lazy-lock () | 495 | (defun turn-on-lazy-lock () |
| @@ -431,7 +497,12 @@ In the `*scratch*' buffer, evaluate:")))) | |||
| 431 | (lazy-lock-mode t)) | 497 | (lazy-lock-mode t)) |
| 432 | 498 | ||
| 433 | (defun lazy-lock-install () | 499 | (defun lazy-lock-install () |
| 434 | (let ((min-size (font-lock-value-in-major-mode lazy-lock-minimum-size))) | 500 | (let ((min-size (font-lock-value-in-major-mode lazy-lock-minimum-size)) |
| 501 | (defer-change (and lazy-lock-defer-time lazy-lock-defer-on-the-fly)) | ||
| 502 | (defer-scroll (and lazy-lock-defer-time lazy-lock-defer-on-scrolling)) | ||
| 503 | (defer-context (and lazy-lock-defer-time lazy-lock-defer-contextually | ||
| 504 | (or (eq lazy-lock-defer-contextually t) | ||
| 505 | (null font-lock-keywords-only))))) | ||
| 435 | ;; | 506 | ;; |
| 436 | ;; Tell Font Lock whether Lazy Lock will do fontification. | 507 | ;; Tell Font Lock whether Lazy Lock will do fontification. |
| 437 | (make-local-variable 'font-lock-fontified) | 508 | (make-local-variable 'font-lock-fontified) |
| @@ -449,39 +520,51 @@ In the `*scratch*' buffer, evaluate:")))) | |||
| 449 | ;; | 520 | ;; |
| 450 | ;; Add the fontification hooks. | 521 | ;; Add the fontification hooks. |
| 451 | (lazy-lock-install-hooks | 522 | (lazy-lock-install-hooks |
| 452 | (or (numberp lazy-lock-defer-time) | ||
| 453 | (if (eq (car (car lazy-lock-defer-time)) 'not) | ||
| 454 | (not (memq major-mode (cdr (car lazy-lock-defer-time)))) | ||
| 455 | (memq major-mode (car lazy-lock-defer-time)))) | ||
| 456 | font-lock-fontified | 523 | font-lock-fontified |
| 457 | (eq lazy-lock-defer-driven t)) | 524 | (cond ((eq (car-safe defer-change) 'not) |
| 525 | (not (memq major-mode (cdr defer-change)))) | ||
| 526 | ((listp defer-change) | ||
| 527 | (memq major-mode defer-change)) | ||
| 528 | (t | ||
| 529 | defer-change)) | ||
| 530 | (eq defer-scroll t) | ||
| 531 | defer-context) | ||
| 458 | ;; | 532 | ;; |
| 459 | ;; Add the fontification timers. | 533 | ;; Add the fontification timers. |
| 460 | (lazy-lock-install-timers | 534 | (lazy-lock-install-timers |
| 461 | (or (cdr-safe lazy-lock-defer-time) lazy-lock-defer-time) | 535 | (if (or defer-change defer-scroll defer-context) lazy-lock-defer-time) |
| 462 | lazy-lock-stealth-time))) | 536 | lazy-lock-stealth-time))) |
| 463 | 537 | ||
| 464 | (defun lazy-lock-install-hooks (deferring fontifying defer-driven) | 538 | (defun lazy-lock-install-hooks (fontifying |
| 539 | defer-change defer-scroll defer-context) | ||
| 465 | ;; | 540 | ;; |
| 466 | ;; Add hook if lazy-lock.el is deferring or is fontifying on scrolling. | 541 | ;; Add hook if lazy-lock.el is fontifying on scrolling or is deferring. |
| 467 | (when (or deferring fontifying) | 542 | (when (or fontifying defer-change defer-scroll defer-context) |
| 468 | (make-local-hook 'window-scroll-functions) | 543 | (make-local-hook 'window-scroll-functions) |
| 469 | (add-hook 'window-scroll-functions (if (and deferring defer-driven) | 544 | (add-hook 'window-scroll-functions (if defer-scroll |
| 470 | 'lazy-lock-defer-after-scroll | 545 | 'lazy-lock-defer-after-scroll |
| 471 | 'lazy-lock-fontify-after-scroll) | 546 | 'lazy-lock-fontify-after-scroll) |
| 472 | nil t)) | 547 | nil t)) |
| 473 | ;; | 548 | ;; |
| 474 | ;; Add hook if lazy-lock.el is not deferring and is fontifying. | 549 | ;; Add hook if lazy-lock.el is fontifying and is not deferring changes. |
| 475 | (when (and (not deferring) fontifying) | 550 | (when (and fontifying (not defer-change) (not defer-context)) |
| 476 | (make-local-hook 'before-change-functions) | 551 | (make-local-hook 'before-change-functions) |
| 477 | (add-hook 'before-change-functions 'lazy-lock-arrange-before-change nil t)) | 552 | (add-hook 'before-change-functions 'lazy-lock-arrange-before-change nil t)) |
| 478 | ;; | 553 | ;; |
| 479 | ;; Add hook if lazy-lock.el is deferring. | 554 | ;; Replace Font Lock mode hook. |
| 480 | (when deferring | 555 | (remove-hook 'after-change-functions 'font-lock-after-change-function t) |
| 481 | (remove-hook 'after-change-functions 'font-lock-after-change-function t) | 556 | (add-hook 'after-change-functions |
| 482 | (add-hook 'after-change-functions 'lazy-lock-defer-after-change nil t)) | 557 | (cond ((and defer-change defer-context) |
| 558 | 'lazy-lock-defer-rest-after-change) | ||
| 559 | (defer-change | ||
| 560 | 'lazy-lock-defer-line-after-change) | ||
| 561 | (defer-context | ||
| 562 | 'lazy-lock-fontify-rest-after-change) | ||
| 563 | (t | ||
| 564 | 'lazy-lock-fontify-line-after-change)) | ||
| 565 | nil t) | ||
| 483 | ;; | 566 | ;; |
| 484 | ;; Add package-specific hooks. | 567 | ;; Add package-specific hook. |
| 485 | (make-local-hook 'outline-view-change-hook) | 568 | (make-local-hook 'outline-view-change-hook) |
| 486 | (add-hook 'outline-view-change-hook 'lazy-lock-fontify-after-outline nil t)) | 569 | (add-hook 'outline-view-change-hook 'lazy-lock-fontify-after-outline nil t)) |
| 487 | 570 | ||
| @@ -506,6 +589,22 @@ In the `*scratch*' buffer, evaluate:")))) | |||
| 506 | 589 | ||
| 507 | (defun lazy-lock-unstall () | 590 | (defun lazy-lock-unstall () |
| 508 | ;; | 591 | ;; |
| 592 | ;; If Font Lock mode is still enabled, make sure that the buffer is | ||
| 593 | ;; fontified, and reinstall its hook. We must do this first. | ||
| 594 | (when font-lock-mode | ||
| 595 | (when (lazy-lock-unfontified-p) | ||
| 596 | (let ((verbose (if (numberp font-lock-verbose) | ||
| 597 | (> (buffer-size) font-lock-verbose) | ||
| 598 | font-lock-verbose))) | ||
| 599 | (if verbose (message "Fontifying %s..." (buffer-name))) | ||
| 600 | ;; Make sure we fontify etc. in the whole buffer. | ||
| 601 | (save-restriction | ||
| 602 | (widen) | ||
| 603 | (lazy-lock-fontify-region (point-min) (point-max))) | ||
| 604 | (if verbose (message "Fontifying %s...%s" (buffer-name) | ||
| 605 | (if (lazy-lock-unfontified-p) "quit" "done"))))) | ||
| 606 | (add-hook 'after-change-functions 'font-lock-after-change-function nil t)) | ||
| 607 | ;; | ||
| 509 | ;; Remove the text properties. | 608 | ;; Remove the text properties. |
| 510 | (lazy-lock-after-unfontify-buffer) | 609 | (lazy-lock-after-unfontify-buffer) |
| 511 | ;; | 610 | ;; |
| @@ -513,19 +612,33 @@ In the `*scratch*' buffer, evaluate:")))) | |||
| 513 | (remove-hook 'window-scroll-functions 'lazy-lock-fontify-after-scroll t) | 612 | (remove-hook 'window-scroll-functions 'lazy-lock-fontify-after-scroll t) |
| 514 | (remove-hook 'window-scroll-functions 'lazy-lock-defer-after-scroll t) | 613 | (remove-hook 'window-scroll-functions 'lazy-lock-defer-after-scroll t) |
| 515 | (remove-hook 'before-change-functions 'lazy-lock-arrange-before-change t) | 614 | (remove-hook 'before-change-functions 'lazy-lock-arrange-before-change t) |
| 516 | (remove-hook 'after-change-functions 'lazy-lock-defer-after-change t) | 615 | (remove-hook 'after-change-functions 'lazy-lock-fontify-line-after-change t) |
| 517 | (remove-hook 'outline-view-change-hook 'lazy-lock-fontify-after-outline t) | 616 | (remove-hook 'after-change-functions 'lazy-lock-fontify-rest-after-change t) |
| 518 | ;; | 617 | (remove-hook 'after-change-functions 'lazy-lock-defer-line-after-change t) |
| 519 | ;; If Font Lock mode is still enabled, reinstall its hook. | 618 | (remove-hook 'after-change-functions 'lazy-lock-defer-rest-after-change t) |
| 520 | (when font-lock-mode | 619 | (remove-hook 'outline-view-change-hook 'lazy-lock-fontify-after-outline t)) |
| 521 | (add-hook 'after-change-functions 'font-lock-after-change-function nil t))) | ||
| 522 | 620 | ||
| 523 | ;; Hook functions. | 621 | ;; Hook functions. |
| 524 | 622 | ||
| 623 | ;; Lazy Lock mode intervenes when (1) a previously invisible buffer region | ||
| 624 | ;; becomes visible, i.e., for demand- or defer-driven on-the-scroll | ||
| 625 | ;; fontification, (2) a buffer modification occurs, i.e., for defer-driven | ||
| 626 | ;; on-the-fly fontification, (3) Emacs becomes idle, i.e., for fontification of | ||
| 627 | ;; deferred fontification and stealth fontification, and (4) other special | ||
| 628 | ;; occasions. | ||
| 629 | |||
| 630 | ;; 1. There are three ways whereby this can happen. | ||
| 631 | ;; | ||
| 632 | ;; (a) Scrolling the window, either explicitly (e.g., `scroll-up') or | ||
| 633 | ;; implicitly (e.g., `search-forward'). Here, `window-start' changes. | ||
| 634 | ;; Fontification occurs by adding `lazy-lock-fontify-after-scroll' (for | ||
| 635 | ;; demand-driven fontification) or `lazy-lock-defer-after-scroll' (for | ||
| 636 | ;; defer-driven fontification) to the hook `window-scroll-functions'. | ||
| 637 | |||
| 525 | (defun lazy-lock-fontify-after-scroll (window window-start) | 638 | (defun lazy-lock-fontify-after-scroll (window window-start) |
| 526 | ;; Called from `window-scroll-functions'. | 639 | ;; Called from `window-scroll-functions'. |
| 527 | ;; Fontify WINDOW from WINDOW-START. We cannot use `window-end' so we work | 640 | ;; Fontify WINDOW from WINDOW-START following the scroll. We cannot use |
| 528 | ;; out what it would be via `vertical-motion'. | 641 | ;; `window-end' so we work out what it would be via `vertical-motion'. |
| 529 | (save-excursion | 642 | (save-excursion |
| 530 | (goto-char window-start) | 643 | (goto-char window-start) |
| 531 | (vertical-motion (window-height window) window) | 644 | (vertical-motion (window-height window) window) |
| @@ -534,21 +647,25 @@ In the `*scratch*' buffer, evaluate:")))) | |||
| 534 | ;; result in an unnecessary trigger after this if we did not cancel it now. | 647 | ;; result in an unnecessary trigger after this if we did not cancel it now. |
| 535 | (set-window-redisplay-end-trigger window nil)) | 648 | (set-window-redisplay-end-trigger window nil)) |
| 536 | 649 | ||
| 537 | (defun lazy-lock-fontify-after-trigger (window trigger-point) | 650 | (defun lazy-lock-defer-after-scroll (window window-start) |
| 538 | ;; Called from `redisplay-end-trigger-functions'. | 651 | ;; Called from `window-scroll-functions'. |
| 539 | ;; Fontify WINDOW from TRIGGER-POINT. We cannot use `window-end' so we work | 652 | ;; Defer fontification following the scroll. Save the current buffer so that |
| 540 | ;; out what it would be via `vertical-motion'. | 653 | ;; we subsequently fontify in all windows showing the buffer. |
| 541 | ;; We could probably just use `lazy-lock-fontify-after-scroll' without loss: | 654 | (unless (memq (current-buffer) lazy-lock-buffers) |
| 542 | ;; (lazy-lock-fontify-after-scroll window (window-start window)) | 655 | (push (current-buffer) lazy-lock-buffers)) |
| 543 | (save-excursion | 656 | ;; A prior deletion that did not cause scrolling, followed by a scroll, would |
| 544 | (goto-char (window-start window)) | 657 | ;; result in an unnecessary trigger after this if we did not cancel it now. |
| 545 | (vertical-motion (window-height window) window) | 658 | (set-window-redisplay-end-trigger window nil)) |
| 546 | (lazy-lock-fontify-region trigger-point (point)))) | 659 | |
| 660 | ;; (b) Resizing the window, either explicitly (e.g., `enlarge-window') or | ||
| 661 | ;; implicitly (e.g., `delete-other-windows'). Here, `window-end' changes. | ||
| 662 | ;; Fontification occurs by adding `lazy-lock-fontify-after-resize' to the | ||
| 663 | ;; hook `window-size-change-functions'. | ||
| 547 | 664 | ||
| 548 | (defun lazy-lock-fontify-after-resize (frame) | 665 | (defun lazy-lock-fontify-after-resize (frame) |
| 549 | ;; Called from `window-size-change-functions'. | 666 | ;; Called from `window-size-change-functions'. |
| 550 | ;; Fontify windows in FRAME. We cannot use `window-start' or `window-end' so | 667 | ;; Fontify windows in FRAME following the resize. We cannot use |
| 551 | ;; we fontify conservatively. | 668 | ;; `window-start' or `window-end' so we fontify conservatively. |
| 552 | (save-excursion | 669 | (save-excursion |
| 553 | (save-selected-window | 670 | (save-selected-window |
| 554 | (select-frame frame) | 671 | (select-frame frame) |
| @@ -559,6 +676,15 @@ In the `*scratch*' buffer, evaluate:")))) | |||
| 559 | (set-window-redisplay-end-trigger window nil))) | 676 | (set-window-redisplay-end-trigger window nil))) |
| 560 | 'nomini frame)))) | 677 | 'nomini frame)))) |
| 561 | 678 | ||
| 679 | ;; (c) Deletion in the buffer. Here, a `window-end' marker can become visible. | ||
| 680 | ;; Fontification occurs by adding `lazy-lock-arrange-before-change' to | ||
| 681 | ;; `before-change-functions' and `lazy-lock-fontify-after-trigger' to the | ||
| 682 | ;; hook `redisplay-end-trigger-functions'. Before every deletion, the | ||
| 683 | ;; marker `window-redisplay-end-trigger' position is set to the soon-to-be | ||
| 684 | ;; changed `window-end' position. If the marker becomes visible, | ||
| 685 | ;; `lazy-lock-fontify-after-trigger' gets called. Ouch. Note that we only | ||
| 686 | ;; have to deal with this eventuality if there is no on-the-fly deferral. | ||
| 687 | |||
| 562 | (defun lazy-lock-arrange-before-change (beg end) | 688 | (defun lazy-lock-arrange-before-change (beg end) |
| 563 | ;; Called from `before-change-functions'. | 689 | ;; Called from `before-change-functions'. |
| 564 | ;; Arrange that if text becomes visible it will be fontified (if a deletion | 690 | ;; Arrange that if text becomes visible it will be fontified (if a deletion |
| @@ -572,22 +698,63 @@ In the `*scratch*' buffer, evaluate:")))) | |||
| 572 | (set-marker (window-redisplay-end-trigger window) (window-end window)) | 698 | (set-marker (window-redisplay-end-trigger window) (window-end window)) |
| 573 | (setq windows (cdr windows)))))) | 699 | (setq windows (cdr windows)))))) |
| 574 | 700 | ||
| 575 | (defun lazy-lock-defer-after-scroll (window window-start) | 701 | (defun lazy-lock-fontify-after-trigger (window trigger-point) |
| 576 | ;; Called from `window-scroll-functions'. | 702 | ;; Called from `redisplay-end-trigger-functions'. |
| 577 | ;; Defer fontification following the scroll. Save the current buffer so that | 703 | ;; Fontify WINDOW from TRIGGER-POINT. We cannot use `window-end' so we work |
| 578 | ;; we subsequently fontify in all windows showing the buffer. | 704 | ;; out what it would be via `vertical-motion'. |
| 579 | (unless (memq (current-buffer) lazy-lock-buffers) | 705 | ;; We could probably just use `lazy-lock-fontify-after-scroll' without loss: |
| 580 | (push (current-buffer) lazy-lock-buffers))) | 706 | ;; (lazy-lock-fontify-after-scroll window (window-start window)) |
| 707 | (save-excursion | ||
| 708 | (goto-char (window-start window)) | ||
| 709 | (vertical-motion (window-height window) window) | ||
| 710 | (lazy-lock-fontify-region trigger-point (point)))) | ||
| 581 | 711 | ||
| 582 | (defun lazy-lock-defer-after-change (beg end old-len) | 712 | ;; 2. Modified text must be marked as unfontified so it can be identified and |
| 713 | ;; fontified later when Emacs is idle. Deferral occurs by adding one of | ||
| 714 | ;; `lazy-lock-fontify-*-after-change' (for on-the-fly fontification) or | ||
| 715 | ;; `lazy-lock-defer-*-after-change' (for deferred fontification) to the | ||
| 716 | ;; hook `after-change-functions'. | ||
| 717 | |||
| 718 | (defalias 'lazy-lock-fontify-line-after-change | ||
| 583 | ;; Called from `after-change-functions'. | 719 | ;; Called from `after-change-functions'. |
| 584 | ;; Defer fontification of the current line. Save the current buffer so that | 720 | ;; Fontify the current change. |
| 585 | ;; we subsequently fontify in all windows showing the buffer. | 721 | 'font-lock-after-change-function) |
| 722 | |||
| 723 | (defun lazy-lock-fontify-rest-after-change (beg end old-len) | ||
| 724 | ;; Called from `after-change-functions'. | ||
| 725 | ;; Fontify the current change and defer fontification of the rest of the | ||
| 726 | ;; buffer. Save the current buffer so that we subsequently fontify in all | ||
| 727 | ;; windows showing the buffer. | ||
| 728 | (lazy-lock-fontify-line-after-change beg end old-len) | ||
| 586 | (save-buffer-state nil | 729 | (save-buffer-state nil |
| 587 | (unless (memq (current-buffer) lazy-lock-buffers) | 730 | (unless (memq (current-buffer) lazy-lock-buffers) |
| 588 | (push (current-buffer) lazy-lock-buffers)) | 731 | (push (current-buffer) lazy-lock-buffers)) |
| 589 | (remove-text-properties | 732 | (remove-text-properties end (point-max) '(lazy-lock nil)))) |
| 590 | (max (1- beg) (point-min)) (min (1+ end) (point-max)) '(lazy-lock nil)))) | 733 | |
| 734 | (defun lazy-lock-defer-line-after-change (beg end old-len) | ||
| 735 | ;; Called from `after-change-functions'. | ||
| 736 | ;; Defer fontification of the current change. Save the current buffer so | ||
| 737 | ;; that we subsequently fontify in all windows showing the buffer. | ||
| 738 | (save-buffer-state nil | ||
| 739 | (unless (memq (current-buffer) lazy-lock-buffers) | ||
| 740 | (push (current-buffer) lazy-lock-buffers)) | ||
| 741 | (remove-text-properties (max (1- beg) (point-min)) | ||
| 742 | (min (1+ end) (point-max)) | ||
| 743 | '(lazy-lock nil)))) | ||
| 744 | |||
| 745 | (defun lazy-lock-defer-rest-after-change (beg end old-len) | ||
| 746 | ;; Called from `after-change-functions'. | ||
| 747 | ;; Defer fontification of the rest of the buffer. Save the current buffer so | ||
| 748 | ;; that we subsequently fontify in all windows showing the buffer. | ||
| 749 | (save-buffer-state nil | ||
| 750 | (unless (memq (current-buffer) lazy-lock-buffers) | ||
| 751 | (push (current-buffer) lazy-lock-buffers)) | ||
| 752 | (remove-text-properties (max (1- beg) (point-min)) | ||
| 753 | (point-max) | ||
| 754 | '(lazy-lock nil)))) | ||
| 755 | |||
| 756 | ;; 3. Deferred fontification and stealth fontification are done from these two | ||
| 757 | ;; functions. They are set up as Idle Timers. | ||
| 591 | 758 | ||
| 592 | (defun lazy-lock-fontify-after-defer () | 759 | (defun lazy-lock-fontify-after-defer () |
| 593 | ;; Called from `timer-idle-list'. | 760 | ;; Called from `timer-idle-list'. |
| @@ -599,7 +766,7 @@ In the `*scratch*' buffer, evaluate:")))) | |||
| 599 | (setq windows (cdr windows))) | 766 | (setq windows (cdr windows))) |
| 600 | (setq lazy-lock-buffers (cdr lazy-lock-buffers)))) | 767 | (setq lazy-lock-buffers (cdr lazy-lock-buffers)))) |
| 601 | ;; Add hook if fontification should now be defer-driven in this buffer. | 768 | ;; Add hook if fontification should now be defer-driven in this buffer. |
| 602 | (when (and lazy-lock-mode lazy-lock-defer-driven | 769 | (when (and lazy-lock-mode lazy-lock-defer-on-scrolling |
| 603 | (memq 'lazy-lock-fontify-after-scroll window-scroll-functions) | 770 | (memq 'lazy-lock-fontify-after-scroll window-scroll-functions) |
| 604 | (not (or (input-pending-p) (lazy-lock-unfontified-p)))) | 771 | (not (or (input-pending-p) (lazy-lock-unfontified-p)))) |
| 605 | (remove-hook 'window-scroll-functions 'lazy-lock-fontify-after-scroll t) | 772 | (remove-hook 'window-scroll-functions 'lazy-lock-fontify-after-scroll t) |
| @@ -617,19 +784,30 @@ In the `*scratch*' buffer, evaluate:")))) | |||
| 617 | (if (not (and lazy-lock-mode (lazy-lock-unfontified-p))) | 784 | (if (not (and lazy-lock-mode (lazy-lock-unfontified-p))) |
| 618 | (setq continue (not (input-pending-p))) | 785 | (setq continue (not (input-pending-p))) |
| 619 | ;; Fontify regions in this buffer while there is no input. | 786 | ;; Fontify regions in this buffer while there is no input. |
| 620 | (do-while (and (lazy-lock-unfontified-p) | 787 | (do-while (and (lazy-lock-unfontified-p) continue) |
| 621 | (setq continue (sit-for lazy-lock-stealth-nice))) | 788 | (if (and lazy-lock-stealth-load |
| 622 | (when lazy-lock-stealth-verbose | 789 | (> (car (load-average)) lazy-lock-stealth-load)) |
| 623 | (if message | 790 | ;; Wait a while before continuing with the loop. |
| 624 | (message "Fontifying stealthily... %2d%% of %s" | 791 | (progn |
| 625 | (lazy-lock-percent-fontified) (buffer-name)) | 792 | (when message |
| 626 | (message "Fontifying stealthily...") | 793 | (message "Fontifying stealthily...suspended") |
| 627 | (setq message t))) | 794 | (setq message nil)) |
| 628 | (lazy-lock-fontify-chunk))) | 795 | (setq continue (sit-for (or lazy-lock-stealth-time 30)))) |
| 796 | ;; Fontify a chunk. | ||
| 797 | (when lazy-lock-stealth-verbose | ||
| 798 | (if message | ||
| 799 | (message "Fontifying stealthily... %2d%% of %s" | ||
| 800 | (lazy-lock-percent-fontified) (buffer-name)) | ||
| 801 | (message "Fontifying stealthily...") | ||
| 802 | (setq message t))) | ||
| 803 | (lazy-lock-fontify-chunk) | ||
| 804 | (setq continue (sit-for (or lazy-lock-stealth-nice 0)))))) | ||
| 629 | (setq buffers (cdr buffers)))) | 805 | (setq buffers (cdr buffers)))) |
| 630 | (when message | 806 | (when message |
| 631 | (message "Fontifying stealthily...%s" (if continue "done" "quit")))))) | 807 | (message "Fontifying stealthily...%s" (if continue "done" "quit")))))) |
| 632 | 808 | ||
| 809 | ;; 4. Special circumstances. | ||
| 810 | |||
| 633 | (defun lazy-lock-fontify-after-outline () | 811 | (defun lazy-lock-fontify-after-outline () |
| 634 | ;; Called from `outline-view-change-hook'. | 812 | ;; Called from `outline-view-change-hook'. |
| 635 | ;; Fontify windows showing the current buffer, as its visibility has changed. | 813 | ;; Fontify windows showing the current buffer, as its visibility has changed. |
| @@ -716,16 +894,14 @@ In the `*scratch*' buffer, evaluate:")))) | |||
| 716 | (defun lazy-lock-fontify-window (window) | 894 | (defun lazy-lock-fontify-window (window) |
| 717 | ;; Fontify in WINDOW between `window-start' and `window-end'. | 895 | ;; Fontify in WINDOW between `window-start' and `window-end'. |
| 718 | ;; We can only do this when we can use `window-start' and `window-end'. | 896 | ;; We can only do this when we can use `window-start' and `window-end'. |
| 719 | (save-excursion | 897 | (with-current-buffer (window-buffer window) |
| 720 | (set-buffer (window-buffer window)) | ||
| 721 | (lazy-lock-fontify-region (window-start window) (window-end window)))) | 898 | (lazy-lock-fontify-region (window-start window) (window-end window)))) |
| 722 | 899 | ||
| 723 | (defun lazy-lock-fontify-conservatively (window) | 900 | (defun lazy-lock-fontify-conservatively (window) |
| 724 | ;; Fontify in WINDOW conservatively around point. | 901 | ;; Fontify in WINDOW conservatively around point. |
| 725 | ;; Where we cannot use `window-start' and `window-end' we do `window-height' | 902 | ;; Where we cannot use `window-start' and `window-end' we do `window-height' |
| 726 | ;; lines around point. That way we guarantee to have done enough. | 903 | ;; lines around point. That way we guarantee to have done enough. |
| 727 | (save-excursion | 904 | (with-current-buffer (window-buffer window) |
| 728 | (set-buffer (window-buffer window)) | ||
| 729 | (lazy-lock-fontify-region | 905 | (lazy-lock-fontify-region |
| 730 | (save-excursion | 906 | (save-excursion |
| 731 | (vertical-motion (- (window-height window)) window) (point)) | 907 | (vertical-motion (- (window-height window)) window) (point)) |
| @@ -742,13 +918,15 @@ In the `*scratch*' buffer, evaluate:")))) | |||
| 742 | ;; Return the percentage (of characters) of the buffer that are fontified. | 918 | ;; Return the percentage (of characters) of the buffer that are fontified. |
| 743 | (save-restriction | 919 | (save-restriction |
| 744 | (widen) | 920 | (widen) |
| 745 | (let ((beg (point-min)) (end (point-max)) (size 0) next) | 921 | (let ((beg (point-min)) (size 0) next) |
| 746 | ;; Find where the next fontified region begins. | 922 | ;; Find where the next fontified region begins. |
| 747 | (while (setq beg (text-property-any beg end 'lazy-lock t)) | 923 | (while (setq beg (text-property-any beg (point-max) 'lazy-lock t)) |
| 748 | (setq next (or (text-property-any beg end 'lazy-lock nil) end) | 924 | (setq next (or (text-property-any beg (point-max) 'lazy-lock nil) |
| 749 | size (+ size (- next beg)) | 925 | (point-max))) |
| 750 | beg next)) | 926 | (incf size (- next beg)) |
| 751 | (/ (* size 100) (buffer-size))))) | 927 | (setq beg next)) |
| 928 | ;; Float because using integer multiplication will frequently overflow. | ||
| 929 | (truncate (* (/ (float size) (point-max)) 100))))) | ||
| 752 | 930 | ||
| 753 | ;; Version dependent workarounds and fixes. | 931 | ;; Version dependent workarounds and fixes. |
| 754 | 932 | ||
| @@ -784,6 +962,50 @@ In the `*scratch*' buffer, evaluate:")))) | |||
| 784 | (while lazy-lock-install | 962 | (while lazy-lock-install |
| 785 | (mapcar 'lazy-lock-fontify-conservatively | 963 | (mapcar 'lazy-lock-fontify-conservatively |
| 786 | (get-buffer-window-list (pop lazy-lock-install) 'nomini t))))) | 964 | (get-buffer-window-list (pop lazy-lock-install) 'nomini t))))) |
| 965 | |||
| 966 | (when (consp lazy-lock-defer-time) | ||
| 967 | ;; | ||
| 968 | ;; In 2.06.04 and below, `lazy-lock-defer-time' could specify modes and time. | ||
| 969 | (with-output-to-temp-buffer "*Help*" | ||
| 970 | (princ "The value of the variable `lazy-lock-defer-time' was\n ") | ||
| 971 | (princ lazy-lock-defer-time) | ||
| 972 | (princ "\n") | ||
| 973 | (princ "This variable cannot now be a list of modes and time, ") | ||
| 974 | (princ "so instead use the forms:\n") | ||
| 975 | (princ " (setq lazy-lock-defer-time ") | ||
| 976 | (princ (cdr lazy-lock-defer-time)) | ||
| 977 | (princ ")\n") | ||
| 978 | (princ " (setq lazy-lock-defer-on-the-fly '") | ||
| 979 | (princ (car lazy-lock-defer-time)) | ||
| 980 | (princ ")\n") | ||
| 981 | (princ "in your ~/.emacs. ") | ||
| 982 | (princ "The above forms have been evaluated for this editor session,\n") | ||
| 983 | (princ "but you should change your ~/.emacs now.")) | ||
| 984 | (setq lazy-lock-defer-on-the-fly (car lazy-lock-defer-time) | ||
| 985 | lazy-lock-defer-time (cdr lazy-lock-defer-time))) | ||
| 986 | |||
| 987 | (when (boundp 'lazy-lock-defer-driven) | ||
| 988 | ;; | ||
| 989 | ;; In 2.06.04 and below, `lazy-lock-defer-driven' was the variable name. | ||
| 990 | (with-output-to-temp-buffer "*Help*" | ||
| 991 | (princ "The value of the variable `lazy-lock-defer-driven' is set to ") | ||
| 992 | (if (memq lazy-lock-defer-driven '(nil t)) | ||
| 993 | (princ lazy-lock-defer-driven) | ||
| 994 | (princ "`") | ||
| 995 | (princ lazy-lock-defer-driven) | ||
| 996 | (princ "'")) | ||
| 997 | (princ ".\n") | ||
| 998 | (princ "This variable is now called `lazy-lock-defer-on-scrolling',\n") | ||
| 999 | (princ "so instead use the form:\n") | ||
| 1000 | (princ " (setq lazy-lock-defer-on-scrolling ") | ||
| 1001 | (unless (memq lazy-lock-defer-driven '(nil t)) | ||
| 1002 | (princ "'")) | ||
| 1003 | (princ lazy-lock-defer-driven) | ||
| 1004 | (princ ")\n") | ||
| 1005 | (princ "in your ~/.emacs. ") | ||
| 1006 | (princ "The above form has been evaluated for this editor session,\n") | ||
| 1007 | (princ "but you should change your ~/.emacs now.")) | ||
| 1008 | (setq lazy-lock-defer-on-scrolling lazy-lock-defer-driven)) | ||
| 787 | 1009 | ||
| 788 | ;; Possibly absent. | 1010 | ;; Possibly absent. |
| 789 | 1011 | ||