From d1f16ed9758409c6bd289a40ca5360c9c4ebba5f Mon Sep 17 00:00:00 2001 From: Ted Tibbetts Date: Tue, 22 Mar 2011 22:55:02 -0300 Subject: [PATCH 1/3] Added update mode switching. Created the `thorough` and `onwrite` profiles. These profiles govern the hooks -- autocommands and mappings -- that jslint.vim will respond to with update events. It is possible to switch a buffer's update profile with the new `:JSLintUpdateMode` command. The `thorough` profile, enabled by default, sets up buffers as they have been set up. It may be useful to people with slow machines, large JS scripts, and/or slow JS interpreters to have the lint checked less often, so I added the `onwrite` profile. Use of the `onwrite` profile alleviates issues I was having where the quickfix entries would not work properly: About half of the time, quickfix entry selection -- via `:cc`, pressing on a qf entry, etc. -- would go to the wrong line. The cursor would end up on the line of another entry in the quickfix list. Disabling the BufEnter autocommand fixes this. --- ftplugin/javascript/jslint.vim | 152 ++++++++++++++++++++++++++++----- 1 file changed, 132 insertions(+), 20 deletions(-) diff --git a/ftplugin/javascript/jslint.vim b/ftplugin/javascript/jslint.vim index 8753829..03f6a83 100755 --- a/ftplugin/javascript/jslint.vim +++ b/ftplugin/javascript/jslint.vim @@ -7,6 +7,13 @@ " let g:JSLintHighlightErrorLine = 0 " in your .vimrc " +" g:JSLintUpdateProfile [String; default='thorough']: +" Determines when updates to JSLint's state will happen. +" 'thorough': Update on virtually all events which can change the buffer. +" 'onwrite': Just update when the buffer is written. +" This variable determines the setting for new buffers; +" to choose an update mode for existing buffers, use `:JSLintUpdateMode`. + if exists("b:did_jslint_plugin") finish else @@ -15,27 +22,137 @@ endif let s:install_dir = expand(':p:h') -au BufLeave call s:JSLintClear() - -au BufEnter call s:JSLint() -au InsertLeave call s:JSLint() -"au InsertEnter call s:JSLint() -au BufWritePost call s:JSLint() -" due to http://tech.groups.yahoo.com/group/vimdev/message/52115 -if(!has("win32") || v:version>702) - au CursorHold call s:JSLint() - au CursorHoldI call s:JSLint() +if !exists("g:JSLintHighlightErrorLine") + let g:JSLintHighlightErrorLine = 1 +endif - au CursorHold call s:GetJSLintMessage() +if !exists('g:JSLintUpdateProfile') + let g:JSLintUpdateProfile = 'thorough' endif -au CursorMoved call s:GetJSLintMessage() -if !exists("g:JSLintHighlightErrorLine") - let g:JSLintHighlightErrorLine = 1 +if !exists('s:update') + " Controls the overall update functionality: + " which autocommands and mappings will trigger hooks. + " The command JSLintUpdateMode + " controls which update mode is used for the current buffer. + " g:JSLintUpdateProfile will be used by default. + let s:update = {} + + " Each profile must contain a Setup method + " and can contain a Cleanup function. + let s:update.profiles = { 'thorough': {} + \ , 'onwrite': {} + \ } + + " Returns [profile_name, profile]. + " a:1, if given, will select the profile. + " Otherwise, it will default to `g:JSLintUpdateProfile` + " unless there is a buffer profile already set. + function s:update.GetProfile(...) + let profile_name = a:0 ? a:1 + \ : exists('b:jslint_update_profile') ? b:jslint_update_profile + \ : g:JSLintUpdateProfile + + if !exists('self.profiles[profile_name]') + throw printf('Non-existent JSLint update profile "%s"', profile_name) + endif + + return [profile_name, s:update.profiles[profile_name]] + endfunction + + " Change the profile used for this buffer to a new one. + " Parameters as GetProfile. + " It calls the current profile's cleanup routine if it exists. + " Autocommands are cleaned up in addition to the effects of that call. + " `b:jslint_update_profile` is updated + " with the name of the selected profile. + function s:update.SelectProfile(...) + let current = self.GetProfile()[1] + + let [profile_name, profile] = call(self.GetProfile, a:000, self) + + if exists('b:jslint_update_profile') + \ && b:jslint_update_profile == profile_name + return + endif + + if exists('b:jslint_update_profile') + au! jslint * + if exists('*current.Cleanup') + call current.Cleanup() + unlet b:jslint_update_profile + endif + endif + + try + let b:jslint_update_profile = profile_name + augroup jslint + call profile.Setup() + finally + augroup END + endtry + endfunction + + " Profiles + function s:update.profiles.thorough.Setup() + au BufLeave call s:JSLintClear() + + au BufEnter call s:JSLint() + au InsertLeave call s:JSLint() + "au InsertEnter call s:JSLint() + au BufWritePost call s:JSLint() + + " due to http://tech.groups.yahoo.com/group/vimdev/message/52115 + if(!has("win32") || v:version>702) + au CursorHold call s:JSLint() + au CursorHoldI call s:JSLint() + + au CursorHold call s:GetJSLintMessage() + endif + + au CursorMoved call s:GetJSLintMessage() + + noremap dd dd:JSLintUpdate + noremap dw dw:JSLintUpdate + noremap u u:JSLintUpdate + noremap :JSLintUpdate + endfunct + + " Handle cleanup except for autocommands + function s:update.profiles.thorough.Cleanup() + let mappings = ['dd', 'dw', 'u', ''] + for mapping in mappings + try + exec 'unmap ' mapping + catch /^E31:/ + endtry + endfor + endfunction + + function s:update.profiles.onwrite.Setup() + au BufWrite call s:JSLint() + + au CursorMoved call s:GetJSLintMessage() + endfunction + + + " :JSLintUpdateMode + " Displays or switches the update profile for this buffer. + function s:CompleteUpdateProfiles(...) + return join(keys(s:update.profiles), "\n") + endfunction + command -buffer -complete=custom,s:CompleteUpdateProfiles -nargs=? + \ JSLintUpdateMode + \ exec == '' + \ ? 'echo s:update.GetProfile()[0]' + \ : 'call s:update.SelectProfile()' endif +exec 'JSLintUpdateMode' g:JSLintUpdateProfile + + if !exists("*s:JSLintUpdate") function s:JSLintUpdate() silent call s:JSLint() @@ -43,18 +160,13 @@ if !exists("*s:JSLintUpdate") endfunction endif -if !exists(":JSLintUpdate") +if exists(":JSLintUpdate") != 2 command JSLintUpdate :call s:JSLintUpdate() endif if !exists(":JSLintToggle") command JSLintToggle :let b:jslint_disabled = exists('b:jslint_disabled') ? b:jslint_disabled ? 0 : 1 : 1 endif -noremap dd dd:JSLintUpdate -noremap dw dw:JSLintUpdate -noremap u u:JSLintUpdate -noremap :JSLintUpdate - " Set up command and parameters if has("win32") let s:cmd = 'cscript /NoLogo ' From a51bf88b3852084e641cda45098c59ba3ee1db2d Mon Sep 17 00:00:00 2001 From: Ted Tibbetts Date: Tue, 22 Mar 2011 23:30:13 -0300 Subject: [PATCH 2/3] Arranged for JSLint() to be run on file open with `onwrite` update profile active. --- ftplugin/javascript/jslint.vim | 6 ++++-- 1 file changed, 4 insertions(+), 2 deletions(-) diff --git a/ftplugin/javascript/jslint.vim b/ftplugin/javascript/jslint.vim index 03f6a83..a876422 100755 --- a/ftplugin/javascript/jslint.vim +++ b/ftplugin/javascript/jslint.vim @@ -135,6 +135,8 @@ if !exists('s:update') au BufWrite call s:JSLint() au CursorMoved call s:GetJSLintMessage() + + call s:JSLint() endfunction @@ -150,8 +152,6 @@ if !exists('s:update') \ : 'call s:update.SelectProfile()' endif -exec 'JSLintUpdateMode' g:JSLintUpdateProfile - if !exists("*s:JSLintUpdate") function s:JSLintUpdate() @@ -378,3 +378,5 @@ if !exists("*s:ActivateJSLintQuickFixWindow") endfunction endif + +exec 'JSLintUpdateMode' g:JSLintUpdateProfile From 4fb24b8b89700c69fa15560a2c70eadbc1dcef02 Mon Sep 17 00:00:00 2001 From: Ted Tibbetts Date: Wed, 23 Mar 2011 03:02:37 -0300 Subject: [PATCH 3/3] Fixed declaration of `:JSLintUpdateMode` Moved out of `s:update` existence check block. --- ftplugin/javascript/jslint.vim | 3 +++ 1 file changed, 3 insertions(+) diff --git a/ftplugin/javascript/jslint.vim b/ftplugin/javascript/jslint.vim index a876422..b0f70cd 100755 --- a/ftplugin/javascript/jslint.vim +++ b/ftplugin/javascript/jslint.vim @@ -145,6 +145,9 @@ if !exists('s:update') function s:CompleteUpdateProfiles(...) return join(keys(s:update.profiles), "\n") endfunction +endif + +if exists(':JSLintUpdateMode') != 2 command -buffer -complete=custom,s:CompleteUpdateProfiles -nargs=? \ JSLintUpdateMode \ exec == ''