1
0
mirror of https://github.com/chylex/IntelliJ-IdeaVim.git synced 2025-08-17 16:31:45 +02:00

Compare commits

...

124 Commits

Author SHA1 Message Date
Alex Plate
3881b905be Update CHANGES.md 2020-11-12 10:51:57 +03:00
Alex Plate
073c62f868 Update version on TeamCity 2020-11-12 10:50:25 +03:00
Alex Plate
d8e0f26bea Revert "Unmute falling tests"
This reverts commit 0296cae7
2020-11-12 10:48:54 +03:00
Alex Plate
04c24ab5d0 Run manual tests 2020-11-12 10:38:02 +03:00
Alex Plate
bfb0ba1ab9 Update emulated plugins 2020-11-12 10:31:11 +03:00
Alex Plate
fb7d48af1f Update IDE actions section in README 2020-11-12 10:11:33 +03:00
Alex Plate
559989ce4b Remove all To Be Released labels 2020-11-12 10:03:56 +03:00
Alex Plate
81f59e3c18 Update plugin.xml 2020-11-12 10:03:04 +03:00
Alex Plate
b6adf9f7a9 Rename ideaenabledbufs to ideavimsupport 2020-11-12 09:45:29 +03:00
Alex Plate
b972a01cf0 Add merged PR to changes 2020-11-12 09:41:57 +03:00
Alex Plate
0296cae712 Unmute falling tests 2020-11-12 09:39:09 +03:00
Matt Ellis
c38b18e16b Prevent inlays causing scrolling to stick 2020-11-12 09:37:55 +03:00
Matt Ellis
8d65c3ed26 Limit how much of an inlay is shown when scrolling 2020-11-12 09:37:55 +03:00
Matt Ellis
995bb966ad Reposition cursor when scrolloff changes 2020-11-12 09:37:55 +03:00
Matt Ellis
dbda1a76ca [VIM-2158] Fix scrolling when scrolloff is greater than half screen height, but less than full screen height 2020-11-12 09:37:55 +03:00
Alex Plate
ed6f990d9a Remove some qodana inspections 2020-11-06 21:39:37 +03:00
Alex Plate
4f86d9cc77 Correct visual mode exiting when after line end 2020-11-06 20:26:26 +03:00
Alex Plate
d55774abab Use vimForEachCaret 2020-11-06 20:21:05 +03:00
Alex Plate
d5591ba08d Update qodana profile 2020-11-06 20:00:21 +03:00
Alex Plate
f67d483c4e Exclude next method from property based testing 2020-11-06 19:48:33 +03:00
Alex Plate
f26ddd4a27 Fix exception in aW 2020-11-06 19:12:40 +03:00
Alex Plate
dbbea642bc Add inspection profiles to the repository 2020-11-06 18:40:02 +03:00
Alex Plate
0539e39977 Fix <C-\><C-N> 2020-11-06 11:16:13 +03:00
Alex Plate
65235d32a1 Fix exception for ]b command 2020-11-06 10:36:03 +03:00
Alex Plate
ecfcdf5a8c Update intellij gradle plugin 2020-11-06 10:06:25 +03:00
Alex Plate
cf127ba7f9 Update plugin description 2020-11-06 09:37:01 +03:00
Alex Plate
1fba77d925 Update getName description 2020-11-05 11:31:41 +03:00
Alex Plate
5752b116f6 Fix plugin.xml 2020-11-04 13:04:36 +03:00
Alex Plate
cdf7fd8ce6 Update markdown to slack version 2020-11-03 12:14:58 +03:00
Alex Plate
8fe07e7b20 Verify plugin only against last major versions of IJ 2020-11-03 11:26:32 +03:00
Alex Plate
b800237606 Refactor common extension test 2020-11-03 11:24:34 +03:00
Alex Plate
fed02e5b8a Update plugin.xml 2020-11-03 11:20:22 +03:00
Alex Plate
2d4d3e9410 Update markdown to slack parser version 2020-11-03 11:20:21 +03:00
Alex Pláte
880d4c6888 Update CONTRIBUTING.md 2020-11-02 14:16:44 +03:00
Alex Plate
6a3d606032 New extension registration process
The new process gives as lazy loading of extension classes
2020-11-01 03:30:00 +03:00
Alex Plate
612a86c4d9 Add new option to enable extensions 2020-11-01 00:51:22 +03:00
Alex Plate
14abc25c01 Update detekt config 2020-11-01 00:47:05 +03:00
Alex Plate
52673d1a02 Remove unnecessary semicolon 2020-10-31 22:04:20 +03:00
Alex Plate
b7caee119e Rename detekt folder 2020-10-31 21:44:53 +03:00
Alex Plate
a148446912 Change order of checks 2020-10-31 19:43:19 +03:00
Alex Plate
1ee9075976 Inline findParentByCondition 2020-10-31 19:40:48 +03:00
Alex Plate
b03627a110 Add info about prepared configurations to contributing guide 2020-10-31 19:27:06 +03:00
Alex Plate
04ac0ab743 [TC] Extract plugin verification into the separate build 2020-10-31 19:21:12 +03:00
Alex Plate
e7aa985ad5 Add run configurations 2020-10-31 18:49:37 +03:00
Alex Plate
4177f4e4f3 Rename ideavim.neovim.test to ideavim.nvim.test 2020-10-31 18:44:53 +03:00
Alex Plate
c1e415b76a [TC] Update nvim config 2020-10-31 18:44:16 +03:00
Alex Plate
8ae656dee3 Remove unused export 2020-10-31 18:42:35 +03:00
aleksei.plate
d48576f48a TeamCity change in 'IntelliJ IDEA plugins / IdeaVim' project: parameters of 'NVIM' build configuration were updated 2020-10-31 15:42:17 +00:00
Alex Plate
c0c5075072 [TC] Use -P to set env var 2020-10-31 18:16:41 +03:00
Alex Plate
59d106b8c4 [TC] Update nvim config 2020-10-31 17:42:58 +03:00
Alex Plate
d96c313ecb [TC] Add execution privilege to nvim 2020-10-31 17:12:22 +03:00
Alex Plate
212c708150 [TC] Use env variable to set nvim path 2020-10-31 17:00:16 +03:00
Alex Plate
3739eb173e Remove nvim branch 2020-10-31 16:54:56 +03:00
Alex Plate
0d3ecce8a2 Read env variable to get nvim path 2020-10-31 16:53:09 +03:00
Alex Plate
164d7a4200 [TC] Update nvim config 2020-10-31 16:45:18 +03:00
Alex Plate
1258e602e6 [TC] Reformat code 2020-10-31 16:38:06 +03:00
Alex Plate
8a5ad713ea Trying to setup neovim tests 2020-10-31 16:29:34 +03:00
Alex Plate
12be65fa09 Update teamcity config: refactoring 2020-10-31 16:00:35 +03:00
Alex Plate
0720431c91 More cleanup 2020-10-31 14:29:26 +03:00
Alex Plate
6f1ac1de97 Add more time checks for is db cell 2020-10-31 14:03:11 +03:00
Alex Plate
99d2d4b594 Update the color of yank highlighting after laf changing 2020-10-31 13:46:08 +03:00
Alex Plate
2bf9b97e49 Continuation of qodana cleanup 2020-10-31 13:11:13 +03:00
Alex Plate
c6600f3348 Fixes base of qodana run 2020-10-30 19:54:26 +03:00
Alex Plate
e29ab54b0e Make default register in RegisterGroup non static field 2020-10-30 19:18:46 +03:00
Alex Plate
197565d4cb Get rid of info logs 2020-10-30 16:47:44 +03:00
Alex Plate
3d570d2020 Make property private 2020-10-30 15:59:56 +03:00
Alex Plate
fe364dc6dc Reduce the depth of "parentByCondition" function 2020-10-30 11:56:50 +03:00
Alex Plate
5d0e82781f Enable teamcity output format for plugin verifier 2020-10-30 11:37:36 +03:00
Alex Plate
24f005a340 Integrate plugin verifier to the project 2020-10-30 11:08:49 +03:00
Alex Plate
1743c08091 Update isIdeaVimdisableHere logging 2020-10-29 12:40:30 +03:00
Alex Plate
81b095c899 Update detekt configuration 2020-10-29 11:43:47 +03:00
Alex Plate
965e8f71a0 Update detekt configuration 2020-10-29 11:01:41 +03:00
Alex Plate
efc789fbf4 Update plugin.xml 2020-10-29 10:58:35 +03:00
Alex Plate
f9cf49a9dd Update CHANGES.md 2020-10-29 10:53:02 +03:00
Alex Plate
0b41bd30cd Rename dialogescape and oneline to ideaenabledbufs 2020-10-29 10:44:34 +03:00
Alex Plate
7c79615c6a [VIM-2144] Correct caret position after block insert with inlays 2020-10-29 10:19:51 +03:00
Alex Plate
10be7354cd [VIM-2156] Fix up/down motions with inlays 2020-10-29 09:46:21 +03:00
Alex Plate
1e9925f092 [VIM-2157] Fix tab for active templates 2020-10-28 11:37:28 +03:00
Alex Plate
838079b249 Apply teamcity dsl patch (update vsc labbeling) 2020-10-27 19:47:47 +03:00
aleksei.plate
a9bf5c93df TeamCity change in 'IntelliJ IDEA plugins / IdeaVim' project: build features of 'Publish EAP Build' build configuration were updated 2020-10-27 16:41:49 +00:00
Alex Plate
d4ec7e1f69 Remove some detekt warnings 2020-10-27 10:01:57 +03:00
Alex Plate
12e9774d4c Use markdown to slack converter to send EAP notification 2020-10-27 09:38:38 +03:00
Alex Plate
7bccaa8717 Remove deprecated methods and options 2020-10-23 11:18:46 +03:00
Alex Plate
319874b973 Update message 2020-10-22 12:11:14 +03:00
Alex Plate
daf8799c39 Update isIdeavimDisabled here report 2020-10-22 12:02:03 +03:00
Alex Plate
f45d4e1451 [VIM-2150] Shift-D should not delete an empty line 2020-10-21 10:26:50 +03:00
Alex Plate
7458d126bc Remove build dependencies for EAP release 2020-10-20 11:59:37 +03:00
Alex Plate
a90ffb7a48 Update plugin.xml 2020-10-20 11:38:20 +03:00
Alex Plate
d1e39903dd Use gradle-changelog-plugin for pushing slack notifications 2020-10-20 11:34:52 +03:00
Alex Plate
f23793f3f3 Test <Action> for insert mode mapping 2020-10-20 11:09:51 +03:00
Alex Plate
800390921c Update branch specification for PRs 2020-10-20 00:59:33 +03:00
Alex Plate
9650450426 Do not run tests on pull requests merging 2020-10-20 00:52:12 +03:00
Alex Plate
7225ab1f1b Use check instead of test for testing 2020-10-20 00:45:24 +03:00
Alex Plate
72dbc45457 Join active test 2020-10-20 00:13:47 +03:00
Alex Plate
3d14f916ef Update TestsForIntelliJ20202 configuration 2020-10-20 00:05:18 +03:00
Alex Plate
5598de70f1 Trying to extract common code for active tests building 2020-10-19 23:59:27 +03:00
Alex Plate
bfccdd6b35 Cleanup builds 2020-10-19 23:54:01 +03:00
Alex Plate
35f36070a4 Update gitignore 2020-10-19 23:42:47 +03:00
Alex Plate
8f0c50a010 Update pull requests vcs root id 2020-10-19 23:40:24 +03:00
Alex Plate
25d6d3694b Update gitignore 2020-10-19 23:39:57 +03:00
Alex Plate
6c784ec01e Exclude NVim builds 2020-10-19 12:26:59 +03:00
Alex Plate
ebc81c55c2 Update GitHub Pull Requests build 2020-10-19 12:16:59 +03:00
aleksei.plate
d08d9fce99 TeamCity change in 'IntelliJ IDEA plugins / IdeaVim' project: Synchronization with own VCS root is enabled 2020-10-19 08:48:07 +00:00
Alex Plate
d1bfce1974 Create a baseline for the detekt 2020-10-19 11:07:53 +03:00
Alex Plate
0d0f326c26 Catch exception instead of NumberFormatException 2020-10-18 21:21:37 +03:00
Alex Plate
2072fa1e13 Add detekt to the project 2020-10-18 21:06:51 +03:00
Alex Plate
fd98274e78 EditorDataContext can now accept a delegate data context 2020-10-16 11:03:05 +03:00
Alex Plate
e72c7d6cb7 Convert EditorDataContext to kotlin 2020-10-16 10:53:49 +03:00
Alex Plate
5860c0031b Rename .java to .kt 2020-10-16 10:53:49 +03:00
Alex Plate
a43232ba6c Move execution of mapping to MappingInfo 2020-10-16 10:27:12 +03:00
Alex Plate
b20bec610a Move converting to presentable string to MappingInfo classes 2020-10-16 10:08:42 +03:00
Alex Plate
3a9f5ea33a Add ability to map actions via <Action> keyword 2020-10-16 10:00:46 +03:00
Alex Plate
5d1caa21d8 Remove java annotation 2020-10-15 19:50:15 +03:00
Alex Plate
70b3156375 Update git for the track action id 2020-10-15 12:08:01 +03:00
Alex Plate
d388a75f98 Add an information about "Track action ids" to readme 2020-10-15 11:44:07 +03:00
Alex Plate
b2a6d0e687 Do now show "Copy action id" action in the notification if there is no id 2020-10-15 10:40:48 +03:00
Alex Plate
462f5bab54 Update intellij gradle plugin version 2020-10-12 11:03:34 +03:00
Alex Plate
e89e0466eb Prepare for 0.60 release 2020-10-09 11:24:48 +02:00
Alex Plate
c9d0d7aef6 [VIM-2140] Downgrade java version to 1.8 2020-10-09 11:06:38 +02:00
Alex Plate
90c7d5a74a Update gradle to 6.6.1 2020-10-09 10:30:41 +02:00
Alex Plate
b19e11b5b6 Use proper access syntax 2020-10-09 10:16:30 +02:00
Alex Plate
2d002c044d Report if time for calculation of isIdeaVimDisabledHere take more than 10ms 2020-10-08 11:39:49 +02:00
Alex Plate
9a7b2bd158 Update the implementation of disabled IdeaVim editors 2020-10-08 11:25:47 +02:00
Alex Plate
461c874de6 Reformat some code 2020-10-08 10:31:21 +02:00
183 changed files with 3095 additions and 787 deletions

146
.detekt/baseline.xml Normal file
View File

@@ -0,0 +1,146 @@
<?xml version="1.0" ?>
<SmellBaseline>
<ManuallySuppressedIssues>
<ID>ComplexMethod:CmdHandler.kt$CmdHandler$private fun addAlias(cmd: ExCommand, editor: Editor?): Boolean</ID>
<ID>ComplexMethod:CommandState.kt$CommandState$ fun toVimNotation(): String</ID>
</ManuallySuppressedIssues>
<CurrentIssues>
<ID>ComplexMethod:HistoryHandler.kt$HistoryHandler$override fun execute(editor: Editor, context: DataContext, cmd: ExCommand): Boolean</ID>
<ID>ComplexMethod:OptionsManager.kt$OptionsManager$ fun parseOptionLine(editor: Editor?, args: String, failOnBad: Boolean): Boolean</ID>
<ID>ComplexMethod:PutGroup.kt$PutGroup$private fun prepareDocumentAndGetStartOffsets(editor: Editor, caret: Caret, typeInRegister: SelectionType, data: PutData, additionalData: Map&lt;String, Any&gt;): List&lt;Int&gt;</ID>
<ID>ComplexMethod:SearchHelperKt.kt$// bounds are considered inside corresponding quotes fun checkInString(chars: CharSequence, currentPos: Int, str: Boolean): Boolean</ID>
<ID>ComplexMethod:TabCloseHandler.kt$TabCloseHandler$ private fun getTabIndexToClose(arg: String, current: Int, last: Int): Int?</ID>
<ID>ComplexMethod:VimExchangeExtension.kt$VimExchangeExtension.Operator$private fun compareExchanges(x: Exchange, y: Exchange): ExchangeCompareResult</ID>
<ID>ComplexMethod:VimMultipleCursorsExtension.kt$VimMultipleCursorsExtension.NextOccurrenceHandler$override fun executeInWriteAction(editor: Editor, context: DataContext)</ID>
<ID>ComplexMethod:VimShortcutKeyAction.kt$VimShortcutKeyAction$private fun isEnabled(e: AnActionEvent): Boolean</ID>
<ID>LongMethod:CmdHandler.kt$CmdHandler$private fun addAlias(cmd: ExCommand, editor: Editor?): Boolean</ID>
<ID>LongMethod:HistoryHandler.kt$HistoryHandler$override fun execute(editor: Editor, context: DataContext, cmd: ExCommand): Boolean</ID>
<ID>LongMethod:OptionsManager.kt$OptionsManager$ fun parseOptionLine(editor: Editor?, args: String, failOnBad: Boolean): Boolean</ID>
<ID>MagicNumber:ActionListHandler.kt$ActionListHandler$50</ID>
<ID>MagicNumber:AddBlockInlaysAction.kt$AddBlockInlaysAction$0.9f</ID>
<ID>MagicNumber:AddBlockInlaysAction.kt$AddBlockInlaysAction$1.75f</ID>
<ID>MagicNumber:AddBlockInlaysAction.kt$AddBlockInlaysAction$10</ID>
<ID>MagicNumber:AddBlockInlaysAction.kt$AddBlockInlaysAction$3</ID>
<ID>MagicNumber:AddBlockInlaysAction.kt$AddBlockInlaysAction$5</ID>
<ID>MagicNumber:AddBlockInlaysAction.kt$AddBlockInlaysAction$6</ID>
<ID>MagicNumber:AddBlockInlaysAction.kt$AddBlockInlaysAction$7</ID>
<ID>MagicNumber:AddInlineInlaysAction.kt$AddInlineInlaysAction$10</ID>
<ID>MagicNumber:AddInlineInlaysAction.kt$AddInlineInlaysAction$20</ID>
<ID>MagicNumber:AddInlineInlaysAction.kt$AddInlineInlaysAction$5</ID>
<ID>MagicNumber:AddInlineInlaysAction.kt$AddInlineInlaysAction$7</ID>
<ID>MagicNumber:BufferListHandler.kt$3</ID>
<ID>MagicNumber:CmdHandler.kt$CmdHandler$11</ID>
<ID>MagicNumber:CmdHandler.kt$CmdHandler$12</ID>
<ID>MagicNumber:CommandBuilder.kt$CommandBuilder$10</ID>
<ID>MagicNumber:CommandBuilder.kt$CommandBuilder$999999999</ID>
<ID>MagicNumber:ConfigurationMigrators.kt$Version 6 to 7 config migration$6</ID>
<ID>MagicNumber:ConfigurationMigrators.kt$Version 6 to 7 config migration$7</ID>
<ID>MagicNumber:EditorHelper.kt$10</ID>
<ID>MagicNumber:ExKeyBindings.kt$ExKeyBindings$0x05</ID>
<ID>MagicNumber:ExKeyBindings.kt$ExKeyBindings$0x08</ID>
<ID>MagicNumber:HistoryHandler.kt$HistoryHandler$7</ID>
<ID>MagicNumber:JumpsHandler.kt$JumpsHandler$200</ID>
<ID>MagicNumber:JumpsHandler.kt$JumpsHandler$3</ID>
<ID>MagicNumber:JumpsHandler.kt$JumpsHandler$5</ID>
<ID>MagicNumber:MarksHandler.kt$MarksHandler$200</ID>
<ID>MagicNumber:MarksHandler.kt$MarksHandler$3</ID>
<ID>MagicNumber:MarksHandler.kt$MarksHandler$5</ID>
<ID>MagicNumber:OptionsManager.kt$OptionsManager$100</ID>
<ID>MagicNumber:OptionsManager.kt$OptionsManager$1000</ID>
<ID>MagicNumber:OptionsManager.kt$OptionsManager$19</ID>
<ID>MagicNumber:OptionsManager.kt$OptionsManager$20</ID>
<ID>MagicNumber:OptionsManager.kt$OptionsManager$3</ID>
<ID>MagicNumber:OptionsManager.kt$OptionsManager$80</ID>
<ID>MagicNumber:ProcessExEntryAction.kt$ProcessExEntryAction$0x0a</ID>
<ID>MagicNumber:RegistersHandler.kt$RegistersHandler$200</ID>
<ID>MagicNumber:SearchHelperKt.kt$3</ID>
<ID>MagicNumber:SelectLastFileHandler.kt$SelectLastFileHandler$999</ID>
<ID>MagicNumber:SelectionType.kt$SelectionType.BLOCK_WISE$3</ID>
<ID>MagicNumber:ShiftLeftHandler.kt$ShiftLeftHandler$31</ID>
<ID>MagicNumber:ShiftRightHandler.kt$ShiftRightHandler$31</ID>
<ID>MagicNumber:VimHighlightedYank.kt$VimHighlightedYank.HighlightHandler$3</ID>
<ID>MagicNumber:VimHighlightedYank.kt$VimHighlightedYank.HighlightHandler$4</ID>
<ID>MatchingDeclarationName:CommandDefinition.kt$CommandName</ID>
<ID>MaxLineLength:ExBeanClass.kt$ExBeanClass$logger&lt;ExBeanClass&gt;().error("IdeaVim doesn't accept contributions to `vimActions` extension points. Please create a plugin using `VimExtension`. Plugin to blame: $pluginId")</ID>
<ID>MaxLineLength:ExRanges.kt$SearchRange$override</ID>
<ID>MaxLineLength:NotificationService.kt$NotificationService$notification.addAction(AppendToIdeaVimRcAction(notification, "set clipboard+=ideaput", "ideaput") { OptionsManager.clipboard.append(ClipboardOptionsData.ideaput) })</ID>
<ID>MaxLineLength:NotificationService.kt$NotificationService.AppendToIdeaVimRcAction$private inner</ID>
<ID>MaxLineLength:NotificationService.kt$NotificationService.AppendToIdeaVimRcAction$val successNotification = Notification(IDEAVIM_NOTIFICATION_ID, IDEAVIM_NOTIFICATION_TITLE, "&lt;code&gt;$optionName&lt;/code&gt; is enabled", NotificationType.INFORMATION)</ID>
<ID>MaxLineLength:OptionsManager.kt$OptionsManager$val clipboard = addOption(ListOption(ClipboardOptionsData.name, ClipboardOptionsData.abbr, arrayOf(ClipboardOptionsData.ideaput, "autoselect,exclude:cons\\|linux"), null))</ID>
<ID>MaxLineLength:PutGroup.kt$PutGroup$private</ID>
<ID>MaxLineLength:PutLinesHandler.kt$PutLinesHandler$val textData = registerGroup.lastRegister?.let { PutData.TextData(it.text ?: StringHelper.toKeyNotation(it.keys), SelectionType.LINE_WISE, it.transferableData) }</ID>
<ID>MaxLineLength:PutTextAction.kt$PutTextBaseAction$val textData = if (lastRegister != null) TextData(lastRegister.text ?: StringHelper.toKeyNotation(lastRegister.keys), lastRegister.type, lastRegister.transferableData) else null</ID>
<ID>MaxLineLength:ReplaceWithRegister.kt$ReplaceWithRegister.Operator$val visualSelection = PutData.VisualSelection(mapOf(editor.caretModel.primaryCaret to VimSelection.create(range.startOffset, range.endOffset - 1, selectionType, editor)), selectionType)</ID>
<ID>MaxLineLength:StatisticReporter.kt$StatisticReporter$val url = "https://plugins.jetbrains.com/plugins/list?pluginId=${VimPlugin.getPluginId().idString}&amp;build=$buildNumber&amp;pluginVersion=$version&amp;os=$os&amp;uuid=$uid"</ID>
<ID>MaxLineLength:VimShortcutKeyAction.kt$VimShortcutKeyAction.Companion$@JvmField val VIM_ONLY_EDITOR_KEYS: Set&lt;KeyStroke&gt; = ImmutableSet.builder&lt;KeyStroke&gt;().addAll(getKeyStrokes(KeyEvent.VK_ENTER, 0)).addAll(getKeyStrokes(KeyEvent.VK_ESCAPE, 0)) .addAll(getKeyStrokes(KeyEvent.VK_TAB, 0)).addAll(getKeyStrokes(KeyEvent.VK_BACK_SPACE, 0, InputEvent.CTRL_DOWN_MASK)) .addAll(getKeyStrokes(KeyEvent.VK_INSERT, 0)).addAll(getKeyStrokes(KeyEvent.VK_DELETE, 0, InputEvent.CTRL_DOWN_MASK)) .addAll(getKeyStrokes(KeyEvent.VK_UP, 0, InputEvent.CTRL_DOWN_MASK, InputEvent.SHIFT_DOWN_MASK)).addAll(getKeyStrokes(KeyEvent.VK_DOWN, 0, InputEvent.CTRL_DOWN_MASK, InputEvent.SHIFT_DOWN_MASK)) .addAll(getKeyStrokes(KeyEvent.VK_LEFT, 0, InputEvent.CTRL_DOWN_MASK, InputEvent.SHIFT_DOWN_MASK, InputEvent.CTRL_DOWN_MASK or InputEvent.SHIFT_DOWN_MASK)) .addAll(getKeyStrokes(KeyEvent.VK_RIGHT, 0, InputEvent.CTRL_DOWN_MASK, InputEvent.SHIFT_DOWN_MASK, InputEvent.CTRL_DOWN_MASK or InputEvent.SHIFT_DOWN_MASK)) .addAll(getKeyStrokes(KeyEvent.VK_HOME, 0, InputEvent.CTRL_DOWN_MASK, InputEvent.SHIFT_DOWN_MASK, InputEvent.CTRL_DOWN_MASK or InputEvent.SHIFT_DOWN_MASK)) .addAll(getKeyStrokes(KeyEvent.VK_END, 0, InputEvent.CTRL_DOWN_MASK, InputEvent.SHIFT_DOWN_MASK, InputEvent.CTRL_DOWN_MASK or InputEvent.SHIFT_DOWN_MASK)) .addAll(getKeyStrokes(KeyEvent.VK_PAGE_UP, 0, InputEvent.SHIFT_DOWN_MASK, InputEvent.CTRL_DOWN_MASK or InputEvent.SHIFT_DOWN_MASK)) .addAll(getKeyStrokes(KeyEvent.VK_PAGE_DOWN, 0, InputEvent.SHIFT_DOWN_MASK, InputEvent.CTRL_DOWN_MASK or InputEvent.SHIFT_DOWN_MASK)).build()</ID>
<ID>MaxLineLength:VimShortcutKeyAction.kt$VimShortcutKeyAction.Companion$ImmutableSet.builder&lt;KeyStroke&gt;().addAll(getKeyStrokes(KeyEvent.VK_ENTER, 0)).addAll(getKeyStrokes(KeyEvent.VK_ESCAPE, 0)) .addAll(getKeyStrokes(KeyEvent.VK_TAB, 0)).addAll(getKeyStrokes(KeyEvent.VK_BACK_SPACE, 0, InputEvent.CTRL_DOWN_MASK)) .addAll(getKeyStrokes(KeyEvent.VK_INSERT, 0)).addAll(getKeyStrokes(KeyEvent.VK_DELETE, 0, InputEvent.CTRL_DOWN_MASK)) .addAll(getKeyStrokes(KeyEvent.VK_UP, 0, InputEvent.CTRL_DOWN_MASK, InputEvent.SHIFT_DOWN_MASK))</ID>
<ID>MaxLineLength:VimShortcutKeyAction.kt$VimShortcutKeyAction.Companion$ImmutableSet.builder&lt;KeyStroke&gt;().addAll(getKeyStrokes(KeyEvent.VK_ENTER, 0)).addAll(getKeyStrokes(KeyEvent.VK_ESCAPE, 0)) .addAll(getKeyStrokes(KeyEvent.VK_TAB, 0)).addAll(getKeyStrokes(KeyEvent.VK_BACK_SPACE, 0, InputEvent.CTRL_DOWN_MASK)) .addAll(getKeyStrokes(KeyEvent.VK_INSERT, 0)).addAll(getKeyStrokes(KeyEvent.VK_DELETE, 0, InputEvent.CTRL_DOWN_MASK)) .addAll(getKeyStrokes(KeyEvent.VK_UP, 0, InputEvent.CTRL_DOWN_MASK, InputEvent.SHIFT_DOWN_MASK)).addAll(getKeyStrokes(KeyEvent.VK_DOWN, 0, InputEvent.CTRL_DOWN_MASK, InputEvent.SHIFT_DOWN_MASK)) .addAll(getKeyStrokes(KeyEvent.VK_LEFT, 0, InputEvent.CTRL_DOWN_MASK, InputEvent.SHIFT_DOWN_MASK, InputEvent.CTRL_DOWN_MASK or InputEvent.SHIFT_DOWN_MASK))</ID>
<ID>MaxLineLength:VimShortcutKeyAction.kt$VimShortcutKeyAction.Companion$ImmutableSet.builder&lt;KeyStroke&gt;().addAll(getKeyStrokes(KeyEvent.VK_ENTER, 0)).addAll(getKeyStrokes(KeyEvent.VK_ESCAPE, 0)) .addAll(getKeyStrokes(KeyEvent.VK_TAB, 0)).addAll(getKeyStrokes(KeyEvent.VK_BACK_SPACE, 0, InputEvent.CTRL_DOWN_MASK)) .addAll(getKeyStrokes(KeyEvent.VK_INSERT, 0)).addAll(getKeyStrokes(KeyEvent.VK_DELETE, 0, InputEvent.CTRL_DOWN_MASK)) .addAll(getKeyStrokes(KeyEvent.VK_UP, 0, InputEvent.CTRL_DOWN_MASK, InputEvent.SHIFT_DOWN_MASK)).addAll(getKeyStrokes(KeyEvent.VK_DOWN, 0, InputEvent.CTRL_DOWN_MASK, InputEvent.SHIFT_DOWN_MASK)) .addAll(getKeyStrokes(KeyEvent.VK_LEFT, 0, InputEvent.CTRL_DOWN_MASK, InputEvent.SHIFT_DOWN_MASK, InputEvent.CTRL_DOWN_MASK or InputEvent.SHIFT_DOWN_MASK)) .addAll(getKeyStrokes(KeyEvent.VK_RIGHT, 0, InputEvent.CTRL_DOWN_MASK, InputEvent.SHIFT_DOWN_MASK, InputEvent.CTRL_DOWN_MASK or InputEvent.SHIFT_DOWN_MASK))</ID>
<ID>MaxLineLength:VimShortcutKeyAction.kt$VimShortcutKeyAction.Companion$ImmutableSet.builder&lt;KeyStroke&gt;().addAll(getKeyStrokes(KeyEvent.VK_ENTER, 0)).addAll(getKeyStrokes(KeyEvent.VK_ESCAPE, 0)) .addAll(getKeyStrokes(KeyEvent.VK_TAB, 0)).addAll(getKeyStrokes(KeyEvent.VK_BACK_SPACE, 0, InputEvent.CTRL_DOWN_MASK)) .addAll(getKeyStrokes(KeyEvent.VK_INSERT, 0)).addAll(getKeyStrokes(KeyEvent.VK_DELETE, 0, InputEvent.CTRL_DOWN_MASK)) .addAll(getKeyStrokes(KeyEvent.VK_UP, 0, InputEvent.CTRL_DOWN_MASK, InputEvent.SHIFT_DOWN_MASK)).addAll(getKeyStrokes(KeyEvent.VK_DOWN, 0, InputEvent.CTRL_DOWN_MASK, InputEvent.SHIFT_DOWN_MASK)) .addAll(getKeyStrokes(KeyEvent.VK_LEFT, 0, InputEvent.CTRL_DOWN_MASK, InputEvent.SHIFT_DOWN_MASK, InputEvent.CTRL_DOWN_MASK or InputEvent.SHIFT_DOWN_MASK)) .addAll(getKeyStrokes(KeyEvent.VK_RIGHT, 0, InputEvent.CTRL_DOWN_MASK, InputEvent.SHIFT_DOWN_MASK, InputEvent.CTRL_DOWN_MASK or InputEvent.SHIFT_DOWN_MASK)) .addAll(getKeyStrokes(KeyEvent.VK_HOME, 0, InputEvent.CTRL_DOWN_MASK, InputEvent.SHIFT_DOWN_MASK, InputEvent.CTRL_DOWN_MASK or InputEvent.SHIFT_DOWN_MASK))</ID>
<ID>MemberNameEqualsClassName:Ranges.kt$Ranges$private val ranges: MutableList&lt;Range&gt; = mutableListOf()</ID>
<ID>NestedBlockDepth:OptionsManager.kt$OptionsManager$ fun parseOptionLine(editor: Editor?, args: String, failOnBad: Boolean): Boolean</ID>
<ID>ReturnCount:ActionBeanClass.kt$ActionBeanClass$fun getParsedModes(): Set&lt;MappingMode&gt;?</ID>
<ID>ReturnCount:Alias.kt$Alias$fun getCommand(input: String, count: Int): String</ID>
<ID>ReturnCount:CmdFilterHandler.kt$CmdFilterHandler$override fun execute(editor: Editor, context: DataContext, cmd: ExCommand): Boolean</ID>
<ID>ReturnCount:CmdHandler.kt$CmdHandler$private fun addAlias(cmd: ExCommand, editor: Editor?): Boolean</ID>
<ID>ReturnCount:CommandGroup.kt$CommandGroup$fun isAlias(command: String): Boolean</ID>
<ID>ReturnCount:DeleteJoinLinesAction.kt$DeleteJoinLinesAction$override fun execute(editor: Editor, context: DataContext, count: Int, rawCount: Int, argument: Argument?): Boolean</ID>
<ID>ReturnCount:DeleteJoinLinesSpacesAction.kt$DeleteJoinLinesSpacesAction$override fun execute(editor: Editor, context: DataContext, count: Int, rawCount: Int, argument: Argument?): Boolean</ID>
<ID>ReturnCount:DeleteJoinVisualLinesAction.kt$DeleteJoinVisualLinesAction$override fun executeForAllCarets(editor: Editor, context: DataContext, cmd: Command, caretsAndSelections: Map&lt;Caret, VimSelection&gt;): Boolean</ID>
<ID>ReturnCount:DeleteJoinVisualLinesSpacesAction.kt$DeleteJoinVisualLinesSpacesAction$override fun executeForAllCarets(editor: Editor, context: DataContext, cmd: Command, caretsAndSelections: Map&lt;Caret, VimSelection&gt;): Boolean</ID>
<ID>ReturnCount:DeleteMotionAction.kt$DeleteMotionAction$override fun execute(editor: Editor, caret: Caret, context: DataContext, count: Int, rawCount: Int, argument: Argument?): Boolean</ID>
<ID>ReturnCount:EditFileHandler.kt$EditFileHandler$override fun execute(editor: Editor, context: DataContext, cmd: ExCommand): Boolean</ID>
<ID>ReturnCount:EditorHelper.kt$ fun Editor.isPrimaryEditor(): Boolean</ID>
<ID>ReturnCount:ExRanges.kt$Range.Companion$ @JvmStatic fun createRange(str: String, offset: Int, move: Boolean): Array&lt;Range&gt;?</ID>
<ID>ReturnCount:FilterMotionAction.kt$FilterMotionAction$override fun execute(editor: Editor, context: DataContext, cmd: Command): Boolean</ID>
<ID>ReturnCount:GotoCharacterHandler.kt$GotoCharacterHandler$override fun execute(editor: Editor, caret: Caret, context: DataContext, cmd: ExCommand): Boolean</ID>
<ID>ReturnCount:Helper.kt$@Suppress("IncorrectParentDisposable") fun Editor.isTemplateActive(): Boolean</ID>
<ID>ReturnCount:HistoryHandler.kt$HistoryHandler$override fun execute(editor: Editor, context: DataContext, cmd: ExCommand): Boolean</ID>
<ID>ReturnCount:IdeaSelectionControl.kt$IdeaSelectionControl$ fun predictMode(editor: Editor, selectionSource: VimListenerManager.SelectionSource): CommandState.Mode</ID>
<ID>ReturnCount:MapHandler.kt$MapHandler$@Throws(ExException::class) private fun executeCommand(cmd: ExCommand, editor: Editor?): Boolean</ID>
<ID>ReturnCount:Marks.kt$IntellijMark$private fun getProject(): Project?</ID>
<ID>ReturnCount:Marks.kt$VimMark.Companion$@JvmStatic fun create(key: Char?, logicalLine: Int?, col: Int?, filename: String?, protocol: String?): VimMark?</ID>
<ID>ReturnCount:ModalEntry.kt$ModalEntry.&lt;no name provided&gt;$override fun dispatchKeyEvent(e: KeyEvent): Boolean</ID>
<ID>ReturnCount:MotionScrollLastScreenLinePageStartAction.kt$MotionScrollLastScreenLinePageStartAction$override fun execute(editor: Editor, context: DataContext, cmd: Command): Boolean</ID>
<ID>ReturnCount:OperatorAction.kt$OperatorAction$override fun execute(editor: Editor, context: DataContext, cmd: Command): Boolean</ID>
<ID>ReturnCount:OptionsManager.kt$OptionsManager$ fun parseOptionLine(editor: Editor?, args: String, failOnBad: Boolean): Boolean</ID>
<ID>ReturnCount:PutGroup.kt$PutGroup$private fun getProviderForPasteViaIde(context: DataContext, typeInRegister: SelectionType, data: PutData): PasteProvider?</ID>
<ID>ReturnCount:PutGroup.kt$PutGroup$private fun prepareDocumentAndGetStartOffsets(editor: Editor, caret: Caret, typeInRegister: SelectionType, data: PutData, additionalData: Map&lt;String, Any&gt;): List&lt;Int&gt;</ID>
<ID>ReturnCount:PutLinesHandler.kt$PutLinesHandler$override fun execute(editor: Editor, context: DataContext, cmd: ExCommand): Boolean</ID>
<ID>ReturnCount:ReloadVimRc.kt$VimRcFileState$fun equalTo(document: Document): Boolean</ID>
<ID>ReturnCount:RepeatHandler.kt$RepeatHandler$@Throws(ExException::class) override fun execute(editor: Editor, caret: Caret, context: DataContext, cmd: ExCommand): Boolean</ID>
<ID>ReturnCount:SelectMotionRightAction.kt$SelectMotionRightAction$override fun getOffset(editor: Editor, caret: Caret, context: DataContext, count: Int, rawCount: Int, argument: Argument?): Int</ID>
<ID>ReturnCount:ShowCmd.kt$ShowCmd$fun getFullText(editor: Editor?): String</ID>
<ID>ReturnCount:TabCloseHandler.kt$TabCloseHandler$ private fun getTabIndexToClose(arg: String, current: Int, last: Int): Int?</ID>
<ID>ReturnCount:TextObjectActionHandler.kt$TextObjectActionHandler$ final override fun baseExecute(editor: Editor, caret: Caret, context: DataContext, cmd: Command): Boolean</ID>
<ID>ReturnCount:UndoRedoHelper.kt$UndoRedoHelper$fun redo(context: DataContext): Boolean</ID>
<ID>ReturnCount:UndoRedoHelper.kt$UndoRedoHelper$fun undo(context: DataContext): Boolean</ID>
<ID>ReturnCount:VimExchangeExtension.kt$VimExchangeExtension.Operator$override fun apply(editor: Editor, context: DataContext, selectionType: SelectionType): Boolean</ID>
<ID>ReturnCount:VimExtensionFacade.kt$VimExtensionFacade$ @JvmStatic fun inputString(editor: Editor, prompt: String, finishOn: Char?): String</ID>
<ID>ReturnCount:VimMultipleCursorsExtension.kt$VimMultipleCursorsExtension.AllOccurrencesHandler$override fun executeInWriteAction(editor: Editor, context: DataContext)</ID>
<ID>ReturnCount:VimMultipleCursorsExtension.kt$VimMultipleCursorsExtension.NextOccurrenceHandler$override fun executeInWriteAction(editor: Editor, context: DataContext)</ID>
<ID>ReturnCount:VimMultipleCursorsExtension.kt$VimMultipleCursorsExtension.SkipOccurrenceHandler$override fun executeInWriteAction(editor: Editor, context: DataContext)</ID>
<ID>ReturnCount:VimScriptParser.kt$VimScriptParser$@Throws(ExException::class) fun evaluate(expression: String, globals: Map&lt;String?, Any?&gt;): Any</ID>
<ID>ReturnCount:VimScriptParser.kt$VimScriptParser$fun findOrCreateIdeaVimRc(): File?</ID>
<ID>ReturnCount:VimShortcutKeyAction.kt$VimShortcutKeyAction$private fun getKeyStroke(e: AnActionEvent): KeyStroke?</ID>
<ID>ReturnCount:VimShortcutKeyAction.kt$VimShortcutKeyAction$private fun isEnabled(e: AnActionEvent): Boolean</ID>
<ID>ReturnCount:VimSurroundExtension.kt$VimSurroundExtension.CSurroundHandler$override fun execute(editor: Editor, context: DataContext)</ID>
<ID>ReturnCount:VimSurroundExtension.kt$VimSurroundExtension.Operator$override fun apply(editor: Editor, context: DataContext, selectionType: SelectionType): Boolean</ID>
<ID>ReturnCount:VisualBlockAppendAction.kt$VisualBlockAppendAction$override fun executeForAllCarets(editor: Editor, context: DataContext, cmd: Command, caretsAndSelections: Map&lt;Caret, VimSelection&gt;): Boolean</ID>
<ID>ReturnCount:VisualBlockInsertAction.kt$VisualBlockInsertAction$override fun executeForAllCarets(editor: Editor, context: DataContext, cmd: Command, caretsAndSelections: Map&lt;Caret, VimSelection&gt;): Boolean</ID>
<ID>ReturnCount:VisualMotionGroup.kt$VisualMotionGroup$ fun toggleVisual(editor: Editor, count: Int, rawCount: Int, subMode: CommandState.SubMode): Boolean</ID>
<ID>ReturnCount:VisualMotionGroup.kt$VisualMotionGroup$fun autodetectVisualSubmode(editor: Editor): CommandState.SubMode</ID>
<ID>ReturnCount:VisualMotionGroup.kt$VisualMotionGroup$fun selectPreviousVisualMode(editor: Editor): Boolean</ID>
<ID>ReturnCount:VisualMotionGroup.kt$VisualMotionGroup$fun swapVisualSelections(editor: Editor): Boolean</ID>
<ID>ReturnCount:VisualMotionGroup.kt$VisualMotionGroup$private fun seemsLikeBlockMode(editor: Editor): Boolean</ID>
<ID>ReturnCount:VisualOperatorActionHandler.kt$VisualOperatorActionHandler$final override fun baseExecute(editor: Editor, caret: Caret, context: DataContext, cmd: Command): Boolean</ID>
<ID>ReturnCount:YankGroup.kt$YankGroup$ fun yankMotion(editor: Editor, context: DataContext, count: Int, rawCount: Int, argument: Argument): Boolean</ID>
<ID>ThrowsCount:CommandHandler.kt$CommandHandler$private fun checkArgs(cmd: ExCommand)</ID>
<ID>TooManyFunctions:CommandBuilder.kt$CommandBuilder</ID>
<ID>TooManyFunctions:CommandState.kt$CommandState</ID>
<ID>TooManyFunctions:PutGroup.kt$PutGroup</ID>
<ID>TooManyFunctions:Ranges.kt$Ranges</ID>
<ID>TooManyFunctions:VisualGroup.kt$com.maddyhome.idea.vim.group.visual.VisualGroup.kt</ID>
<ID>TooManyFunctions:VisualMotionGroup.kt$VisualMotionGroup</ID>
</CurrentIssues>
</SmellBaseline>

31
.detekt/config.yaml Normal file
View File

@@ -0,0 +1,31 @@
formatting:
Indentation:
indentSize: 2
continuationIndentSize: 8
ParameterListWrapping:
indentSize: 8
complexity:
LongParameterList:
functionThreshold: 12
NestedBlockDepth:
threshold: 6
ComplexCondition:
threshold: 6
ComplexMethod:
threshold: 20
exceptions:
TooGenericExceptionCaught:
active: false
naming:
ClassNaming:
excludes: "**/ConfigurationMigrators.kt, **/VersionDetectors.kt"
performance:
SpreadOperator:
active: false
style:
ForbiddenComment:
active: false
MaxLineLength:
maxLineLength: 160
ReturnCount:
max: 5

5
.gitignore vendored
View File

@@ -5,9 +5,14 @@
!/.idea/scopes !/.idea/scopes
!/.idea/copyright !/.idea/copyright
!/.idea/icon.png !/.idea/icon.png
!/.idea/inspectionProfiles
/build/ /build/
/out/ /out/
/tmp/ /tmp/
*.DS_Store *.DS_Store
.teamcity/.idea
.teamcity/target
.teamcity/*.iml

View File

@@ -0,0 +1,9 @@
<component name="InspectionProjectProfileManager">
<profile version="1.0">
<option name="myName" value="Project Default" />
<inspection_tool class="MissortedModifiers" enabled="true" level="WARNING" enabled_by_default="true">
<option name="m_requireAnnotationsFirst" value="true" />
</inspection_tool>
<inspection_tool class="StaticMethodOnlyUsedInOneClass" enabled="true" level="WARNING" enabled_by_default="true" />
</profile>
</component>

23
.idea/inspectionProfiles/Qodana.xml generated Normal file
View File

@@ -0,0 +1,23 @@
<component name="InspectionProjectProfileManager">
<profile version="1.0">
<description>Inspections profile for Qodana</description>
<option name="myName" value="Qodana" />
<inspection_tool class="CanBeFinal" enabled="false" level="WARNING" enabled_by_default="false">
<option name="REPORT_CLASSES" value="false" />
<option name="REPORT_METHODS" value="false" />
<option name="REPORT_FIELDS" value="true" />
</inspection_tool>
<inspection_tool class="GrUnresolvedAccess" enabled="false" level="WEAK WARNING" enabled_by_default="false" />
<inspection_tool class="MissortedModifiers" enabled="true" level="WARNING" enabled_by_default="true">
<option name="m_requireAnnotationsFirst" value="true" />
</inspection_tool>
<inspection_tool class="SameReturnValue" enabled="false" level="WARNING" enabled_by_default="false" />
<inspection_tool class="SpellCheckingInspection" enabled="false" level="TYPO" enabled_by_default="false">
<option name="processCode" value="true" />
<option name="processLiterals" value="true" />
<option name="processComments" value="true" />
</inspection_tool>
<inspection_tool class="StaticMethodOnlyUsedInOneClass" enabled="true" level="WARNING" enabled_by_default="true" />
<inspection_tool class="SuperTearDownInFinally" enabled="true" level="WARNING" enabled_by_default="true" />
</profile>
</component>

View File

@@ -0,0 +1,24 @@
<component name="ProjectRunConfigurationManager">
<configuration default="false" name="IdeaVim full verification" type="GradleRunConfiguration" factoryName="Gradle">
<ExternalSystemSettings>
<option name="executionName" />
<option name="externalProjectPath" value="$PROJECT_DIR$" />
<option name="externalSystemIdString" value="GRADLE" />
<option name="scriptParameters" value="" />
<option name="taskDescriptions">
<list />
</option>
<option name="taskNames">
<list>
<option value="check" />
<option value="runPluginVerifier" />
</list>
</option>
<option name="vmOptions" value="" />
</ExternalSystemSettings>
<ExternalSystemDebugServerProcess>true</ExternalSystemDebugServerProcess>
<ExternalSystemReattachDebugProcess>true</ExternalSystemReattachDebugProcess>
<DebugAllEnabled>false</DebugAllEnabled>
<method v="2" />
</configuration>
</component>

View File

@@ -0,0 +1,23 @@
<component name="ProjectRunConfigurationManager">
<configuration default="false" name="IdeaVim tests" type="GradleRunConfiguration" factoryName="Gradle">
<ExternalSystemSettings>
<option name="executionName" />
<option name="externalProjectPath" value="$PROJECT_DIR$" />
<option name="externalSystemIdString" value="GRADLE" />
<option name="scriptParameters" value="" />
<option name="taskDescriptions">
<list />
</option>
<option name="taskNames">
<list>
<option value="test" />
</list>
</option>
<option name="vmOptions" value="" />
</ExternalSystemSettings>
<ExternalSystemDebugServerProcess>true</ExternalSystemDebugServerProcess>
<ExternalSystemReattachDebugProcess>true</ExternalSystemReattachDebugProcess>
<DebugAllEnabled>false</DebugAllEnabled>
<method v="2" />
</configuration>
</component>

View File

@@ -0,0 +1,23 @@
<component name="ProjectRunConfigurationManager">
<configuration default="false" name="Start IJ with IdeaVim" type="GradleRunConfiguration" factoryName="Gradle">
<ExternalSystemSettings>
<option name="executionName" />
<option name="externalProjectPath" value="$PROJECT_DIR$" />
<option name="externalSystemIdString" value="GRADLE" />
<option name="scriptParameters" value="" />
<option name="taskDescriptions">
<list />
</option>
<option name="taskNames">
<list>
<option value="runIde" />
</list>
</option>
<option name="vmOptions" value="" />
</ExternalSystemSettings>
<ExternalSystemDebugServerProcess>true</ExternalSystemDebugServerProcess>
<ExternalSystemReattachDebugProcess>true</ExternalSystemReattachDebugProcess>
<DebugAllEnabled>false</DebugAllEnabled>
<method v="2" />
</configuration>
</component>

86
.teamcity/_Self/Project.kt vendored Normal file
View File

@@ -0,0 +1,86 @@
package _Self
import _Self.buildTypes.GitHubPullRequests
import _Self.buildTypes.Nvim
import _Self.buildTypes.PluginVerifier
import _Self.buildTypes.Release
import _Self.buildTypes.ReleaseEap
import _Self.buildTypes.TestsForIntelliJ20181
import _Self.buildTypes.TestsForIntelliJ20182
import _Self.buildTypes.TestsForIntelliJ20183
import _Self.buildTypes.TestsForIntelliJ20191
import _Self.buildTypes.TestsForIntelliJ20192
import _Self.buildTypes.TestsForIntelliJ20193
import _Self.buildTypes.TestsForIntelliJ20201
import _Self.buildTypes.TestsForIntelliJ20202
import _Self.buildTypes.TestsForIntelliJEAP
import _Self.vcsRoots.Branch_181
import _Self.vcsRoots.Branch_183
import _Self.vcsRoots.Branch_191_193
import _Self.vcsRoots.GitHubPullRequest
import jetbrains.buildServer.configs.kotlin.v2019_2.Project
object Project : Project({
description = "Vim emulation plugin for the IntelliJ platform products"
vcsRoot(Branch_183)
vcsRoot(Branch_181)
vcsRoot(GitHubPullRequest)
vcsRoot(Branch_191_193)
buildType(GitHubPullRequests)
buildType(Release)
buildType(TestsForIntelliJ20201)
buildType(TestsForIntelliJ20191)
buildType(TestsForIntelliJ20181)
buildType(TestsForIntelliJ20192)
buildType(TestsForIntelliJ20182)
buildType(TestsForIntelliJ20193)
buildType(TestsForIntelliJ20183)
buildType(Nvim)
buildType(ReleaseEap)
buildType(TestsForIntelliJ20202)
buildType(TestsForIntelliJEAP)
buildType(PluginVerifier)
features {
feature {
id = "PROJECT_EXT_768"
type = "CloudImage"
param("use-spot-instances", "true")
param("user-tags", "project=idea-vim")
param("agent_pool_id", "41")
param("image-instances-limit", "")
param("subnet-id", "subnet-58839511")
param("ebs-optimized", "false")
param("instance-type", "c5d.large")
param("amazon-id", "ami-0d1a6a32faa92923e")
param("spot-instance-price", "0.1")
param("source-id", "BuildAgentsIdeaVim")
param("image-name-prefix", "BuildAgentsIdeaVim")
param("key-pair-name", "teamcity-prod-pub")
param("security-group-ids", "sg-eda08696,sg-7332cf0f,")
param("profileId", "amazon-48")
}
feature {
id = "amazon-48"
type = "CloudProfile"
param("profileServerUrl", "")
param("secure:access-id", "credentialsJSON:dbcdb2a2-de5f-4bc9-9421-292b19e83947")
param("system.cloud.profile_id", "amazon-48")
param("total-work-time", "")
param("description", "")
param("cloud-code", "amazon")
param("enabled", "true")
param("max-running-instances", "10")
param("agentPushPreset", "")
param("profileId", "amazon-48")
param("name", "Cloud Agents")
param("next-hour", "")
param("secure:secret-key", "credentialsJSON:65a87fe7-0977-4af9-96f1-344f2b82d269")
param("region", "eu-west-1")
param("terminate-idle-time", "15")
param("not-checked", "")
}
}
})

View File

@@ -0,0 +1,45 @@
package _Self.buildTypes
import jetbrains.buildServer.configs.kotlin.v2019_2.BuildType
import jetbrains.buildServer.configs.kotlin.v2019_2.CheckoutMode
import jetbrains.buildServer.configs.kotlin.v2019_2.DslContext
import jetbrains.buildServer.configs.kotlin.v2019_2.buildSteps.gradle
import jetbrains.buildServer.configs.kotlin.v2019_2.triggers.vcs
sealed class ActiveTests(buildName: String, ijVersion: String) : BuildType({
name = buildName
params {
param("env.ORG_GRADLE_PROJECT_downloadIdeaSources", "false")
param("env.ORG_GRADLE_PROJECT_ideaVersion", ijVersion)
param("env.ORG_GRADLE_PROJECT_instrumentPluginCode", "false")
}
vcs {
root(DslContext.settingsRoot)
checkoutMode = CheckoutMode.ON_SERVER
}
steps {
gradle {
tasks = "clean check"
buildFile = ""
enableStacktrace = true
param("org.jfrog.artifactory.selectedDeployableServer.defaultModuleVersionConfiguration", "GLOBAL")
}
}
triggers {
vcs {
branchFilter = ""
}
}
requirements {
noLessThanVer("teamcity.agent.jvm.version", "1.8")
}
})
object TestsForIntelliJEAP : ActiveTests("Tests for IntelliJ Latest EAP", "LATEST-EAP-SNAPSHOT")
object TestsForIntelliJ20202 : ActiveTests("Tests for IntelliJ 2020.2", "2020.2")
object TestsForIntelliJ20201 : ActiveTests("Tests for IntelliJ 2020.1", "2020.1")

View File

@@ -0,0 +1,74 @@
package _Self.buildTypes
import _Self.vcsRoots.GitHubPullRequest
import jetbrains.buildServer.configs.kotlin.v2019_2.BuildType
import jetbrains.buildServer.configs.kotlin.v2019_2.CheckoutMode
import jetbrains.buildServer.configs.kotlin.v2019_2.buildFeatures.PullRequests
import jetbrains.buildServer.configs.kotlin.v2019_2.buildFeatures.commitStatusPublisher
import jetbrains.buildServer.configs.kotlin.v2019_2.buildFeatures.pullRequests
import jetbrains.buildServer.configs.kotlin.v2019_2.buildSteps.gradle
import jetbrains.buildServer.configs.kotlin.v2019_2.triggers.VcsTrigger
import jetbrains.buildServer.configs.kotlin.v2019_2.triggers.vcs
object GitHubPullRequests : BuildType({
name = "GitHub Pull Requests"
description = "Test GitHub pull requests"
params {
param("env.ORG_GRADLE_PROJECT_downloadIdeaSources", "false")
param("env.ORG_GRADLE_PROJECT_ideaVersion", "2020.1")
param("env.ORG_GRADLE_PROJECT_instrumentPluginCode", "false")
}
vcs {
root(_Self.vcsRoots.GitHubPullRequest)
checkoutMode = CheckoutMode.ON_SERVER
branchFilter = """
+:*
-:<default>
""".trimIndent()
}
steps {
gradle {
tasks = "clean test"
buildFile = ""
enableStacktrace = true
param("org.jfrog.artifactory.selectedDeployableServer.defaultModuleVersionConfiguration", "GLOBAL")
}
}
triggers {
vcs {
quietPeriodMode = VcsTrigger.QuietPeriodMode.USE_DEFAULT
branchFilter = ""
}
}
features {
pullRequests {
provider = github {
authType = token {
token = "credentialsJSON:43afd6e5-6ad5-4d12-a218-cf1547717a7f"
}
filterTargetBranch = "refs/heads/master"
filterAuthorRole = PullRequests.GitHubRoleFilter.EVERYBODY
}
}
commitStatusPublisher {
vcsRootExtId = "${GitHubPullRequest.id}"
publisher = github {
githubUrl = "https://api.github.com"
authType = personalToken {
token = "credentialsJSON:43afd6e5-6ad5-4d12-a218-cf1547717a7f"
}
}
param("github_oauth_user", "AlexPl292")
}
}
requirements {
noLessThanVer("teamcity.agent.jvm.version", "1.8")
}
})

54
.teamcity/_Self/buildTypes/Nvim.kt vendored Normal file
View File

@@ -0,0 +1,54 @@
package _Self.buildTypes
import jetbrains.buildServer.configs.kotlin.v2019_2.BuildType
import jetbrains.buildServer.configs.kotlin.v2019_2.CheckoutMode
import jetbrains.buildServer.configs.kotlin.v2019_2.DslContext
import jetbrains.buildServer.configs.kotlin.v2019_2.buildSteps.gradle
import jetbrains.buildServer.configs.kotlin.v2019_2.buildSteps.script
import jetbrains.buildServer.configs.kotlin.v2019_2.triggers.vcs
object Nvim : BuildType({
name = "Tests with nvim"
description = "Running tests with nvim integration"
params {
param("env.ORG_GRADLE_PROJECT_downloadIdeaSources", "false")
param("env.ORG_GRADLE_PROJECT_ideaVersion", "LATEST-EAP-SNAPSHOT")
param("env.ORG_GRADLE_PROJECT_instrumentPluginCode", "false")
param("env.ideavim.nvim.path", "./nvim-linux64/bin/nvim")
}
vcs {
root(DslContext.settingsRoot)
checkoutMode = CheckoutMode.ON_SERVER
}
steps {
script {
name = "Set up NeoVim"
scriptContent = """
wget https://github.com/neovim/neovim/releases/download/v0.4.4/nvim-linux64.tar.gz
tar xzf nvim-linux64.tar.gz
cd nvim-linux64/bin
chmod +x nvim
""".trimIndent()
}
gradle {
tasks = "clean testWithNeovim"
buildFile = ""
enableStacktrace = true
param("org.jfrog.artifactory.selectedDeployableServer.defaultModuleVersionConfiguration", "GLOBAL")
}
}
triggers {
vcs {
branchFilter = ""
}
}
requirements {
noLessThanVer("teamcity.agent.jvm.version", "1.8")
}
})

View File

@@ -0,0 +1,40 @@
package _Self.buildTypes
import jetbrains.buildServer.configs.kotlin.v2019_2.BuildType
import jetbrains.buildServer.configs.kotlin.v2019_2.CheckoutMode
import jetbrains.buildServer.configs.kotlin.v2019_2.DslContext
import jetbrains.buildServer.configs.kotlin.v2019_2.buildSteps.gradle
import jetbrains.buildServer.configs.kotlin.v2019_2.triggers.vcs
object PluginVerifier : BuildType({
name = "Plugin verification"
params {
param("env.ORG_GRADLE_PROJECT_downloadIdeaSources", "false")
param("env.ORG_GRADLE_PROJECT_instrumentPluginCode", "false")
}
vcs {
root(DslContext.settingsRoot)
checkoutMode = CheckoutMode.ON_SERVER
}
steps {
gradle {
tasks = "clean runPluginVerifier"
buildFile = ""
enableStacktrace = true
param("org.jfrog.artifactory.selectedDeployableServer.defaultModuleVersionConfiguration", "GLOBAL")
}
}
triggers {
vcs {
branchFilter = ""
}
}
requirements {
noLessThanVer("teamcity.agent.jvm.version", "1.8")
}
})

42
.teamcity/_Self/buildTypes/Release.kt vendored Normal file
View File

@@ -0,0 +1,42 @@
package _Self.buildTypes
import jetbrains.buildServer.configs.kotlin.v2019_2.BuildType
import jetbrains.buildServer.configs.kotlin.v2019_2.CheckoutMode
import jetbrains.buildServer.configs.kotlin.v2019_2.DslContext
import jetbrains.buildServer.configs.kotlin.v2019_2.buildSteps.gradle
object Release : BuildType({
name = "Publish Release"
description = "Build and publish IdeaVim plugin"
artifactRules = "build/distributions/*"
buildNumberPattern = "0.61"
params {
param("env.ORG_GRADLE_PROJECT_ideaVersion", "2020.2")
password(
"env.ORG_GRADLE_PROJECT_publishToken",
"credentialsJSON:ec1dc748-e289-47e1-88b6-f193d7999bf4",
label = "Password"
)
param("env.ORG_GRADLE_PROJECT_publishUsername", "vlan")
param("env.ORG_GRADLE_PROJECT_version", "%build.number%")
param("env.ORG_GRADLE_PROJECT_downloadIdeaSources", "false")
param("env.ORG_GRADLE_PROJECT_publishChannels", "default,eap")
}
vcs {
root(DslContext.settingsRoot)
checkoutMode = CheckoutMode.ON_SERVER
}
steps {
gradle {
tasks = "clean publishPlugin"
buildFile = ""
enableStacktrace = true
param("org.jfrog.artifactory.selectedDeployableServer.defaultModuleVersionConfiguration", "GLOBAL")
}
}
})

View File

@@ -0,0 +1,75 @@
package _Self.buildTypes
import jetbrains.buildServer.configs.kotlin.v2019_2.BuildType
import jetbrains.buildServer.configs.kotlin.v2019_2.CheckoutMode
import jetbrains.buildServer.configs.kotlin.v2019_2.DslContext
import jetbrains.buildServer.configs.kotlin.v2019_2.buildFeatures.vcsLabeling
import jetbrains.buildServer.configs.kotlin.v2019_2.buildSteps.gradle
import jetbrains.buildServer.configs.kotlin.v2019_2.triggers.ScheduleTrigger
import jetbrains.buildServer.configs.kotlin.v2019_2.triggers.schedule
object ReleaseEap : BuildType({
name = "Publish EAP Build"
description = "Build and publish EAP of IdeaVim plugin"
artifactRules = "build/distributions/*"
buildNumberPattern = "0.61.%build.counter%"
params {
param("env.ORG_GRADLE_PROJECT_ideaVersion", "2020.2")
password(
"env.ORG_GRADLE_PROJECT_publishToken",
"credentialsJSON:ec1dc748-e289-47e1-88b6-f193d7999bf4",
label = "Token"
)
param("env.ORG_GRADLE_PROJECT_publishUsername", "vlan")
param("env.ORG_GRADLE_PROJECT_version", "%build.number%")
param("env.ORG_GRADLE_PROJECT_downloadIdeaSources", "false")
param("env.ORG_GRADLE_PROJECT_publishChannels", "eap")
password(
"env.ORG_GRADLE_PROJECT_slackUrl",
"credentialsJSON:a8ab8150-e6f8-4eaf-987c-bcd65eac50b5",
label = "Slack Token"
)
}
vcs {
root(DslContext.settingsRoot)
checkoutMode = CheckoutMode.ON_SERVER
}
steps {
gradle {
tasks = "clean publishPlugin slackEapNotification"
buildFile = ""
enableStacktrace = true
param("org.jfrog.artifactory.selectedDeployableServer.defaultModuleVersionConfiguration", "GLOBAL")
}
}
triggers {
schedule {
enabled = false
schedulingPolicy = daily {
hour = 22
}
branchFilter = ""
triggerBuild = onWatchedBuildChange {
buildType = "IdeaVim_TestsForIntelliJBranch146"
watchedBuildRule = ScheduleTrigger.WatchedBuildRule.LAST_SUCCESSFUL
watchedBuildBranchFilter = "<default>"
promoteWatchedBuild = false
}
}
}
features {
vcsLabeling {
vcsRootId = "${DslContext.settingsRoot.id}"
labelingPattern = "%system.build.number%-EAP"
successfulOnly = true
branchFilter = ""
}
}
})

View File

@@ -0,0 +1,44 @@
package _Self.buildTypes
import jetbrains.buildServer.configs.kotlin.v2019_2.BuildType
import jetbrains.buildServer.configs.kotlin.v2019_2.CheckoutMode
import jetbrains.buildServer.configs.kotlin.v2019_2.buildSteps.gradle
import jetbrains.buildServer.configs.kotlin.v2019_2.triggers.vcs
object TestsForIntelliJ20183 : BuildType({
name = "Tests for IntelliJ 2018.3"
description = "branch 183"
params {
param("env.ORG_GRADLE_PROJECT_downloadIdeaSources", "false")
param("env.ORG_GRADLE_PROJECT_legacyNoJavaPlugin", "true")
param("env.ORG_GRADLE_PROJECT_ideaVersion", "IC-2018.3")
param("env.ORG_GRADLE_PROJECT_instrumentPluginCode", "false")
param("env.ORG_GRADLE_PROJECT_javaVersion", "1.8")
}
vcs {
root(_Self.vcsRoots.Branch_183)
checkoutMode = CheckoutMode.ON_SERVER
}
steps {
gradle {
tasks = "clean test"
buildFile = ""
enableStacktrace = true
param("org.jfrog.artifactory.selectedDeployableServer.defaultModuleVersionConfiguration", "GLOBAL")
}
}
triggers {
vcs {
branchFilter = ""
}
}
requirements {
noLessThanVer("teamcity.agent.jvm.version", "1.8")
}
})

View File

@@ -0,0 +1,47 @@
@file:Suppress("ClassName")
package _Self.buildTypes
import jetbrains.buildServer.configs.kotlin.v2019_2.BuildType
import jetbrains.buildServer.configs.kotlin.v2019_2.CheckoutMode
import jetbrains.buildServer.configs.kotlin.v2019_2.buildSteps.gradle
import jetbrains.buildServer.configs.kotlin.v2019_2.triggers.vcs
sealed class TestsForIntelliJ_181_branch(private val version: String) : BuildType({
name = "Tests for IntelliJ $version"
params {
param("env.ORG_GRADLE_PROJECT_downloadIdeaSources", "false")
param("env.ORG_GRADLE_PROJECT_ideaVersion", "IC-$version")
param("env.ORG_GRADLE_PROJECT_instrumentPluginCode", "false")
param("env.ORG_GRADLE_PROJECT_javaVersion", "1.8")
}
vcs {
root(_Self.vcsRoots.Branch_181)
checkoutMode = CheckoutMode.ON_SERVER
}
steps {
gradle {
tasks = "clean test"
buildFile = ""
enableStacktrace = true
param("org.jfrog.artifactory.selectedDeployableServer.defaultModuleVersionConfiguration", "GLOBAL")
}
}
triggers {
vcs {
branchFilter = ""
}
}
requirements {
noLessThanVer("teamcity.agent.jvm.version", "1.8")
}
})
object TestsForIntelliJ20181 : TestsForIntelliJ_181_branch("2018.1")
object TestsForIntelliJ20182 : TestsForIntelliJ_181_branch("2018.2")

View File

@@ -0,0 +1,49 @@
@file:Suppress("ClassName")
package _Self.buildTypes
import jetbrains.buildServer.configs.kotlin.v2019_2.BuildType
import jetbrains.buildServer.configs.kotlin.v2019_2.CheckoutMode
import jetbrains.buildServer.configs.kotlin.v2019_2.buildSteps.gradle
import jetbrains.buildServer.configs.kotlin.v2019_2.triggers.vcs
sealed class TestsForIntelliJ_191_193_branch(private val version: String) : BuildType({
name = "Tests for IntelliJ $version"
params {
param("env.ORG_GRADLE_PROJECT_downloadIdeaSources", "false")
param("env.ORG_GRADLE_PROJECT_legacyNoJavaPlugin", "true")
param("env.ORG_GRADLE_PROJECT_ideaVersion", "IC-$version")
param("env.ORG_GRADLE_PROJECT_instrumentPluginCode", "false")
param("env.ORG_GRADLE_PROJECT_javaVersion", "1.8")
}
vcs {
root(_Self.vcsRoots.Branch_191_193)
checkoutMode = CheckoutMode.ON_SERVER
}
steps {
gradle {
tasks = "clean test"
buildFile = ""
enableStacktrace = true
param("org.jfrog.artifactory.selectedDeployableServer.defaultModuleVersionConfiguration", "GLOBAL")
}
}
triggers {
vcs {
branchFilter = ""
}
}
requirements {
noLessThanVer("teamcity.agent.jvm.version", "1.8")
}
})
object TestsForIntelliJ20191 : TestsForIntelliJ_191_193_branch("2019.1")
object TestsForIntelliJ20192 : TestsForIntelliJ_191_193_branch("2019.2")
object TestsForIntelliJ20193 : TestsForIntelliJ_191_193_branch("2019.3")

12
.teamcity/_Self/vcsRoots/Branch_181.kt vendored Normal file
View File

@@ -0,0 +1,12 @@
@file:Suppress("ClassName")
package _Self.vcsRoots
import jetbrains.buildServer.configs.kotlin.v2019_2.vcs.GitVcsRoot
object Branch_181 : GitVcsRoot({
name = "https://github.com/JetBrains/ideavim (branch 181)"
url = "https://github.com/JetBrains/ideavim.git"
branch = "181"
useMirrors = false
})

12
.teamcity/_Self/vcsRoots/Branch_183.kt vendored Normal file
View File

@@ -0,0 +1,12 @@
@file:Suppress("ClassName")
package _Self.vcsRoots
import jetbrains.buildServer.configs.kotlin.v2019_2.vcs.GitVcsRoot
object Branch_183 : GitVcsRoot({
name = "https://github.com/JetBrains/ideavim (branch 183)"
url = "https://github.com/JetBrains/ideavim.git"
branch = "183"
useMirrors = false
})

View File

@@ -0,0 +1,12 @@
@file:Suppress("ClassName")
package _Self.vcsRoots
import jetbrains.buildServer.configs.kotlin.v2019_2.vcs.GitVcsRoot
object Branch_191_193 : GitVcsRoot({
name = "https://github.com/JetBrains/ideavim (branch 191-193)"
url = "https://github.com/JetBrains/ideavim.git"
branch = "191-193"
useMirrors = false
})

View File

@@ -0,0 +1,12 @@
package _Self.vcsRoots
import jetbrains.buildServer.configs.kotlin.v2019_2.vcs.GitVcsRoot
object GitHubPullRequest : GitVcsRoot({
name = "IdeaVim Pull Requests"
url = "git@github.com:JetBrains/ideavim.git"
branchSpec = "+:refs/(pull/*)/head"
authMethod = uploadedKey {
uploadedKey = "Alex Plate TeamCity key"
}
})

104
.teamcity/pom.xml vendored Normal file
View File

@@ -0,0 +1,104 @@
<?xml version="1.0"?>
<project>
<modelVersion>4.0.0</modelVersion>
<name>IdeaVim Config DSL Script</name>
<groupId>IdeaVim</groupId>
<artifactId>IdeaVim_dsl</artifactId>
<version>1.0-SNAPSHOT</version>
<parent>
<groupId>org.jetbrains.teamcity</groupId>
<artifactId>configs-dsl-kotlin-parent</artifactId>
<version>1.0-SNAPSHOT</version>
</parent>
<repositories>
<repository>
<id>jetbrains-all</id>
<url>https://download.jetbrains.com/teamcity-repository</url>
<snapshots>
<enabled>true</enabled>
</snapshots>
</repository>
<repository>
<id>teamcity-server</id>
<url>https://teamcity.jetbrains.com/app/dsl-plugins-repository</url>
<snapshots>
<enabled>true</enabled>
</snapshots>
</repository>
</repositories>
<pluginRepositories>
<pluginRepository>
<id>JetBrains</id>
<url>https://download.jetbrains.com/teamcity-repository</url>
</pluginRepository>
</pluginRepositories>
<build>
<sourceDirectory>${basedir}</sourceDirectory>
<plugins>
<plugin>
<artifactId>kotlin-maven-plugin</artifactId>
<groupId>org.jetbrains.kotlin</groupId>
<version>${kotlin.version}</version>
<configuration/>
<executions>
<execution>
<id>compile</id>
<phase>process-sources</phase>
<goals>
<goal>compile</goal>
</goals>
</execution>
<execution>
<id>test-compile</id>
<phase>process-test-sources</phase>
<goals>
<goal>test-compile</goal>
</goals>
</execution>
</executions>
</plugin>
<plugin>
<groupId>org.jetbrains.teamcity</groupId>
<artifactId>teamcity-configs-maven-plugin</artifactId>
<version>${teamcity.dsl.version}</version>
<configuration>
<format>kotlin</format>
<dstDir>target/generated-configs</dstDir>
</configuration>
</plugin>
</plugins>
</build>
<dependencies>
<dependency>
<groupId>org.jetbrains.teamcity</groupId>
<artifactId>configs-dsl-kotlin</artifactId>
<version>${teamcity.dsl.version}</version>
<scope>compile</scope>
</dependency>
<dependency>
<groupId>org.jetbrains.teamcity</groupId>
<artifactId>configs-dsl-kotlin-plugins</artifactId>
<version>1.0-SNAPSHOT</version>
<type>pom</type>
<scope>compile</scope>
</dependency>
<dependency>
<groupId>org.jetbrains.kotlin</groupId>
<artifactId>kotlin-stdlib-jdk8</artifactId>
<version>${kotlin.version}</version>
<scope>compile</scope>
</dependency>
<dependency>
<groupId>org.jetbrains.kotlin</groupId>
<artifactId>kotlin-script-runtime</artifactId>
<version>${kotlin.version}</version>
<scope>compile</scope>
</dependency>
</dependencies>
</project>

33
.teamcity/settings.kts vendored Normal file
View File

@@ -0,0 +1,33 @@
import jetbrains.buildServer.configs.kotlin.v2019_2.*
/*
The settings script is an entry point for defining a single
TeamCity project. TeamCity looks for the 'settings.kts' file in a
project directory and runs it if it's found, so the script name
shouldn't be changed and its package should be the same as the
project's id.
The script should contain a single call to the project() function
with a Project instance or an init function as an argument.
VcsRoots, BuildTypes, and Templates of this project must be
registered inside project using the vcsRoot(), buildType(), and
template() methods respectively.
Subprojects can be defined either in their own settings.kts or by
calling the subProjects() method in this project.
To debug settings scripts in command-line, run the
mvnDebug org.jetbrains.teamcity:teamcity-configs-maven-plugin:generate
command and attach your debugger to the port 8000.
To debug in IntelliJ Idea, open the 'Maven Projects' tool window (View ->
Tool Windows -> Maven Projects), find the generate task
node (Plugins -> teamcity-configs -> teamcity-configs:generate),
the 'Debug' option is available in the context menu for the task.
*/
version = "2020.1"
project(_Self.Project)

View File

@@ -22,13 +22,51 @@ It is important to distinguish EAP from traditional pre-release software.
Please note that the quality of EAP versions may at times be way below even Please note that the quality of EAP versions may at times be way below even
usual beta standards. usual beta standards.
To Be Released ## To Be Released
-----------
**Features:** ...
## 0.61, 2020-11-12
### Features:
* Ability to map IDE actions via the `<Action>` keyword. E.g. `map <C-K> <Action>(CommentByLineComment)`.
Check out `README.md` for the details.
* `IdeaVim: track action Ids` command to find action ids for the `:action` command.
Enable this option in "Search everywhere" (double shift).
* Ability to enable extensions using `vim-plug` or `vundle` syntax.
E.g. to enable commentary extension you can use one of the following commands:
```vim
set commentary
Plug 'tpope/vim-commentary'
Plug 'https://github.com/tpope/vim-commentary'
Plugin 'tpope/vim-commentary'
...
```
This approach is especially handy if you have `.vimrc` with plugins registered via `vim-plug` or `vundle`.
### Changes:
* Fix `<Esc>` for dialogs. Now `<Esc>` will exit insert / visual mode and close the dialog from normal mode.
* Add option to disable IdeaVim in dialogs / single line editors. [VIM-765](https://youtrack.jetbrains.com/issue/VIM-765)
Use `set ideavimsupport=` to disable IdeaVim in dialog editors.
* Reposition cursor when `scrolloff` changes
### Fixes:
* [VIM-2150](https://youtrack.jetbrains.com/issue/VIM-2150) `Shift-D` should not delete an empty line
* [VIM-2157](https://youtrack.jetbrains.com/issue/VIM-2157) Fix tab with an active template
* [VIM-2156](https://youtrack.jetbrains.com/issue/VIM-2156) Correct up/down motions with inlays
* [VIM-2144](https://youtrack.jetbrains.com/issue/VIM-2144) Correct text position after block insert with inlays
* [VIM-2158](https://youtrack.jetbrains.com/issue/VIM-2158) Fix scrolling when `scrolloff` is over half screen height, but less than full height
### Merged PRs:
* [255](https://github.com/JetBrains/ideavim/pull/255) by [Matt Ellis](https://github.com/citizenmatt): Fix various scrolling issues
## 0.60, 2020-10-09
### Features:
* Support of `virtualedit=onemore` ([VIM-844](https://youtrack.jetbrains.com/issue/VIM-844)) * Support of `virtualedit=onemore` ([VIM-844](https://youtrack.jetbrains.com/issue/VIM-844))
**Fixes:** ### Fixes:
* [VIM-2097](https://youtrack.jetbrains.com/issue/VIM-2097) Do not apply mappings for register selecting * [VIM-2097](https://youtrack.jetbrains.com/issue/VIM-2097) Do not apply mappings for register selecting
* [VIM-2080](https://youtrack.jetbrains.com/issue/VIM-2080) Fix S command with count * [VIM-2080](https://youtrack.jetbrains.com/issue/VIM-2080) Fix S command with count
* [VIM-2099](https://youtrack.jetbrains.com/issue/VIM-2099) Fix operations with backward inclusive motions * [VIM-2099](https://youtrack.jetbrains.com/issue/VIM-2099) Fix operations with backward inclusive motions
@@ -38,22 +76,21 @@ To Be Released
* [VIM-1770](https://youtrack.jetbrains.com/issue/VIM-1770) Fix goto end with large inline hints * [VIM-1770](https://youtrack.jetbrains.com/issue/VIM-1770) Fix goto end with large inline hints
* [VIM-2110](https://youtrack.jetbrains.com/issue/VIM-2110) Fix scrolling for non-monospaced fonts * [VIM-2110](https://youtrack.jetbrains.com/issue/VIM-2110) Fix scrolling for non-monospaced fonts
**Changes:** ### Changes:
* `:w` works as `:wa` by default. This can be disabled with `ideawrite` option. * `:w` works as `:wa` by default. This can be disabled with `ideawrite` option.
Now features like `Prettier on save` or `Run on save for files` would work with `:w` command as well. Now features like `Prettier on save` or `Run on save for files` would work with `:w` command as well.
See [VIM-1968](https://youtrack.jetbrains.com/issue/VIM-1968). See [VIM-1968](https://youtrack.jetbrains.com/issue/VIM-1968).
**Merged PRs:** ### Merged PRs:
* [248](https://github.com/JetBrains/ideavim/pull/248) by [Yaohui Wang](https://github.com/yaohui-wyh): Check if project is disposed when editorDeinit * [248](https://github.com/JetBrains/ideavim/pull/248) by [Yaohui Wang](https://github.com/yaohui-wyh): Check if project is disposed when editorDeinit
* [242](https://github.com/JetBrains/ideavim/pull/242) by [Iain Ballard](https://github.com/i-e-b): Partial implementation of virtualedit config * [242](https://github.com/JetBrains/ideavim/pull/242) by [Iain Ballard](https://github.com/i-e-b): Partial implementation of virtualedit config
* [252](https://github.com/JetBrains/ideavim/pull/252) by [Matt Ellis](https://github.com/citizenmatt): Fixes for scrolling * [252](https://github.com/JetBrains/ideavim/pull/252) by [Matt Ellis](https://github.com/citizenmatt): Fixes for scrolling
0.59, 2020-08-25 ## 0.59, 2020-08-25
------------
**Features:** ### Features:
* `vim-highlightedyank` plugin emulation ([VIM-1970](https://youtrack.jetbrains.com/issue/VIM-1970) | [vim-highlightedyank](https://github.com/machakann/vim-highlightedyank)). * `vim-highlightedyank` plugin emulation ([VIM-1970](https://youtrack.jetbrains.com/issue/VIM-1970) | [vim-highlightedyank](https://github.com/machakann/vim-highlightedyank)).
* <details> * <details>
@@ -63,22 +100,21 @@ To Be Released
* [VIM-2068](https://youtrack.jetbrains.com/issue/VIM-2068) `:tabclose` command * [VIM-2068](https://youtrack.jetbrains.com/issue/VIM-2068) `:tabclose` command
**Fixes:** ### Fixes:
* [VIM-1421](https://youtrack.jetbrains.com/issue/VIM-1421) Escape key finishes `t` and `f` motions * [VIM-1421](https://youtrack.jetbrains.com/issue/VIM-1421) Escape key finishes `t` and `f` motions
* [VIM-2075](https://youtrack.jetbrains.com/issue/VIM-2075) Fix zR command * [VIM-2075](https://youtrack.jetbrains.com/issue/VIM-2075) Fix zR command
* [VIM-2059](https://youtrack.jetbrains.com/issue/VIM-2059) Fixed macro editing * [VIM-2059](https://youtrack.jetbrains.com/issue/VIM-2059) Fixed macro editing
**Merged PRs:** ### Merged PRs:
* [237](https://github.com/JetBrains/ideavim/pull/237) by [Adrià Farrés](https://github.com/adriafarres): Reset operator-pending commands on escape * [237](https://github.com/JetBrains/ideavim/pull/237) by [Adrià Farrés](https://github.com/adriafarres): Reset operator-pending commands on escape
* [241](https://github.com/JetBrains/ideavim/pull/241) by [Patrick Elmquist](https://github.com/patrick-elmquist): Properly reset when pressing Esc in the middle of command * [241](https://github.com/JetBrains/ideavim/pull/241) by [Patrick Elmquist](https://github.com/patrick-elmquist): Properly reset when pressing Esc in the middle of command
* [244](https://github.com/JetBrains/ideavim/pull/244) by [Rieon Ke](https://github.com/rieonke): Implement tabc[lose] ex command * [244](https://github.com/JetBrains/ideavim/pull/244) by [Rieon Ke](https://github.com/rieonke): Implement tabc[lose] ex command
* [240](https://github.com/JetBrains/ideavim/pull/240) by [Rieon Ke](https://github.com/rieonke): add support for putting & editing macros * [240](https://github.com/JetBrains/ideavim/pull/240) by [Rieon Ke](https://github.com/rieonke): add support for putting & editing macros
* [245](https://github.com/JetBrains/ideavim/pull/245) by [KostkaBrukowa](https://github.com/KostkaBrukowa): VIM-1970 | Working solution of plugin vim-highlightedyank * [245](https://github.com/JetBrains/ideavim/pull/245) by [KostkaBrukowa](https://github.com/KostkaBrukowa): VIM-1970 | Working solution of plugin vim-highlightedyank
0.58, 2020-07-07 ## 0.58, 2020-07-07
-------------
**Features:** ### Features:
* `exchange` plugin emulation ([VIM-921](https://youtrack.jetbrains.com/issue/VIM-921) | [vim-exchange](https://github.com/tommcdo/vim-exchange)). * `exchange` plugin emulation ([VIM-921](https://youtrack.jetbrains.com/issue/VIM-921) | [vim-exchange](https://github.com/tommcdo/vim-exchange)).
* `~/.ideavimrc` file can be reloaded using the new floating action. * `~/.ideavimrc` file can be reloaded using the new floating action.
@@ -89,10 +125,10 @@ To Be Released
* Add `:buffer` command. * Add `:buffer` command.
**Changes:** ### Changes:
* Support IntelliJ's smooth scrolling. Use "Enable smooth scrolling" checkbox in _Preferences | Editor | General_ to disable. * Support IntelliJ's smooth scrolling. Use "Enable smooth scrolling" checkbox in _Preferences | Editor | General_ to disable.
**Fixes:** ### Fixes:
* [VIM-1994](https://youtrack.jetbrains.com/issue/VIM-1994) Correct paste after `y}P` command. * [VIM-1994](https://youtrack.jetbrains.com/issue/VIM-1994) Correct paste after `y}P` command.
* [VIM-1924](https://youtrack.jetbrains.com/issue/VIM-1924) Select next occurrence doesn't become block selection. * [VIM-1924](https://youtrack.jetbrains.com/issue/VIM-1924) Select next occurrence doesn't become block selection.
* [VIM-2038](https://youtrack.jetbrains.com/issue/VIM-2038) Last line is now accessible in normal mode * [VIM-2038](https://youtrack.jetbrains.com/issue/VIM-2038) Last line is now accessible in normal mode
@@ -102,7 +138,7 @@ To Be Released
* Fix mappings to `"\<SPACE>"` including `let mapleader="\<SPACE>"` * Fix mappings to `"\<SPACE>"` including `let mapleader="\<SPACE>"`
**Merged PRs:** ### Merged PRs:
* [233](https://github.com/JetBrains/ideavim/pull/233) by [valis](https://github.com/valis): [VIM-1994] Correct paste after `y}P` command. * [233](https://github.com/JetBrains/ideavim/pull/233) by [valis](https://github.com/valis): [VIM-1994] Correct paste after `y}P` command.
* [224](https://github.com/JetBrains/ideavim/pull/224) by [pmnoxx](https://github.com/pmnoxx): Populate intelij navigation history together with ideavim jumplist. * [224](https://github.com/JetBrains/ideavim/pull/224) by [pmnoxx](https://github.com/pmnoxx): Populate intelij navigation history together with ideavim jumplist.
* [227](https://github.com/JetBrains/ideavim/pull/227) by [angelbot](https://github.com/angelbot): Add support for buffer command. * [227](https://github.com/JetBrains/ideavim/pull/227) by [angelbot](https://github.com/angelbot): Add support for buffer command.
@@ -110,33 +146,31 @@ To Be Released
* [231](https://github.com/JetBrains/ideavim/pull/231) by [citizenmatt](https://github.com/citizenmatt): Support smooth scrolling. * [231](https://github.com/JetBrains/ideavim/pull/231) by [citizenmatt](https://github.com/citizenmatt): Support smooth scrolling.
* [239](https://github.com/JetBrains/ideavim/pull/239) by [citizenmatt](https://github.com/citizenmatt): Use new API for relative line numbers * [239](https://github.com/JetBrains/ideavim/pull/239) by [citizenmatt](https://github.com/citizenmatt): Use new API for relative line numbers
0.57, 2020-04-28 ## 0.57, 2020-04-28
-------------
**Fixes:** ### Fixes:
* [VIM-1992](https://youtrack.jetbrains.com/issue/VIM-1992) Fix mappings to `<S-Letter>` * [VIM-1992](https://youtrack.jetbrains.com/issue/VIM-1992) Fix mappings to `<S-Letter>`
* [VIM-1991](https://youtrack.jetbrains.com/issue/VIM-1991) Fix working with number registers * [VIM-1991](https://youtrack.jetbrains.com/issue/VIM-1991) Fix working with number registers
**Merged PRs:** ### Merged PRs:
* [234](https://github.com/JetBrains/ideavim/pull/234) by [runforprogram](https://github.com/runforprogram): [VIM-1991] fix >0 number register not work * [234](https://github.com/JetBrains/ideavim/pull/234) by [runforprogram](https://github.com/runforprogram): [VIM-1991] fix >0 number register not work
0.56, 2020-04-09 ## 0.56, 2020-04-09
--------------
**Features:** ### Features:
* `ReplaceWithRegister` plugin emulation ([ReplaceWithRegister](https://www.vim.org/scripts/script.php?script_id=2703)). * `ReplaceWithRegister` plugin emulation ([ReplaceWithRegister](https://www.vim.org/scripts/script.php?script_id=2703)).
* `argtextobj.vim` plugin emulation ([argtextobj.vim](https://vim.sourceforge.io/scripts/script.php?script_id=2699)). * `argtextobj.vim` plugin emulation ([argtextobj.vim](https://vim.sourceforge.io/scripts/script.php?script_id=2699)).
* `vim-textobj-entire` plugin emulation ([vim-textobj-entire](https://github.com/kana/vim-textobj-entire)). * `vim-textobj-entire` plugin emulation ([vim-textobj-entire](https://github.com/kana/vim-textobj-entire)).
* [VIM-434](https://youtrack.jetbrains.com/issue/VIM-434) Add `'showcmd'` support, on by default. * [VIM-434](https://youtrack.jetbrains.com/issue/VIM-434) Add `'showcmd'` support, on by default.
* Support `ls/buffers/files` commands. * Support `ls/buffers/files` commands.
**Changes:** ### Changes:
* Replace `ideastatusbar` option with `ideastatusicon`. Now you can make the icon gray. * Replace `ideastatusbar` option with `ideastatusicon`. Now you can make the icon gray.
**Deprecations:** ### Deprecations:
* `ideastatusbar` option is deprecated now. See `ideastatusicon`. * `ideastatusbar` option is deprecated now. See `ideastatusicon`.
**Fixes:** ### Fixes:
* [VIM-1284](https://youtrack.jetbrains.com/issue/VIM-1284) Fix mapping of digits. * [VIM-1284](https://youtrack.jetbrains.com/issue/VIM-1284) Fix mapping of digits.
* Fix handling of counts on both operator and motion, e.g. `3d2w` deletes 6 words, instead of 32. * Fix handling of counts on both operator and motion, e.g. `3d2w` deletes 6 words, instead of 32.
* Allow mapping of `<C-K>` and `<C-V>`/`<C-Q>`. * Allow mapping of `<C-K>` and `<C-V>`/`<C-Q>`.
@@ -149,15 +183,14 @@ To Be Released
* [VIM-1911](https://youtrack.jetbrains.com/issue/VIM-1911) Lookup keys respect `IDE` handler. * [VIM-1911](https://youtrack.jetbrains.com/issue/VIM-1911) Lookup keys respect `IDE` handler.
* [VIM-1008](https://youtrack.jetbrains.com/issue/VIM-1008) Correct `ci{` behavior. * [VIM-1008](https://youtrack.jetbrains.com/issue/VIM-1008) Correct `ci{` behavior.
0.55, 2020-01-20 ## 0.55, 2020-01-20
--------------
**Features:** ### Features:
* Surround and Commentary extensions support repeating with a dot command ([VIM-1118](https://youtrack.jetbrains.com/issue/VIM-1118)) * Surround and Commentary extensions support repeating with a dot command ([VIM-1118](https://youtrack.jetbrains.com/issue/VIM-1118))
* Support XDG settings standard ([VIM-664](https://youtrack.jetbrains.com/issue/VIM-664)) * Support XDG settings standard ([VIM-664](https://youtrack.jetbrains.com/issue/VIM-664))
* Add option to remove the status bar icon ([VIM-1847](https://youtrack.jetbrains.com/issue/VIM-1847)) * Add option to remove the status bar icon ([VIM-1847](https://youtrack.jetbrains.com/issue/VIM-1847))
**Fixes:** ### Fixes:
* [VIM-1823](https://youtrack.jetbrains.com/issue/VIM-1823) Fix multiple carets with ignorecase * [VIM-1823](https://youtrack.jetbrains.com/issue/VIM-1823) Fix multiple carets with ignorecase
* [VIM-1053](https://youtrack.jetbrains.com/issue/VIM-1053) * [VIM-1053](https://youtrack.jetbrains.com/issue/VIM-1053)
[VIM-1038](https://youtrack.jetbrains.com/issue/VIM-1038) [VIM-1038](https://youtrack.jetbrains.com/issue/VIM-1038)
@@ -180,21 +213,20 @@ To Be Released
* [VIM-1884](https://youtrack.jetbrains.com/issue/VIM-1884) Show quickDoc during popup with `CTRL-J` * [VIM-1884](https://youtrack.jetbrains.com/issue/VIM-1884) Show quickDoc during popup with `CTRL-J`
* [VIM-987](https://youtrack.jetbrains.com/issue/VIM-987) Fix arrow keys for the NEO keyboard * [VIM-987](https://youtrack.jetbrains.com/issue/VIM-987) Fix arrow keys for the NEO keyboard
0.54, 2019-11-20 ## 0.54, 2019-11-20
--------------
**Features:** ### Features:
* EasyMotion plugin emulation ([VIM-820](https://youtrack.jetbrains.com/issue/VIM-820) | [Instructions](https://github.com/JetBrains/ideavim#emulated-vim-plugins)) * EasyMotion plugin emulation ([VIM-820](https://youtrack.jetbrains.com/issue/VIM-820) | [Instructions](https://github.com/JetBrains/ideavim#emulated-vim-plugins))
* Support surrounding with a function name ([link](https://github.com/tpope/vim-surround/blob/master/doc/surround.txt#L138)) * Support surrounding with a function name ([link](https://github.com/tpope/vim-surround/blob/master/doc/surround.txt#L138))
* Add `:delmarks` command ([VIM-1720](https://youtrack.jetbrains.com/issue/VIM-1720)) * Add `:delmarks` command ([VIM-1720](https://youtrack.jetbrains.com/issue/VIM-1720))
* Add IdeaVim icon to the status bar ([VIM-943](https://youtrack.jetbrains.com/issue/VIM-943)) * Add IdeaVim icon to the status bar ([VIM-943](https://youtrack.jetbrains.com/issue/VIM-943))
**Changes:** ### Changes:
* Remove the default IdeaVim toggle shortcut (<kbd>CTRL</kbd><kbd>ALT</kbd><kbd>V</kbd>) * Remove the default IdeaVim toggle shortcut (<kbd>CTRL</kbd><kbd>ALT</kbd><kbd>V</kbd>)
* Rename `refactoring` value of `selectmode` option to `ideaselection` * Rename `refactoring` value of `selectmode` option to `ideaselection`
* Remove `template` value of `selectmode` option and replace it with `idearefactormode` option. * Remove `template` value of `selectmode` option and replace it with `idearefactormode` option.
**Fixes:** ### Fixes:
* [VIM-1766](https://youtrack.jetbrains.com/issue/VIM-1766) Fix disappearing caret in ex entry on Linux * [VIM-1766](https://youtrack.jetbrains.com/issue/VIM-1766) Fix disappearing caret in ex entry on Linux
* [VIM-1032](https://youtrack.jetbrains.com/issue/VIM-1032) Annotations work well with relative line numbers enabled * [VIM-1032](https://youtrack.jetbrains.com/issue/VIM-1032) Annotations work well with relative line numbers enabled
* [VIM-1762](https://youtrack.jetbrains.com/issue/VIM-1762) Relative line numbers respect line number theme * [VIM-1762](https://youtrack.jetbrains.com/issue/VIM-1762) Relative line numbers respect line number theme
@@ -221,8 +253,7 @@ To Be Released
* [VIM-1604](https://youtrack.jetbrains.com/issue/VIM-1604) Add IdeaVim logo * [VIM-1604](https://youtrack.jetbrains.com/issue/VIM-1604) Add IdeaVim logo
0.53, 2019-08-07 ## 0.53, 2019-08-07
--------------
* [VIM-1711](https://youtrack.jetbrains.com/issue/VIM-1711) Search is not triggered during surround action * [VIM-1711](https://youtrack.jetbrains.com/issue/VIM-1711) Search is not triggered during surround action
* [VIM-1712](https://youtrack.jetbrains.com/issue/VIM-1712) Fix `Y` command for visual mode * [VIM-1712](https://youtrack.jetbrains.com/issue/VIM-1712) Fix `Y` command for visual mode
* [VIM-1713](https://youtrack.jetbrains.com/issue/VIM-1713) Surround in visual mode put caret in correct position * [VIM-1713](https://youtrack.jetbrains.com/issue/VIM-1713) Surround in visual mode put caret in correct position
@@ -233,8 +264,7 @@ To Be Released
* [VIM-1736](https://youtrack.jetbrains.com/issue/VIM-1736) Fix `` for ex panel * [VIM-1736](https://youtrack.jetbrains.com/issue/VIM-1736) Fix `` for ex panel
* [VIM-1739](https://youtrack.jetbrains.com/issue/VIM-1739) Fix full-width characters for ex pane * [VIM-1739](https://youtrack.jetbrains.com/issue/VIM-1739) Fix full-width characters for ex pane
0.52, 2019-07-23 ## 0.52, 2019-07-23
--------------
* Introduce [Select Mode](https://github.com/JetBrains/ideavim/wiki/Select-mode). * Introduce [Select Mode](https://github.com/JetBrains/ideavim/wiki/Select-mode).
@@ -327,8 +357,7 @@ To Be Released
* [VIM-1698](https://youtrack.jetbrains.com/issue/VIM-1698) Paste doesn't clear clipboard * [VIM-1698](https://youtrack.jetbrains.com/issue/VIM-1698) Paste doesn't clear clipboard
* [VIM-1359](https://youtrack.jetbrains.com/issue/VIM-1359) Fix behavior of i_CTRL-W action * [VIM-1359](https://youtrack.jetbrains.com/issue/VIM-1359) Fix behavior of i_CTRL-W action
0.51, 2019-02-12 ## 0.51, 2019-02-12
----------------
* [VIM-1558](https://youtrack.jetbrains.com/issue/VIM-1558) Fixed scrolling for code with block inlays in Rider 2018.3 * [VIM-1558](https://youtrack.jetbrains.com/issue/VIM-1558) Fixed scrolling for code with block inlays in Rider 2018.3
* [VIM-1187](https://youtrack.jetbrains.com/issue/VIM-1187) Improved performance of `set relativelinenumber` on large files * [VIM-1187](https://youtrack.jetbrains.com/issue/VIM-1187) Improved performance of `set relativelinenumber` on large files
@@ -336,8 +365,7 @@ To Be Released
* [VIM-798](https://youtrack.jetbrains.com/issue/VIM-798) Allow arrow keys for window navigation commands * [VIM-798](https://youtrack.jetbrains.com/issue/VIM-798) Allow arrow keys for window navigation commands
0.50, 2018-10-18 ## 0.50, 2018-10-18
----------------
Moved "Vim Emulation" settings into "File | Settings | Vim Emulation". Support Moved "Vim Emulation" settings into "File | Settings | Vim Emulation". Support
for vim-multiple-cursors commands `<A-n>`, `<A-x>`, `<A-p>`, `g<A-n>` (put `set for vim-multiple-cursors commands `<A-n>`, `<A-x>`, `<A-p>`, `g<A-n>` (put `set
@@ -363,8 +391,7 @@ Vim commands for multiple cursors. Various bug fixes.
* [VIM-1274](https://youtrack.jetbrains.com/issue/VIM-1274) Correctly process escaping when `smartcase` is on * [VIM-1274](https://youtrack.jetbrains.com/issue/VIM-1274) Correctly process escaping when `smartcase` is on
0.49, 2017-12-12 ## 0.49, 2017-12-12
----------------
Enabled zero-latency typing for Vim emulation. Added support for `iskeyword` option. Various bug fixes. Enabled zero-latency typing for Vim emulation. Added support for `iskeyword` option. Various bug fixes.
@@ -372,8 +399,7 @@ Enabled zero-latency typing for Vim emulation. Added support for `iskeyword` opt
* [VIM-1367](https://youtrack.jetbrains.com/issue/VIM-1367) Support `iskeyword` option * [VIM-1367](https://youtrack.jetbrains.com/issue/VIM-1367) Support `iskeyword` option
* [VIM-523](https://youtrack.jetbrains.com/issue/VIM-523) Fixed global mark remembering only the line number * [VIM-523](https://youtrack.jetbrains.com/issue/VIM-523) Fixed global mark remembering only the line number
0.48, 2017-01-15 ## 0.48, 2017-01-15
----------------
A bugfix release. A bugfix release.
@@ -387,8 +413,7 @@ Features:
* Support for zero-latency rendering * Support for zero-latency rendering
0.47, 2016-10-19 ## 0.47, 2016-10-19
----------------
A bugfix release. A bugfix release.
@@ -398,8 +423,7 @@ Bug fixes:
* VIM-1190 Fixed exception "Write access is allowed from write-safe contexts only" * VIM-1190 Fixed exception "Write access is allowed from write-safe contexts only"
0.46, 2016-07-07 ## 0.46, 2016-07-07
----------------
Added `incsearch` option for incremental search. Added support for `it` and Added `incsearch` option for incremental search. Added support for `it` and
`at` tag block selection. Added `vim-surround` commands `ys`, `cs`, `ds`, `at` tag block selection. Added `vim-surround` commands `ys`, `cs`, `ds`,
@@ -427,8 +451,7 @@ Bug fixes:
* VIM-1126 Fixed warning about modifying shortcuts of global actions for 2016.2 * VIM-1126 Fixed warning about modifying shortcuts of global actions for 2016.2
0.44, 2015-11-02 ## 0.44, 2015-11-02
----------------
A bugfix release. A bugfix release.
@@ -437,16 +460,14 @@ A bugfix release.
plugin disabled plugin disabled
0.43, 2015-11-02 ## 0.43, 2015-11-02
----------------
A bugfix release. A bugfix release.
* VIM-1039 Fixed running the plugin with Java 6 * VIM-1039 Fixed running the plugin with Java 6
0.42, 2015-11-01 ## 0.42, 2015-11-01
----------------
This release is compatible with IntelliJ 15+ and other IDEs based on the This release is compatible with IntelliJ 15+ and other IDEs based on the
IntelliJ platform branch 143+. IntelliJ platform branch 143+.
@@ -454,8 +475,7 @@ IntelliJ platform branch 143+.
* VIM-970 Fixed move commands in read-only files * VIM-970 Fixed move commands in read-only files
0.41, 2015-06-10 ## 0.41, 2015-06-10
----------------
A bugfix release. A bugfix release.
@@ -463,8 +483,7 @@ A bugfix release.
IntelliJ IntelliJ
0.40, 2015-06-09 ## 0.40, 2015-06-09
----------------
Added support for `mapleader`. Support comments in `%` brace matching. Various Added support for `mapleader`. Support comments in `%` brace matching. Various
bug fixes. bug fixes.
@@ -491,8 +510,7 @@ Bug fixes:
* VIM-930 Fixed editor focus issues after closing Ex entry box on Oracle Java 6 * VIM-930 Fixed editor focus issues after closing Ex entry box on Oracle Java 6
0.39, 2014-12-03 ## 0.39, 2014-12-03
----------------
A bugfix release. A bugfix release.
@@ -504,8 +522,7 @@ Bug fixes:
* EA-63022 Don't update line numbers in the caret movement event listener * EA-63022 Don't update line numbers in the caret movement event listener
0.38, 2014-12-01 ## 0.38, 2014-12-01
----------------
Added support for `number` and `relativenumber` options, `clipboard=unnamed` Added support for `number` and `relativenumber` options, `clipboard=unnamed`
option. Added `:action` and `:actionlist` commands for executing arbitrary option. Added `:action` and `:actionlist` commands for executing arbitrary
@@ -537,8 +554,7 @@ Bug fixes:
* VIM-723 Fix pasting to an empty line * VIM-723 Fix pasting to an empty line
0.37, 2014-10-15 ## 0.37, 2014-10-15
----------------
A bugfix release. A bugfix release.
@@ -549,8 +565,7 @@ Bug fixes:
* VIM-407 Fixed `>>` to work if a line contains only one character * VIM-407 Fixed `>>` to work if a line contains only one character
0.36, 2014-10-14 ## 0.36, 2014-10-14
----------------
Added support for common window splitting and navigation commands. Various bug Added support for common window splitting and navigation commands. Various bug
fixes. fixes.
@@ -569,8 +584,7 @@ Bug fixes:
* VIM-569 Fixed `<C-W>` when the caret is at the end of a line * VIM-569 Fixed `<C-W>` when the caret is at the end of a line
0.35, 2014-05-15 ## 0.35, 2014-05-15
----------------
The `~/.vimrc` initialization file is no longer read by default, use The `~/.vimrc` initialization file is no longer read by default, use
`~/.ideavimrc` instead. `~/.ideavimrc` instead.
@@ -591,8 +605,7 @@ Bug fixes:
selection selection
0.34, 2014-04-29 ## 0.34, 2014-04-29
----------------
A bugfix release. A bugfix release.
@@ -606,8 +619,7 @@ Bug fixes:
* VIM-667 Ignore potentially nested lines of .vimrc based on leading whitespace * VIM-667 Ignore potentially nested lines of .vimrc based on leading whitespace
0.33, 2014-04-28 ## 0.33, 2014-04-28
----------------
Added support for `:map` key mapping commands. New keyboard shortcuts handler Added support for `:map` key mapping commands. New keyboard shortcuts handler
that doesn't require a separate keymap for Vim emulation. Added support for that doesn't require a separate keymap for Vim emulation. Added support for
@@ -626,14 +638,12 @@ Bug fixes:
* VIM-281 Don't disable global reformat code action for Vim emulation * VIM-281 Don't disable global reformat code action for Vim emulation
0.32, 2013-11-15 ## 0.32, 2013-11-15
----------------
Fixed API compatibility with IntelliJ platform builds 132.1052+. Fixed API compatibility with IntelliJ platform builds 132.1052+.
0.31, 2013-11-12 ## 0.31, 2013-11-12
----------------
A bugfix release. A bugfix release.
@@ -642,8 +652,7 @@ Bug fixes:
* VIM-582 Fixed line comment and reformat commands with no visual selection * VIM-582 Fixed line comment and reformat commands with no visual selection
0.30, 2013-11-11 ## 0.30, 2013-11-11
----------------
Added support for a separate `.ideavimrc` config file. Fixed long-standing Added support for a separate `.ideavimrc` config file. Fixed long-standing
issues with merged undo/redo commands and `<Esc>` during code completion. issues with merged undo/redo commands and `<Esc>` during code completion.
@@ -663,8 +672,7 @@ Bug fixes:
* Fixed several reported exceptions * Fixed several reported exceptions
0.29, 2013-05-15 ## 0.29, 2013-05-15
----------------
A bugfix release. A bugfix release.
@@ -675,8 +683,7 @@ Bug fixes:
* VIM-121 Don't move cursor while scrolling * VIM-121 Don't move cursor while scrolling
0.28, 2013-04-06 ## 0.28, 2013-04-06
----------------
A bugfix release. A bugfix release.
@@ -686,8 +693,7 @@ Bug fixes:
* VIM-479 Don't try to activate insert mode for diff view * VIM-479 Don't try to activate insert mode for diff view
0.27, 2013-04-03 ## 0.27, 2013-04-03
----------------
New Vim keymap generator creates better keymaps, especially for Mac OS X. New Vim keymap generator creates better keymaps, especially for Mac OS X.
Restart after reconfiguring the keymap is no longer required. Restart after reconfiguring the keymap is no longer required.
@@ -708,8 +714,7 @@ Bug fixes:
* Fixed command window font size to match editor font size * Fixed command window font size to match editor font size
0.26, 2012-12-26 ## 0.26, 2012-12-26
----------------
Added support for paste in the command mode: from a register using `<C-R>`, Added support for paste in the command mode: from a register using `<C-R>`,
from the clipboard using `<S-Insert>` or `<M-V>`. Added support for the last from the clipboard using `<S-Insert>` or `<M-V>`. Added support for the last
@@ -728,8 +733,7 @@ Bug fixes:
* VIM-302 Fixed tab switching order for `gt` and `gT` * VIM-302 Fixed tab switching order for `gt` and `gT`
0.25, 2012-12-19 ## 0.25, 2012-12-19
----------------
A bugfix release. A bugfix release.
@@ -738,8 +742,7 @@ A bugfix release.
character character
0.24, 2012-12-03 ## 0.24, 2012-12-03
----------------
Added Vim string object selection motions (see help topics `v_i"`, `v_a"`). Added Vim string object selection motions (see help topics `v_i"`, `v_a"`).
Various bug fixes. Various bug fixes.
@@ -778,8 +781,7 @@ Bug fixes:
* VIM-157 Fixed regression in moving the cursor after `~` * VIM-157 Fixed regression in moving the cursor after `~`
0.23.115, 2012-11-14 ## 0.23.115, 2012-11-14
--------------------
A bugfix release. A bugfix release.
@@ -788,8 +790,7 @@ A bugfix release.
* VIM-112 Delete a single previous word with <C-W> in insert mode, not all inserted words * VIM-112 Delete a single previous word with <C-W> in insert mode, not all inserted words
0.23.111, 2012-11-12 ## 0.23.111, 2012-11-12
--------------------
A bugfix release. A bugfix release.
@@ -808,8 +809,7 @@ A bugfix release.
found found
0.23.93, 2012-03-21 ## 0.23.93, 2012-03-21
-------------------
A bugfix release. Vim.xml was fixed to use Command+C, Command+V on Mac OS. A bugfix release. Vim.xml was fixed to use Command+C, Command+V on Mac OS.
Unfortunately you need to update Vim.xml manually this time. Unfortunately you need to update Vim.xml manually this time.

View File

@@ -26,7 +26,12 @@ OK, ready to do some coding?
* Fork the repository and clone it to the local machine. * Fork the repository and clone it to the local machine.
* Open the project with IntelliJ IDEA. * Open the project with IntelliJ IDEA.
Yoo hoo! Youre all set to begin contributing. Here are some useful gradle commands: Yoo hoo! Youre all set to begin contributing.
We've prepared some useful configurations for you:
![Prepared configurations](resources/contributing/configurations.png)
And here are useful gradle commands:
* `./gradlew runIde` — start the dev version of IntelliJ IDEA with IdeaVim installed. * `./gradlew runIde` — start the dev version of IntelliJ IDEA with IdeaVim installed.
* `./gradlew test` — run tests. * `./gradlew test` — run tests.
@@ -136,5 +141,5 @@ This is just terrible. [You know what to do](https://github.com/JetBrains/ideavi
* [Changelog](CHANGES.md) * [Changelog](CHANGES.md)
* [Contributors listing](AUTHORS.md) * [Contributors listing](AUTHORS.md)
[teamcity-build-status]: https://teamcity.jetbrains.com/viewType.html?buildTypeId=IdeaVim_TestsForIntelliJ20201&guest=1 [teamcity-build-status]: https://teamcity.jetbrains.com/viewType.html?buildTypeId=IdeaVim_TestsForIntelliJEAP&guest=1
[teamcity-build-status-svg]: https://teamcity.jetbrains.com/app/rest/builds/buildType:(id:IdeaVim_TestsForIntelliJ20201)/statusIcon.svg?guest=1 [teamcity-build-status-svg]: https://teamcity.jetbrains.com/app/rest/builds/buildType:(id:IdeaVim_TestsForIntelliJEAP)/statusIcon.svg?guest=1

View File

@@ -11,7 +11,7 @@ IdeaVim
[![Gitter][gitter-svg]][gitter] [![Gitter][gitter-svg]][gitter]
[![Twitter][twitter-svg]][twitter] [![Twitter][twitter-svg]][twitter]
IdeaVim is a Vim emulation plugin for IDEs based on the IntelliJ Platform. IdeaVim is a Vim emulation plugin for IntelliJ Platform-based IDEs.
##### Contact maintainers: ##### Contact maintainers:
* [Bug tracker](https://youtrack.jetbrains.com/issues/VIM) * [Bug tracker](https://youtrack.jetbrains.com/issues/VIM)
@@ -188,25 +188,38 @@ Changes to the IDE
### Executing IDE Actions ### Executing IDE Actions
IdeaVim adds two commands for listing and executing arbitrary IDE actions as IdeaVim adds various commands for listing and executing arbitrary IDE actions as
Ex commands or via `:map` command mappings: Ex commands or via `:map` command mappings:
**Executing actions:**
* `:action {action_id}`
* Execute an action by id. Works from Ex command line.
* `<Action>(*action_id*)`
* For the mappings you can use a special `<Action>` keyword. Don't forget the parentheses.
**Finding actions:**
* `:actionlist [pattern]` * `:actionlist [pattern]`
* Find IDE actions by name or keymap pattern (E.g. `:actionlist extract`, `:actionlist <C-D`) * Find IDE actions by id or keymap pattern (E.g. `:actionlist extract`, `:actionlist <C-D`)
* `:action {name}`
* Execute an action named `NAME` * In addition to `:actionlist` command, IdeaVim provides `IdeaVim: track action Ids` option to
extract the ids of executed command. This option can be found in "Search everywhere" (double `shift`).
<details>
<summary><strong>"Track aciton Ids" Details</strong> (click to see)</summary>
<img src="resources/readme/track_action_id.gif" alt="track action ids"/>
</details>
Examples: Examples:
```vim ```vim
" Map \r to the Reformat Code action " Map \r to the Reformat Code action
:map \r :action ReformatCode<CR> :map \r <Action>(ReformatCode)
" Map <leader>d to start debug " Map <leader>d to start debug
:map <leader>d :action Debug<CR> :map <leader>d <Action>(Debug)
" Map \b to toggle the breakpoint on the current line " Map \b to toggle the breakpoint on the current line
:map \b :action ToggleLineBreakpoint<CR> :map \b <Action>(ToggleLineBreakpoint)
``` ```
### Undo/Redo ### Undo/Redo

View File

@@ -1,15 +1,21 @@
import dev.feedforward.markdownto.DownParser
buildscript { buildscript {
repositories { repositories {
mavenCentral() mavenCentral()
maven { url 'https://jitpack.io' }
} }
dependencies { dependencies {
classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:$kotlinVersion" classpath "org.jetbrains.kotlin:kotlin-gradle-plugin:$kotlinVersion"
classpath "com.github.AlexPl292:mark-down-to-slack:1.1.2"
} }
} }
plugins { plugins {
id 'org.jetbrains.intellij' version '0.4.18' id 'org.jetbrains.intellij' version '0.6.2'
id 'io.gitlab.arturbosch.detekt' version '1.14.1'
id "org.jetbrains.changelog" version "0.6.2"
} }
apply plugin: 'java' apply plugin: 'java'
@@ -46,8 +52,15 @@ intellij {
} }
} }
runPluginVerifier {
ideVersions = ["IC-2020.1.4", "IC-2020.2.3"]
downloadDirectory = "${project.buildDir}/pluginVerifier/ides"
teamCityOutputFormat = true
}
repositories { repositories {
mavenCentral() mavenCentral()
jcenter()
} }
dependencies { dependencies {
@@ -69,20 +82,44 @@ compileTestKotlin {
} }
} }
task testWithNeovim(type : Test) { detekt {
config = files("${rootProject.projectDir}/.detekt/config.yaml")
baseline = file("${rootProject.projectDir}/.detekt/baseline.xml")
input = files("src")
buildUponDefaultConfig = true
reports {
html.enabled = false
xml.enabled = false
txt.enabled = false
}
}
tasks.detekt.jvmTarget = javaVersion
task testWithNeovim(type: Test) {
group = "verification" group = "verification"
systemProperty "ideavim.neovim.test", 'true' systemProperty "ideavim.nvim.test", 'true'
}
changelog {
groups = ["Features:", "Changes:", "Deprecations:", "Fixes:", "Merged PRs:"]
itemPrefix = "*"
path = "${project.projectDir}/CHANGES.md"
unreleasedTerm = "To Be Released"
headerParserRegex = /0\.\d{2}(.\d+)?/
// header = { "${project.version}" }
// version = "0.60"
} }
tasks.register("slackEapNotification") { tasks.register("slackEapNotification") {
doLast { doLast {
if (!slackUrl) return if (!slackUrl) return
def post = new URL(slackUrl).openConnection() def post = new URL(slackUrl).openConnection()
def changeLog = extractChangelog() def changeLog = changelog.getUnreleased().toText()
changeLog = changeLog.replace("* ", "• ") // Replace stars with bullets def slackDown = new DownParser(changeLog, true).toSlack().toString()
changeLog = changeLog.replace("**", "*") // Enable bold text def message = """
changeLog = changeLog.replaceAll("\\[([^]]+)]\\(([^)]+)\\)", '<$2|$1>') // Enable links
def message ="""
{ {
"text": "New version of IdeaVim", "text": "New version of IdeaVim",
"blocks": [ "blocks": [
@@ -90,7 +127,7 @@ tasks.register("slackEapNotification") {
"type": "section", "type": "section",
"text": { "text": {
"type": "mrkdwn", "type": "mrkdwn",
"text": "IdeaVim EAP $version has been released\\n$changeLog" "text": "IdeaVim EAP $version has been released\\n$slackDown"
} }
} }
] ]
@@ -102,32 +139,8 @@ tasks.register("slackEapNotification") {
post.getOutputStream().write(message.getBytes("UTF-8")) post.getOutputStream().write(message.getBytes("UTF-8"))
def postRC = post.getResponseCode() def postRC = post.getResponseCode()
println(postRC) println(postRC)
if(postRC == 200) { if (postRC == 200) {
println(post.getInputStream().getText()) println(post.getInputStream().getText())
} }
} }
} }
// Very primitive changelog extraction code
def extractChangelog() {
def startLine = "_Available since $version EAP:_"
def endLine = "_To Be Released..._"
def startSaving = false
def res = new StringBuilder()
new File("./CHANGES.md").eachLine { line ->
if (startSaving) {
if (line == endLine) {
startSaving = false
}
else {
res.append(line).append('\n')
}
}
else {
if (line == startLine) {
startSaving = true
}
}
}
return res.toString()
}

View File

@@ -4,7 +4,15 @@ Emulated Vim Plugins
IdeaVim extensions emulate plugins of the original Vim. In order to use IdeaVim extensions emulate plugins of the original Vim. In order to use
IdeaVim extensions, you have to enable them via this command in your `~/.ideavimrc`: IdeaVim extensions, you have to enable them via this command in your `~/.ideavimrc`:
set <extension-name> ```
set <extension-name>
```
If you reuse your existing `.vimrc` file using `source ~/.vimrc`, IdeaVim can parse and enable plugins that are defined
using [vim-plug](https://github.com/junegunn/vim-plug) or [vundle](https://github.com/VundleVim/Vundle.vim).
No additional set commands in `~/.ideavimrc` are required.
If you'd like to disable some plugin that's enabled in `.vimrc`, you can use `set no<extension-name>`
in `~/.ideavimrc`.
Available extensions: Available extensions:
@@ -20,18 +28,52 @@ Available extensions:
## surround ## surround
* Setup: `set surround` * Setup: `set surround`
* <details>
<summary>Alternative vim-plug / vundle syntax</summary>
<code>Plug 'https://github.com/tpope/vim-surround'</code>
<br/>
<code>Plug 'tpope/vim-surround'</code>
<br/>
<code>Plug 'vim-surround'</code>
<br/>
<code>Plug 'https://www.vim.org/scripts/script.php?script_id=1697'</code>
</details>
* Emulates [vim-surround](https://github.com/tpope/vim-surround) * Emulates [vim-surround](https://github.com/tpope/vim-surround)
* Commands: `ys`, `cs`, `ds`, `S` * Commands: `ys`, `cs`, `ds`, `S`
## multiple-cursors ## multiple-cursors
* Setup: `set multiple-cursors` * Setup: `set multiple-cursors`
* <details>
<summary>Alternative vim-plug / vundle syntax</summary>
<code>Plug 'https://github.com/terryma/vim-multiple-cursors'</code>
<br/>
<code>Plug 'terryma/vim-multiple-cursors'</code>
<br/>
<code>Plug 'vim-multiple-cursors'</code>
</details>
* Emulates [vim-multiple-cursors](https://github.com/terryma/vim-multiple-cursors) * Emulates [vim-multiple-cursors](https://github.com/terryma/vim-multiple-cursors)
* Commands: `<A-n>`, `<A-x>`, `<A-p>`, `g<A-n>` * Commands: `<A-n>`, `<A-x>`, `<A-p>`, `g<A-n>`
## commentary ## commentary
* Setup: `set commentary` * Setup: `set commentary`
* <details>
<summary>Alternative vim-plug / vundle syntax</summary>
<code>Plug 'https://github.com/tpope/vim-commentary'</code>
<br/>
<code>Plug 'tpope/vim-commentary'</code>
<br/>
<code>Plug 'vim-commentary'</code>
<br/>
<code>Plug 'https://www.vim.org/scripts/script.php?script_id=3695'</code>
<br/>
<code>Plug 'tomtom/tcomment_vim'</code>
<br/>
<code>Plug 'tcomment_vim'</code>
<br/>
<code>Plug 'https://www.vim.org/scripts/script.php?script_id=1173'</code>
</details>
* Emulates [commentary.vim](https://github.com/tpope/vim-commentary) * Emulates [commentary.vim](https://github.com/tpope/vim-commentary)
* Commands: `gcc`, `gc + motion`, `v_gc` * Commands: `gcc`, `gc + motion`, `v_gc`
* By [Daniel Leong](https://github.com/dhleong) * By [Daniel Leong](https://github.com/dhleong)
@@ -39,6 +81,22 @@ Available extensions:
## ReplaceWithRegister ## ReplaceWithRegister
* Setup: `set ReplaceWithRegister` * Setup: `set ReplaceWithRegister`
* <details>
<summary>Alternative vim-plug / vundle syntax</summary>
<code>Plug 'https://github.com/vim-scripts/ReplaceWithRegister'</code>
<br/>
<code>Plug 'vim-scripts/ReplaceWithRegister'</code>
<br/>
<code>Plug 'ReplaceWithRegister'</code>
<br/>
<code>Plug 'https://github.com/inkarkat/vim-ReplaceWithRegister'</code>
<br/>
<code>Plug 'inkarkat/vim-ReplaceWithRegister'</code>
<br/>
<code>Plug 'vim-ReplaceWithRegister'</code>
<br/>
<code>Plug 'https://www.vim.org/scripts/script.php?script_id=2703'</code>
</details>
* Emulates [ReplaceWithRegister](https://github.com/vim-scripts/ReplaceWithRegister) * Emulates [ReplaceWithRegister](https://github.com/vim-scripts/ReplaceWithRegister)
* Commands: `gr`, `grr` * Commands: `gr`, `grr`
* By [igrekster](https://github.com/igrekster) * By [igrekster](https://github.com/igrekster)
@@ -47,6 +105,16 @@ Available extensions:
* Setup: * Setup:
* `set argtextobj` * `set argtextobj`
* <details>
<summary>Alternative vim-plug / vundle syntax</summary>
<code>Plug 'https://github.com/vim-scripts/argtextobj.vim'</code>
<br/>
<code>Plug 'vim-scripts/argtextobj.vim'</code>
<br/>
<code>Plug 'argtextobj.vim'</code>
<br/>
<code>Plug 'https://www.vim.org/scripts/script.php?script_id=2699'</code>
</details>
* By default, only the arguments inside parenthesis are considered. To extend the functionality * By default, only the arguments inside parenthesis are considered. To extend the functionality
to other types of brackets, set `g:argtextobj_pairs` variable to a comma-separated to other types of brackets, set `g:argtextobj_pairs` variable to a comma-separated
list of colon-separated pairs (same as VIM's `matchpairs` option), like list of colon-separated pairs (same as VIM's `matchpairs` option), like
@@ -59,6 +127,14 @@ Available extensions:
## exchange ## exchange
* Setup: `set exchange` * Setup: `set exchange`
* <details>
<summary>Alternative vim-plug / vundle syntax</summary>
<code>Plug 'https://github.com/tommcdo/vim-exchange'</code>
<br/>
<code>Plug 'tommcdo/vim-exchange'</code>
<br/>
<code>Plug 'vim-exchange'</code>
</details>
* Emulates [vim-exchange](https://github.com/tommcdo/vim-exchange) * Emulates [vim-exchange](https://github.com/tommcdo/vim-exchange)
* Commands: `cx`, `cxx`, `X`, `cxc` * Commands: `cx`, `cxx`, `X`, `cxc`
* By [fan-tom](https://github.com/fan-tom) * By [fan-tom](https://github.com/fan-tom)
@@ -66,6 +142,16 @@ Available extensions:
## textobj-entire ## textobj-entire
* Setup: `set textobj-entire` * Setup: `set textobj-entire`
* <details>
<summary>Alternative vim-plug / vundle syntax</summary>
<code>Plug 'https://github.com/kana/vim-textobj-entire'</code>
<br/>
<code>Plug 'kana/vim-textobj-entire'</code>
<br/>
<code>Plug 'vim-textobj-entire'</code>
<br/>
<code>Plug 'https://www.vim.org/scripts/script.php?script_id=2610'</code>
</details>
* Emulates [vim-textobj-entire](https://github.com/kana/vim-textobj-entire) * Emulates [vim-textobj-entire](https://github.com/kana/vim-textobj-entire)
* Additional text objects: `ae`, `ie` * Additional text objects: `ae`, `ie`
* By [Alexandre Grison](https://github.com/agrison) * By [Alexandre Grison](https://github.com/agrison)
@@ -74,6 +160,14 @@ Available extensions:
* Setup: * Setup:
* `set highlightedyank` * `set highlightedyank`
* <details>
<summary>Alternative vim-plug / vundle syntax</summary>
<code>Plug 'https://github.com/machakann/vim-highlightedyank'</code>
<br/>
<code>Plug 'machakann/vim-highlightedyank'</code>
<br/>
<code>Plug 'vim-highlightedyank'</code>
</details>
* if you want to optimize highlight duration, assign a time in milliseconds: * if you want to optimize highlight duration, assign a time in milliseconds:
`let g:highlightedyank_highlight_duration = "1000"` `let g:highlightedyank_highlight_duration = "1000"`
A negative number makes the highlight persistent. A negative number makes the highlight persistent.

View File

@@ -59,12 +59,6 @@ The following `:set` commands can appear in `~/.ideavimrc` or be set manually in
ideaselection when IDE sets a selection - IdeaVim ONLY ideaselection when IDE sets a selection - IdeaVim ONLY
(examples: extend selection, wrap with while, etc.) (examples: extend selection, wrap with while, etc.)
Deprecated values:
template ~~please use `idearefactormode` option~~
when starting a template - IdeaVim ONLY
refactoring ~~please use ideaselection~~
same as ideaselection - IdeaVim ONLY
'showmode' 'smd' message on the status line to show current mode 'showmode' 'smd' message on the status line to show current mode
'showcmd' 'sc' show (partial) command in the status bar 'showcmd' 'sc' show (partial) command in the status bar
'sidescroll' 'ss' minimum number of columns to scroll horizontally 'sidescroll' 'ss' minimum number of columns to scroll horizontally
@@ -105,12 +99,6 @@ The following `:set` commands can appear in `~/.ideavimrc` or be set manually in
If true, join command will be performed via IDE If true, join command will be performed via IDE
See wiki/`ideajoin` examples See wiki/`ideajoin` examples
`ideastatusbar` `ideastatusbar` Boolean (default true)
DEPRECATED. Please use `ideastatusicon`
If false, IdeaVim icon won't be shown in the status bar.
Works only from `~/.ideavimrc` after the IDE restart.
`ideastatusicon` `ideastatusicon` String(default "enabled") `ideastatusicon` `ideastatusicon` String(default "enabled")
Define the behavior of IdeaVim icon in the status bar. Define the behavior of IdeaVim icon in the status bar.
@@ -120,7 +108,7 @@ The following `:set` commands can appear in `~/.ideavimrc` or be set manually in
- gray - use the gray version of the icon - gray - use the gray version of the icon
- disabled - hide the icon - disabled - hide the icon
`ideawrite` `ideawrite` String (default "all") [To Be Released] `ideawrite` `ideawrite` String (default "all")
"file" or "all". Defines the behaviour of ":w" command. "file" or "all". Defines the behaviour of ":w" command.
Value "all" enables execution of ":wa" (save all) command on ":w" (save). Value "all" enables execution of ":wa" (save all) command on ":w" (save).
This feature exists because some IJ options like "Prettier on save" or "ESlint on save" This feature exists because some IJ options like "Prettier on save" or "ESlint on save"
@@ -137,5 +125,12 @@ The following `:set` commands can appear in `~/.ideavimrc` or be set manually in
"<C-Down>", "<C-Up>", "<PageUp>", "<PageDown>", "<C-Down>", "<C-Up>", "<PageUp>", "<PageDown>",
"<C-J>", "<C-Q>" "<C-J>", "<C-Q>"
`ideavimsupport` `ideavimsupport` List of strings (default "dialog")
Define the list of additional buffers where IdeaVim is enabled.
- dialog - enable IdeaVim in dialogs
- singleline - enable IdeaVim in single line editors (not suggested)
---------- ----------
[1] - cursor keys, <End>, <Home>, <PageUp> and <PageDown> [1] - cursor keys, <End>, <Home>, <PageUp> and <PageDown>

View File

@@ -4,7 +4,7 @@ ideaVersion=LATEST-EAP-SNAPSHOT
downloadIdeaSources=true downloadIdeaSources=true
instrumentPluginCode=true instrumentPluginCode=true
version=SNAPSHOT version=SNAPSHOT
javaVersion=11 javaVersion=1.8
kotlinVersion=1.3.71 kotlinVersion=1.3.71
publishUsername=username publishUsername=username
publishToken=token publishToken=token

Binary file not shown.

View File

@@ -1,6 +1,5 @@
#Thu Jun 25 19:36:41 MSK 2020
distributionUrl=https\://services.gradle.org/distributions/gradle-6.5-all.zip
distributionBase=GRADLE_USER_HOME distributionBase=GRADLE_USER_HOME
distributionPath=wrapper/dists distributionPath=wrapper/dists
zipStorePath=wrapper/dists distributionUrl=https\://services.gradle.org/distributions/gradle-6.6.1-bin.zip
zipStoreBase=GRADLE_USER_HOME zipStoreBase=GRADLE_USER_HOME
zipStorePath=wrapper/dists

2
gradlew vendored
View File

@@ -82,6 +82,7 @@ esac
CLASSPATH=$APP_HOME/gradle/wrapper/gradle-wrapper.jar CLASSPATH=$APP_HOME/gradle/wrapper/gradle-wrapper.jar
# Determine the Java command to use to start the JVM. # Determine the Java command to use to start the JVM.
if [ -n "$JAVA_HOME" ] ; then if [ -n "$JAVA_HOME" ] ; then
if [ -x "$JAVA_HOME/jre/sh/java" ] ; then if [ -x "$JAVA_HOME/jre/sh/java" ] ; then
@@ -129,6 +130,7 @@ fi
if [ "$cygwin" = "true" -o "$msys" = "true" ] ; then if [ "$cygwin" = "true" -o "$msys" = "true" ] ; then
APP_HOME=`cygpath --path --mixed "$APP_HOME"` APP_HOME=`cygpath --path --mixed "$APP_HOME"`
CLASSPATH=`cygpath --path --mixed "$CLASSPATH"` CLASSPATH=`cygpath --path --mixed "$CLASSPATH"`
JAVACMD=`cygpath --unix "$JAVACMD"` JAVACMD=`cygpath --unix "$JAVACMD"`
# We build the pattern for arguments to be converted via cygpath # We build the pattern for arguments to be converted via cygpath

1
gradlew.bat vendored
View File

@@ -84,6 +84,7 @@ set CMD_LINE_ARGS=%*
set CLASSPATH=%APP_HOME%\gradle\wrapper\gradle-wrapper.jar set CLASSPATH=%APP_HOME%\gradle\wrapper\gradle-wrapper.jar
@rem Execute Gradle @rem Execute Gradle
"%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -classpath "%CLASSPATH%" org.gradle.wrapper.GradleWrapperMain %CMD_LINE_ARGS% "%JAVA_EXE%" %DEFAULT_JVM_OPTS% %JAVA_OPTS% %GRADLE_OPTS% "-Dorg.gradle.appname=%APP_BASE_NAME%" -classpath "%CLASSPATH%" org.gradle.wrapper.GradleWrapperMain %CMD_LINE_ARGS%

View File

@@ -64,5 +64,6 @@
<vimExCommand implementation="com.maddyhome.idea.vim.ex.handler.TabCloseHandler" names="tabc[lose]"/> <vimExCommand implementation="com.maddyhome.idea.vim.ex.handler.TabCloseHandler" names="tabc[lose]"/>
<vimExCommand implementation="com.maddyhome.idea.vim.ex.handler.BufferListHandler" names="buffers,ls,files"/> <vimExCommand implementation="com.maddyhome.idea.vim.ex.handler.BufferListHandler" names="buffers,ls,files"/>
<vimExCommand implementation="com.maddyhome.idea.vim.ex.handler.BufferHandler" names="b[uffer]"/> <vimExCommand implementation="com.maddyhome.idea.vim.ex.handler.BufferHandler" names="b[uffer]"/>
<vimExCommand implementation="com.maddyhome.idea.vim.ex.handler.PlugHandler" names="Plug[in]"/>
</extensions> </extensions>
</idea-plugin> </idea-plugin>

View File

@@ -1,12 +1,84 @@
<idea-plugin> <idea-plugin>
<extensions defaultExtensionNs="IdeaVIM"> <extensions defaultExtensionNs="IdeaVIM">
<vimExtension implementation="com.maddyhome.idea.vim.extension.surround.VimSurroundExtension"/> <vimExtension implementation="com.maddyhome.idea.vim.extension.surround.VimSurroundExtension" name="surround">
<vimExtension implementation="com.maddyhome.idea.vim.extension.multiplecursors.VimMultipleCursorsExtension"/> <aliases>
<vimExtension implementation="com.maddyhome.idea.vim.extension.commentary.CommentaryExtension"/> <alias name="https://github.com/tpope/vim-surround"/>
<vimExtension implementation="com.maddyhome.idea.vim.extension.textobjentire.VimTextObjEntireExtension"/> <alias name="tpope/vim-surround"/>
<vimExtension implementation="com.maddyhome.idea.vim.extension.argtextobj.VimArgTextObjExtension"/> <alias name="vim-surround"/>
<vimExtension implementation="com.maddyhome.idea.vim.extension.replacewithregister.ReplaceWithRegister"/> <alias name="https://www.vim.org/scripts/script.php?script_id=1697"/>
<vimExtension implementation="com.maddyhome.idea.vim.extension.exchange.VimExchangeExtension"/> </aliases>
<vimExtension implementation="com.maddyhome.idea.vim.extension.highlightedyank.VimHighlightedYank"/> </vimExtension>
<vimExtension implementation="com.maddyhome.idea.vim.extension.multiplecursors.VimMultipleCursorsExtension"
name="multiple-cursors">
<aliases>
<alias name="https://github.com/terryma/vim-multiple-cursors"/>
<alias name="terryma/vim-multiple-cursors"/>
<alias name="vim-multiple-cursors"/>
</aliases>
</vimExtension>
<vimExtension implementation="com.maddyhome.idea.vim.extension.commentary.CommentaryExtension" name="commentary">
<aliases>
<alias name="https://github.com/tpope/vim-commentary"/>
<alias name="tpope/vim-commentary"/>
<alias name="vim-commentary"/>
<alias name="https://www.vim.org/scripts/script.php?script_id=3695"/>
<alias name="https://github.com/tomtom/tcomment_vim"/>
<alias name="tomtom/tcomment_vim"/>
<alias name="tcomment_vim"/>
<alias name="https://www.vim.org/scripts/script.php?script_id=1173"/>
</aliases>
</vimExtension>
<vimExtension implementation="com.maddyhome.idea.vim.extension.textobjentire.VimTextObjEntireExtension"
name="textobj-entire">
<aliases>
<alias name="https://github.com/kana/vim-textobj-entire"/>
<alias name="kana/vim-textobj-entire"/>
<alias name="vim-textobj-entire"/>
<alias name="https://www.vim.org/scripts/script.php?script_id=2610"/>
</aliases>
</vimExtension>
<vimExtension implementation="com.maddyhome.idea.vim.extension.argtextobj.VimArgTextObjExtension"
name="argtextobj">
<aliases>
<alias name="https://github.com/vim-scripts/argtextobj.vim"/>
<alias name="vim-scripts/argtextobj.vim"/>
<alias name="argtextobj.vim"/>
<alias name="https://www.vim.org/scripts/script.php?script_id=2699"/>
</aliases>
</vimExtension>
<vimExtension implementation="com.maddyhome.idea.vim.extension.replacewithregister.ReplaceWithRegister"
name="ReplaceWithRegister">
<aliases>
<alias name="https://github.com/vim-scripts/ReplaceWithRegister"/>
<alias name="vim-scripts/ReplaceWithRegister"/>
<alias name="ReplaceWithRegister"/>
<alias name="https://github.com/inkarkat/vim-ReplaceWithRegister"/>
<alias name="inkarkat/vim-ReplaceWithRegister"/>
<alias name="vim-ReplaceWithRegister"/>
<alias name="https://www.vim.org/scripts/script.php?script_id=2703"/>
</aliases>
</vimExtension>
<vimExtension implementation="com.maddyhome.idea.vim.extension.exchange.VimExchangeExtension" name="exchange">
<aliases>
<alias name="https://github.com/tommcdo/vim-exchange"/>
<alias name="tommcdo/vim-exchange"/>
<alias name="vim-exchange"/>
</aliases>
</vimExtension>
<vimExtension implementation="com.maddyhome.idea.vim.extension.highlightedyank.VimHighlightedYank"
name="highlightedyank">
<aliases>
<alias name="https://github.com/machakann/vim-highlightedyank"/>
<alias name="machakann/vim-highlightedyank"/>
<alias name="vim-highlightedyank"/>
</aliases>
</vimExtension>
</extensions> </extensions>
</idea-plugin> </idea-plugin>

View File

@@ -2,6 +2,8 @@
<applicationListeners> <applicationListeners>
<listener class="com.maddyhome.idea.vim.ui.ExEntryPanel$LafListener" <listener class="com.maddyhome.idea.vim.ui.ExEntryPanel$LafListener"
topic="com.intellij.ide.ui.LafManagerListener"/> topic="com.intellij.ide.ui.LafManagerListener"/>
<listener class="com.maddyhome.idea.vim.extension.highlightedyank.HighlightColorResetter"
topic="com.intellij.ide.ui.LafManagerListener"/>
</applicationListeners> </applicationListeners>
<projectListeners> <projectListeners>
<listener class="com.maddyhome.idea.vim.ui.ExOutputPanel$LafListener" <listener class="com.maddyhome.idea.vim.ui.ExOutputPanel$LafListener"

View File

@@ -1,16 +1,54 @@
<idea-plugin url="https://plugins.jetbrains.com/plugin/164" xmlns:xi="http://www.w3.org/2001/XInclude"> <idea-plugin url="https://plugins.jetbrains.com/plugin/164" xmlns:xi="http://www.w3.org/2001/XInclude">
<name>IdeaVim</name> <name>IdeaVim</name>
<id>IdeaVIM</id> <id>IdeaVIM</id>
<change-notes><![CDATA[ <change-notes>
<ul> &lt;h3&gt;Features:&lt;/h3&gt;
<li>Support of `virtualedit=onemore`</li> &lt;br/&gt;
<li>A lot of fixes for scrolling</li> &lt;ul&gt;&lt;li&gt;Ability to map IDE actions via the &lt;code&gt;&amp;lt;Action&amp;gt;&lt;/code&gt; keyword. E.g.
</ul> &lt;code&gt;map &amp;lt;C-K&amp;gt; &amp;lt;Action&amp;gt;(CommentByLineComment)&lt;/code&gt;.
<p>See also the complete <a href="https://github.com/JetBrains/ideavim/blob/master/CHANGES.md">changelog</a>.</p> Check out &lt;code&gt;README.md&lt;/code&gt; for the details.&lt;/li&gt;&lt;li&gt;&lt;code&gt;IdeaVim: track action
]]></change-notes> Ids&lt;/code&gt; command to find action ids for the &lt;code&gt;:action&lt;/code&gt; command.
Enable this option in &amp;quot;Search everywhere&amp;quot; (double shift).&lt;/li&gt;&lt;li&gt;Ability to enable
extensions using &lt;code&gt;vim-plug&lt;/code&gt; or &lt;code&gt;vundle&lt;/code&gt; syntax.&lt;br /&gt;
E.g. to enable commentary extension you can use one of the following commands:&lt;pre&gt;&lt;code
class="language-vim"&gt;set commentary
Plug 'tpope/vim-commentary'
Plug 'https://github.com/tpope/vim-commentary'
Plugin 'tpope/vim-commentary'
...
&lt;/code&gt;&lt;/pre&gt;&lt;p&gt;This approach is especially handy if you have &lt;code&gt;.vimrc&lt;/code&gt; with
plugins registered via &lt;code&gt;vim-plug&lt;/code&gt; or &lt;code&gt;vundle&lt;/code&gt;.&lt;/p&gt;&lt;/li&gt;&lt;/ul&gt;
&lt;br/&gt;
&lt;h3&gt;Changes:&lt;/h3&gt;
&lt;br/&gt;
&lt;ul&gt;&lt;li&gt;Fix &lt;code&gt;&amp;lt;Esc&amp;gt;&lt;/code&gt; for dialogs. Now &lt;code&gt;&amp;lt;Esc&amp;gt;&lt;/code&gt;
will exit insert / visual mode and close the dialog from normal mode.&lt;/li&gt;&lt;li&gt;Add option to disable
IdeaVim in dialogs / single line editors. &lt;a href="https://youtrack.jetbrains.com/issue/VIM-765"&gt;VIM-765&lt;/a&gt;&lt;br
/&gt;
Use &lt;code&gt;set ideavimsupport=&lt;/code&gt; to disable IdeaVim in dialog editors. &lt;/li&gt;&lt;li&gt;Reposition
cursor when &lt;code&gt;scrolloff&lt;/code&gt; changes&lt;/li&gt;&lt;/ul&gt;
&lt;br/&gt;
&lt;h3&gt;Fixes:&lt;/h3&gt;
&lt;br/&gt;
&lt;ul&gt;&lt;li&gt;&lt;a href="https://youtrack.jetbrains.com/issue/VIM-2150"&gt;VIM-2150&lt;/a&gt; &lt;code&gt;Shift-D&lt;/code&gt;
should not delete an empty line&lt;/li&gt;&lt;li&gt;&lt;a href="https://youtrack.jetbrains.com/issue/VIM-2157"&gt;VIM-2157&lt;/a&gt;
Fix tab with an active template&lt;/li&gt;&lt;li&gt;&lt;a href="https://youtrack.jetbrains.com/issue/VIM-2156"&gt;VIM-2156&lt;/a&gt;
Correct up/down motions with inlays&lt;/li&gt;&lt;li&gt;&lt;a href="https://youtrack.jetbrains.com/issue/VIM-2144"&gt;VIM-2144&lt;/a&gt;
Correct text position after block insert with inlays&lt;/li&gt;&lt;li&gt;&lt;a
href="https://youtrack.jetbrains.com/issue/VIM-2158"&gt;VIM-2158&lt;/a&gt; Fix scrolling when &lt;code&gt;scrolloff&lt;/code&gt;
is over half screen height, but less than full height&lt;/li&gt;&lt;/ul&gt;
&lt;br/&gt;
&lt;p&gt;See also the complete &lt;a href="https://github.com/JetBrains/ideavim/blob/master/CHANGES.md"&gt;changelog&lt;/a&gt;.&lt;/p&gt;
</change-notes>
<description><![CDATA[ <description><![CDATA[
<p>Vim emulation plug-in for IDEs based on the IntelliJ platform.</p> <p>Vim emulation plugin for IntelliJ Platform-based IDEs.</p>
<p>IdeaVim supports many Vim features including normal/insert/visual modes, motion keys, deletion/changing, marks, registers, some Ex commands, Vim regexps, configuration via ~/.ideavimrc, macros, window commands, etc.</p> <br/>
<p>IdeaVim supports many Vim features including normal/insert/visual modes, motion keys, deletion/changing,
marks, registers, some Ex commands, Vim regexps, configuration via ~/.ideavimrc, macros, Vim plugins, etc.</p>
<br/>
<p>See also:</p> <p>See also:</p>
<ul> <ul>
<li><a href="https://github.com/JetBrains/ideavim">GitHub repository</a>: documentation and contributing</li> <li><a href="https://github.com/JetBrains/ideavim">GitHub repository</a>: documentation and contributing</li>
@@ -35,7 +73,10 @@
</application-components> </application-components>
<extensionPoints> <extensionPoints>
<extensionPoint name="vimExtension" interface="com.maddyhome.idea.vim.extension.VimExtension" dynamic="true"/> <extensionPoint name="vimExtension" beanClass="com.maddyhome.idea.vim.extension.ExtensionBeanClass" dynamic="true">
<with attribute="implementation" implements="com.maddyhome.idea.vim.extension.VimExtension"/>
</extensionPoint>
<!-- For internal use only --> <!-- For internal use only -->
<extensionPoint name="vimExCommand" beanClass="com.maddyhome.idea.vim.ex.ExBeanClass" dynamic="true"> <extensionPoint name="vimExCommand" beanClass="com.maddyhome.idea.vim.ex.ExBeanClass" dynamic="true">

Binary file not shown.

After

Width:  |  Height:  |  Size: 22 KiB

Binary file not shown.

After

Width:  |  Height:  |  Size: 2.1 MiB

View File

@@ -29,6 +29,7 @@ import com.intellij.openapi.command.UndoConfirmationPolicy;
import com.intellij.openapi.editor.Caret; import com.intellij.openapi.editor.Caret;
import com.intellij.openapi.editor.Editor; import com.intellij.openapi.editor.Editor;
import com.intellij.openapi.editor.actionSystem.ActionPlan; import com.intellij.openapi.editor.actionSystem.ActionPlan;
import com.intellij.openapi.editor.actionSystem.CaretSpecificDataContext;
import com.intellij.openapi.editor.actionSystem.DocCommandGroupId; import com.intellij.openapi.editor.actionSystem.DocCommandGroupId;
import com.intellij.openapi.editor.actionSystem.TypedActionHandler; import com.intellij.openapi.editor.actionSystem.TypedActionHandler;
import com.intellij.openapi.project.Project; import com.intellij.openapi.project.Project;
@@ -300,7 +301,7 @@ public class KeyHandler {
return node; return node;
} }
private static <T> boolean isPrefix(@NotNull List<T> list1, @NotNull List<T> list2) { public static <T> boolean isPrefix(@NotNull List<T> list1, @NotNull List<T> list2) {
if (list1.size() > list2.size()) { if (list1.size() > list2.size()) {
return false; return false;
} }
@@ -392,7 +393,7 @@ public class KeyHandler {
} }
for (KeyStroke keyStroke : unhandledKeys) { for (KeyStroke keyStroke : unhandledKeys) {
handleKey(editor, keyStroke, new EditorDataContext(editor), false); handleKey(editor, keyStroke, new EditorDataContext(editor, null), false);
} }
}, ModalityState.stateForComponent(editor.getComponent()))); }, ModalityState.stateForComponent(editor.getComponent())));
} }
@@ -435,80 +436,9 @@ public class KeyHandler {
mappingState.resetMappingSequence(); mappingState.resetMappingSequence();
final EditorDataContext currentContext = new EditorDataContext(editor); final EditorDataContext currentContext = new EditorDataContext(editor, context);
if (mappingInfo instanceof ToKeysMappingInfo) { mappingInfo.execute(editor, context);
final List<KeyStroke> toKeys = ((ToKeysMappingInfo)mappingInfo).getToKeys();
final boolean fromIsPrefix = isPrefix(mappingInfo.getFromKeys(), toKeys);
boolean first = true;
for (KeyStroke keyStroke : toKeys) {
final boolean recursive = mappingInfo.isRecursive() && !(first && fromIsPrefix);
handleKey(editor, keyStroke, currentContext, recursive);
first = false;
}
}
else if (mappingInfo instanceof ToHandlerMappingInfo) {
final VimExtensionHandler extensionHandler = ((ToHandlerMappingInfo)mappingInfo).getExtensionHandler();
final CommandProcessor processor = CommandProcessor.getInstance();
// Cache isOperatorPending in case the extension changes the mode while moving the caret
// See CommonExtensionTest
// TODO: Is this legal? Should we assert in this case?
final boolean shouldCalculateOffsets = commandState.isOperatorPending();
Map<Caret, Integer> startOffsets =
editor.getCaretModel().getAllCarets().stream().collect(Collectors.toMap(Function.identity(), Caret::getOffset));
if (extensionHandler.isRepeatable()) {
VimRepeater.Extension.INSTANCE.clean();
}
processor.executeCommand(editor.getProject(), () -> extensionHandler.execute(editor, context),
"Vim " + extensionHandler.getClass().getSimpleName(), null);
if (extensionHandler.isRepeatable()) {
VimRepeater.Extension.INSTANCE.setLastExtensionHandler(extensionHandler);
VimRepeater.Extension.INSTANCE.setArgumentCaptured(null);
VimRepeater.INSTANCE.setRepeatHandler(true);
}
if (shouldCalculateOffsets && !commandState.getCommandBuilder().hasCurrentCommandPartArgument()) {
Map<Caret, VimSelection> offsets = new HashMap<>();
for (Caret caret : editor.getCaretModel().getAllCarets()) {
@Nullable Integer startOffset = startOffsets.get(caret);
if (caret.hasSelection()) {
final VimSelection vimSelection = VimSelection.Companion
.create(UserDataManager.getVimSelectionStart(caret), caret.getOffset(),
SelectionType.fromSubMode(CommandStateHelper.getSubMode(editor)), editor);
offsets.put(caret, vimSelection);
commandState.popModes();
}
else if (startOffset != null && startOffset != caret.getOffset()) {
// Command line motions are always characterwise exclusive
int endOffset = caret.getOffset();
if (startOffset < endOffset) {
endOffset -= 1;
} else {
startOffset -= 1;
}
final VimSelection vimSelection = VimSelection.Companion
.create(startOffset, endOffset, SelectionType.CHARACTER_WISE, editor);
offsets.put(caret, vimSelection);
try (VimListenerSuppressor.Locked ignored = SelectionVimListenerSuppressor.INSTANCE.lock()) {
// Move caret to the initial offset for better undo action
// This is not a necessary thing, but without it undo action look less convenient
editor.getCaretModel().moveToOffset(startOffset);
}
}
}
if (!offsets.isEmpty()) {
commandState.getCommandBuilder().completeCommandPart(new Argument(offsets));
}
}
}
// If we've just evaluated the previous key sequence, make sure to also handle the current key // If we've just evaluated the previous key sequence, make sure to also handle the current key
if (mappingInfo != currentMappingInfo) { if (mappingInfo != currentMappingInfo) {

View File

@@ -24,10 +24,7 @@ import com.intellij.notification.NotificationListener;
import com.intellij.openapi.Disposable; import com.intellij.openapi.Disposable;
import com.intellij.openapi.application.Application; import com.intellij.openapi.application.Application;
import com.intellij.openapi.application.ApplicationManager; import com.intellij.openapi.application.ApplicationManager;
import com.intellij.openapi.components.PersistentStateComponent; import com.intellij.openapi.components.*;
import com.intellij.openapi.components.ServiceManager;
import com.intellij.openapi.components.State;
import com.intellij.openapi.components.Storage;
import com.intellij.openapi.diagnostic.Logger; import com.intellij.openapi.diagnostic.Logger;
import com.intellij.openapi.extensions.PluginId; import com.intellij.openapi.extensions.PluginId;
import com.intellij.openapi.keymap.Keymap; import com.intellij.openapi.keymap.Keymap;

View File

@@ -25,7 +25,9 @@ import com.intellij.openapi.project.Project
@Service @Service
class VimProjectService(val project: Project) : Disposable { class VimProjectService(val project: Project) : Disposable {
override fun dispose() {} override fun dispose() {
// Nothing
}
companion object { companion object {
@JvmStatic @JvmStatic

View File

@@ -61,7 +61,7 @@ class VimTypedActionHandler(origHandler: TypedActionHandler?) : TypedActionHandl
try { try {
val modifiers = if (charTyped == ' ' && VimKeyListener.isSpaceShift) KeyEvent.SHIFT_DOWN_MASK else 0 val modifiers = if (charTyped == ' ' && VimKeyListener.isSpaceShift) KeyEvent.SHIFT_DOWN_MASK else 0
val keyStroke = KeyStroke.getKeyStroke(charTyped, modifiers) val keyStroke = KeyStroke.getKeyStroke(charTyped, modifiers)
handler.handleKey(editor, keyStroke, EditorDataContext(editor)) handler.handleKey(editor, keyStroke, EditorDataContext(editor, context))
} catch (e: Throwable) { } catch (e: Throwable) {
logger.error(e) logger.error(e)
} }

View File

@@ -20,15 +20,29 @@ package com.maddyhome.idea.vim.action
import com.intellij.openapi.actionSystem.DataContext import com.intellij.openapi.actionSystem.DataContext
import com.intellij.openapi.editor.Editor import com.intellij.openapi.editor.Editor
import com.maddyhome.idea.vim.KeyHandler import com.maddyhome.idea.vim.KeyHandler
import com.maddyhome.idea.vim.VimPlugin
import com.maddyhome.idea.vim.command.Command import com.maddyhome.idea.vim.command.Command
import com.maddyhome.idea.vim.command.CommandState
import com.maddyhome.idea.vim.group.MotionGroup
import com.maddyhome.idea.vim.handler.VimActionHandler import com.maddyhome.idea.vim.handler.VimActionHandler
import com.maddyhome.idea.vim.helper.getTopLevelEditor import com.maddyhome.idea.vim.helper.getTopLevelEditor
import com.maddyhome.idea.vim.helper.mode
import com.maddyhome.idea.vim.helper.vimForEachCaret
class ResetModeAction : VimActionHandler.SingleExecution() { class ResetModeAction : VimActionHandler.SingleExecution() {
override val type: Command.Type = Command.Type.OTHER_WRITABLE override val type: Command.Type = Command.Type.OTHER_WRITABLE
override fun execute(editor: Editor, context: DataContext, cmd: Command): Boolean { override fun execute(editor: Editor, context: DataContext, cmd: Command): Boolean {
val modeBeforeReset = editor.mode
KeyHandler.getInstance().fullReset(editor.getTopLevelEditor()) KeyHandler.getInstance().fullReset(editor.getTopLevelEditor())
if (modeBeforeReset == CommandState.Mode.INSERT) {
editor.vimForEachCaret { caret ->
val position = VimPlugin.getMotion().getOffsetOfHorizontalMotion(editor, caret, -1, false)
MotionGroup.moveCaret(editor, caret, position)
}
}
return true return true
} }
} }

View File

@@ -39,6 +39,7 @@ import com.maddyhome.idea.vim.helper.inInsertMode
import com.maddyhome.idea.vim.helper.inNormalMode import com.maddyhome.idea.vim.helper.inNormalMode
import com.maddyhome.idea.vim.helper.isIdeaVimDisabledHere import com.maddyhome.idea.vim.helper.isIdeaVimDisabledHere
import com.maddyhome.idea.vim.helper.isPrimaryEditor import com.maddyhome.idea.vim.helper.isPrimaryEditor
import com.maddyhome.idea.vim.helper.isTemplateActive
import com.maddyhome.idea.vim.key.ShortcutOwner import com.maddyhome.idea.vim.key.ShortcutOwner
import com.maddyhome.idea.vim.listener.IdeaSpecifics.aceJumpActive import com.maddyhome.idea.vim.listener.IdeaSpecifics.aceJumpActive
import com.maddyhome.idea.vim.option.OptionsManager import com.maddyhome.idea.vim.option.OptionsManager
@@ -63,7 +64,7 @@ class VimShortcutKeyAction : AnAction(), DumbAware {
} }
// Should we use HelperKt.getTopLevelEditor(editor) here, as we did in former EditorKeyHandler? // Should we use HelperKt.getTopLevelEditor(editor) here, as we did in former EditorKeyHandler?
try { try {
KeyHandler.getInstance().handleKey(editor, keyStroke, EditorDataContext(editor)) KeyHandler.getInstance().handleKey(editor, keyStroke, EditorDataContext(editor, e.dataContext))
} catch (ignored: ProcessCanceledException) { } catch (ignored: ProcessCanceledException) {
// Control-flow exceptions (like ProcessCanceledException) should never be logged // Control-flow exceptions (like ProcessCanceledException) should never be logged
// See {@link com.intellij.openapi.diagnostic.Logger.checkException} // See {@link com.intellij.openapi.diagnostic.Logger.checkException}
@@ -84,7 +85,7 @@ class VimShortcutKeyAction : AnAction(), DumbAware {
if (editor != null && keyStroke != null) { if (editor != null && keyStroke != null) {
if (editor.isIdeaVimDisabledHere) return false if (editor.isIdeaVimDisabledHere) return false
// Workaround for smart step into // Workaround for smart step into
@Suppress("DEPRECATION") @Suppress("DEPRECATION", "LocalVariableName", "VariableNaming")
val SMART_STEP_INPLACE_DATA = Key.findKeyByName("SMART_STEP_INPLACE_DATA") val SMART_STEP_INPLACE_DATA = Key.findKeyByName("SMART_STEP_INPLACE_DATA")
if (SMART_STEP_INPLACE_DATA != null && editor.getUserData(SMART_STEP_INPLACE_DATA) != null) return false if (SMART_STEP_INPLACE_DATA != null && editor.getUserData(SMART_STEP_INPLACE_DATA) != null) return false
@@ -96,6 +97,8 @@ class VimShortcutKeyAction : AnAction(), DumbAware {
if (keyCode == KeyEvent.VK_ESCAPE) return isEnabledForEscape(editor) if (keyCode == KeyEvent.VK_ESCAPE) return isEnabledForEscape(editor)
if (keyCode == KeyEvent.VK_TAB && editor.isTemplateActive()) return false
if (editor.inInsertMode) { // XXX: <Tab> won't be recorded in macros if (editor.inInsertMode) { // XXX: <Tab> won't be recorded in macros
if (keyCode == KeyEvent.VK_TAB) { if (keyCode == KeyEvent.VK_TAB) {
VimPlugin.getChange().tabAction = true VimPlugin.getChange().tabAction = true
@@ -123,8 +126,9 @@ class VimShortcutKeyAction : AnAction(), DumbAware {
} }
private fun isEnabledForEscape(editor: Editor): Boolean { private fun isEnabledForEscape(editor: Editor): Boolean {
return (editor.isPrimaryEditor() || EditorHelper.isFileEditor(editor) && !editor.inNormalMode) || return editor.isPrimaryEditor()
(OptionsManager.dialogescape.value == "on" && !editor.inNormalMode) || EditorHelper.isFileEditor(editor) && !editor.inNormalMode
|| OptionsManager.ideavimsupport.contains("dialog") && !editor.inNormalMode
} }
private fun isShortcutConflict(keyStroke: KeyStroke): Boolean { private fun isShortcutConflict(keyStroke: KeyStroke): Boolean {

View File

@@ -24,6 +24,8 @@ import com.maddyhome.idea.vim.VimPlugin
import com.maddyhome.idea.vim.command.Argument import com.maddyhome.idea.vim.command.Argument
import com.maddyhome.idea.vim.command.Command import com.maddyhome.idea.vim.command.Command
import com.maddyhome.idea.vim.command.CommandFlags import com.maddyhome.idea.vim.command.CommandFlags
import com.maddyhome.idea.vim.command.CommandFlags.FLAG_MULTIKEY_UNDO
import com.maddyhome.idea.vim.command.CommandFlags.FLAG_NO_REPEAT_INSERT
import com.maddyhome.idea.vim.handler.ChangeEditorActionHandler import com.maddyhome.idea.vim.handler.ChangeEditorActionHandler
import com.maddyhome.idea.vim.helper.enumSetOf import com.maddyhome.idea.vim.helper.enumSetOf
import java.util.* import java.util.*
@@ -31,14 +33,16 @@ import java.util.*
class ChangeCharactersAction : ChangeEditorActionHandler.ForEachCaret() { class ChangeCharactersAction : ChangeEditorActionHandler.ForEachCaret() {
override val type: Command.Type = Command.Type.CHANGE override val type: Command.Type = Command.Type.CHANGE
override val flags: EnumSet<CommandFlags> = enumSetOf(CommandFlags.FLAG_NO_REPEAT_INSERT, CommandFlags.FLAG_MULTIKEY_UNDO) override val flags: EnumSet<CommandFlags> = enumSetOf(FLAG_NO_REPEAT_INSERT, FLAG_MULTIKEY_UNDO)
override fun execute(editor: Editor, override fun execute(
caret: Caret, editor: Editor,
context: DataContext, caret: Caret,
count: Int, context: DataContext,
rawCount: Int, count: Int,
argument: Argument?): Boolean { rawCount: Int,
argument: Argument?
): Boolean {
return VimPlugin.getChange().changeCharacters(editor, caret, count) return VimPlugin.getChange().changeCharacters(editor, caret, count)
} }
} }

View File

@@ -24,6 +24,8 @@ import com.maddyhome.idea.vim.VimPlugin
import com.maddyhome.idea.vim.command.Argument import com.maddyhome.idea.vim.command.Argument
import com.maddyhome.idea.vim.command.Command import com.maddyhome.idea.vim.command.Command
import com.maddyhome.idea.vim.command.CommandFlags import com.maddyhome.idea.vim.command.CommandFlags
import com.maddyhome.idea.vim.command.CommandFlags.FLAG_MULTIKEY_UNDO
import com.maddyhome.idea.vim.command.CommandFlags.FLAG_NO_REPEAT_INSERT
import com.maddyhome.idea.vim.handler.ChangeEditorActionHandler import com.maddyhome.idea.vim.handler.ChangeEditorActionHandler
import com.maddyhome.idea.vim.helper.enumSetOf import com.maddyhome.idea.vim.helper.enumSetOf
import java.util.* import java.util.*
@@ -31,7 +33,7 @@ import java.util.*
class ChangeEndOfLineAction : ChangeEditorActionHandler.ForEachCaret() { class ChangeEndOfLineAction : ChangeEditorActionHandler.ForEachCaret() {
override val type: Command.Type = Command.Type.CHANGE override val type: Command.Type = Command.Type.CHANGE
override val flags: EnumSet<CommandFlags> = enumSetOf(CommandFlags.FLAG_NO_REPEAT_INSERT, CommandFlags.FLAG_MULTIKEY_UNDO) override val flags: EnumSet<CommandFlags> = enumSetOf(FLAG_NO_REPEAT_INSERT, FLAG_MULTIKEY_UNDO)
override fun execute(editor: Editor, override fun execute(editor: Editor,
caret: Caret, caret: Caret,

View File

@@ -25,6 +25,8 @@ import com.maddyhome.idea.vim.action.motion.updown.MotionDownLess1FirstNonSpaceA
import com.maddyhome.idea.vim.command.Argument import com.maddyhome.idea.vim.command.Argument
import com.maddyhome.idea.vim.command.Command import com.maddyhome.idea.vim.command.Command
import com.maddyhome.idea.vim.command.CommandFlags import com.maddyhome.idea.vim.command.CommandFlags
import com.maddyhome.idea.vim.command.CommandFlags.FLAG_MULTIKEY_UNDO
import com.maddyhome.idea.vim.command.CommandFlags.FLAG_NO_REPEAT_INSERT
import com.maddyhome.idea.vim.handler.ChangeEditorActionHandler import com.maddyhome.idea.vim.handler.ChangeEditorActionHandler
import com.maddyhome.idea.vim.helper.enumSetOf import com.maddyhome.idea.vim.helper.enumSetOf
import java.util.* import java.util.*
@@ -32,14 +34,16 @@ import java.util.*
class ChangeLineAction : ChangeEditorActionHandler.ForEachCaret() { class ChangeLineAction : ChangeEditorActionHandler.ForEachCaret() {
override val type: Command.Type = Command.Type.CHANGE override val type: Command.Type = Command.Type.CHANGE
override val flags: EnumSet<CommandFlags> = enumSetOf(CommandFlags.FLAG_NO_REPEAT_INSERT, CommandFlags.FLAG_MULTIKEY_UNDO) override val flags: EnumSet<CommandFlags> = enumSetOf(FLAG_NO_REPEAT_INSERT, FLAG_MULTIKEY_UNDO)
override fun execute(editor: Editor, override fun execute(
caret: Caret, editor: Editor,
context: DataContext, caret: Caret,
count: Int, context: DataContext,
rawCount: Int, count: Int,
argument: Argument?): Boolean { rawCount: Int,
argument: Argument?
): Boolean {
// `S` command is a synonym of `cc` // `S` command is a synonym of `cc`
val motion = MotionDownLess1FirstNonSpaceAction() val motion = MotionDownLess1FirstNonSpaceAction()
val command = Command(1, motion, motion.type, motion.flags) val command = Command(1, motion, motion.type, motion.flags)

View File

@@ -23,6 +23,9 @@ import com.intellij.openapi.editor.Editor
import com.maddyhome.idea.vim.VimPlugin import com.maddyhome.idea.vim.VimPlugin
import com.maddyhome.idea.vim.command.Command import com.maddyhome.idea.vim.command.Command
import com.maddyhome.idea.vim.command.CommandFlags import com.maddyhome.idea.vim.command.CommandFlags
import com.maddyhome.idea.vim.command.CommandFlags.FLAG_EXIT_VISUAL
import com.maddyhome.idea.vim.command.CommandFlags.FLAG_MOT_LINEWISE
import com.maddyhome.idea.vim.command.CommandFlags.FLAG_MULTIKEY_UNDO
import com.maddyhome.idea.vim.command.SelectionType import com.maddyhome.idea.vim.command.SelectionType
import com.maddyhome.idea.vim.common.TextRange import com.maddyhome.idea.vim.common.TextRange
import com.maddyhome.idea.vim.group.visual.VimSelection import com.maddyhome.idea.vim.group.visual.VimSelection
@@ -37,7 +40,7 @@ import java.util.*
class ChangeVisualLinesAction : VisualOperatorActionHandler.ForEachCaret() { class ChangeVisualLinesAction : VisualOperatorActionHandler.ForEachCaret() {
override val type: Command.Type = Command.Type.CHANGE override val type: Command.Type = Command.Type.CHANGE
override val flags: EnumSet<CommandFlags> = enumSetOf(CommandFlags.FLAG_MOT_LINEWISE, CommandFlags.FLAG_MULTIKEY_UNDO, CommandFlags.FLAG_EXIT_VISUAL) override val flags: EnumSet<CommandFlags> = enumSetOf(FLAG_MOT_LINEWISE, FLAG_MULTIKEY_UNDO, FLAG_EXIT_VISUAL)
override fun executeAction(editor: Editor, override fun executeAction(editor: Editor,
caret: Caret, caret: Caret,

View File

@@ -23,6 +23,9 @@ import com.intellij.openapi.editor.Editor
import com.maddyhome.idea.vim.VimPlugin import com.maddyhome.idea.vim.VimPlugin
import com.maddyhome.idea.vim.command.Command import com.maddyhome.idea.vim.command.Command
import com.maddyhome.idea.vim.command.CommandFlags import com.maddyhome.idea.vim.command.CommandFlags
import com.maddyhome.idea.vim.command.CommandFlags.FLAG_EXIT_VISUAL
import com.maddyhome.idea.vim.command.CommandFlags.FLAG_MOT_LINEWISE
import com.maddyhome.idea.vim.command.CommandFlags.FLAG_MULTIKEY_UNDO
import com.maddyhome.idea.vim.command.SelectionType import com.maddyhome.idea.vim.command.SelectionType
import com.maddyhome.idea.vim.common.TextRange import com.maddyhome.idea.vim.common.TextRange
import com.maddyhome.idea.vim.group.visual.VimSelection import com.maddyhome.idea.vim.group.visual.VimSelection
@@ -37,7 +40,7 @@ import java.util.*
class ChangeVisualLinesEndAction : VisualOperatorActionHandler.ForEachCaret() { class ChangeVisualLinesEndAction : VisualOperatorActionHandler.ForEachCaret() {
override val type: Command.Type = Command.Type.CHANGE override val type: Command.Type = Command.Type.CHANGE
override val flags: EnumSet<CommandFlags> = enumSetOf(CommandFlags.FLAG_MOT_LINEWISE, CommandFlags.FLAG_MULTIKEY_UNDO, CommandFlags.FLAG_EXIT_VISUAL) override val flags: EnumSet<CommandFlags> = enumSetOf(FLAG_MOT_LINEWISE, FLAG_MULTIKEY_UNDO, FLAG_EXIT_VISUAL)
override fun executeAction(editor: Editor, override fun executeAction(editor: Editor,
caret: Caret, caret: Caret,

View File

@@ -28,7 +28,7 @@ import com.maddyhome.idea.vim.handler.VisualOperatorActionHandler
import com.maddyhome.idea.vim.helper.enumSetOf import com.maddyhome.idea.vim.helper.enumSetOf
import java.util.* import java.util.*
sealed class IncNumber(val inc: Int, val avalanche: Boolean) : VisualOperatorActionHandler.ForEachCaret() { sealed class IncNumber(val inc: Int, private val avalanche: Boolean) : VisualOperatorActionHandler.ForEachCaret() {
override val type: Command.Type = Command.Type.CHANGE override val type: Command.Type = Command.Type.CHANGE
override val flags: EnumSet<CommandFlags> = enumSetOf(CommandFlags.FLAG_EXIT_VISUAL) override val flags: EnumSet<CommandFlags> = enumSetOf(CommandFlags.FLAG_EXIT_VISUAL)

View File

@@ -10,7 +10,7 @@ import javax.swing.KeyStroke
class InsertCompletedDigraphAction : VimActionHandler.SingleExecution() { class InsertCompletedDigraphAction : VimActionHandler.SingleExecution() {
override val type: Command.Type = Command.Type.INSERT override val type: Command.Type = Command.Type.INSERT
override val argumentType: Argument.Type? = Argument.Type.DIGRAPH override val argumentType: Argument.Type = Argument.Type.DIGRAPH
override fun execute(editor: Editor, context: DataContext, cmd: Command): Boolean { override fun execute(editor: Editor, context: DataContext, cmd: Command): Boolean {
// The converted digraph character has been captured as an argument, push it back through key handler // The converted digraph character has been captured as an argument, push it back through key handler

View File

@@ -10,7 +10,7 @@ import javax.swing.KeyStroke
class InsertCompletedLiteralAction : VimActionHandler.SingleExecution() { class InsertCompletedLiteralAction : VimActionHandler.SingleExecution() {
override val type: Command.Type = Command.Type.INSERT override val type: Command.Type = Command.Type.INSERT
override val argumentType: Argument.Type? = Argument.Type.DIGRAPH override val argumentType: Argument.Type = Argument.Type.DIGRAPH
override fun execute(editor: Editor, context: DataContext, cmd: Command): Boolean { override fun execute(editor: Editor, context: DataContext, cmd: Command): Boolean {
// The converted literal character has been captured as an argument, push it back through key handler // The converted literal character has been captured as an argument, push it back through key handler

View File

@@ -37,7 +37,7 @@ class MotionInnerSentenceAction : TextObjectActionHandler() {
override val visualType: TextObjectVisualType = TextObjectVisualType.CHARACTER_WISE override val visualType: TextObjectVisualType = TextObjectVisualType.CHARACTER_WISE
override fun getRange(editor: Editor, caret: Caret, context: DataContext, count: Int, rawCount: Int, argument: Argument?): TextRange? { override fun getRange(editor: Editor, caret: Caret, context: DataContext, count: Int, rawCount: Int, argument: Argument?): TextRange {
return VimPlugin.getMotion().getSentenceRange(editor, caret, count, false) return VimPlugin.getMotion().getSentenceRange(editor, caret, count, false)
} }
} }

View File

@@ -31,7 +31,7 @@ class MotionInnerWordAction : TextObjectActionHandler() {
override val visualType: TextObjectVisualType = TextObjectVisualType.CHARACTER_WISE override val visualType: TextObjectVisualType = TextObjectVisualType.CHARACTER_WISE
override fun getRange(editor: Editor, caret: Caret, context: DataContext, count: Int, rawCount: Int, argument: Argument?): TextRange? { override fun getRange(editor: Editor, caret: Caret, context: DataContext, count: Int, rawCount: Int, argument: Argument?): TextRange {
return VimPlugin.getMotion().getWordRange(editor, caret, count, false, false) return VimPlugin.getMotion().getWordRange(editor, caret, count, false, false)
} }
} }

View File

@@ -32,7 +32,7 @@ class MotionOuterBigWordAction : TextObjectActionHandler() {
override val visualType: TextObjectVisualType = TextObjectVisualType.CHARACTER_WISE override val visualType: TextObjectVisualType = TextObjectVisualType.CHARACTER_WISE
override fun getRange(editor: Editor, caret: Caret, context: DataContext, count: Int, rawCount: Int, argument: Argument?): TextRange? { override fun getRange(editor: Editor, caret: Caret, context: DataContext, count: Int, rawCount: Int, argument: Argument?): TextRange {
return VimPlugin.getMotion().getWordRange(editor, caret, count, true, true) return VimPlugin.getMotion().getWordRange(editor, caret, count, true, true)
} }
} }

View File

@@ -37,7 +37,7 @@ class MotionOuterSentenceAction : TextObjectActionHandler() {
override val visualType: TextObjectVisualType = TextObjectVisualType.CHARACTER_WISE override val visualType: TextObjectVisualType = TextObjectVisualType.CHARACTER_WISE
override fun getRange(editor: Editor, caret: Caret, context: DataContext, count: Int, rawCount: Int, argument: Argument?): TextRange? { override fun getRange(editor: Editor, caret: Caret, context: DataContext, count: Int, rawCount: Int, argument: Argument?): TextRange {
return VimPlugin.getMotion().getSentenceRange(editor, caret, count, true) return VimPlugin.getMotion().getSentenceRange(editor, caret, count, true)
} }
} }

View File

@@ -32,7 +32,7 @@ class MotionOuterWordAction : TextObjectActionHandler() {
override val visualType: TextObjectVisualType = TextObjectVisualType.CHARACTER_WISE override val visualType: TextObjectVisualType = TextObjectVisualType.CHARACTER_WISE
override fun getRange(editor: Editor, caret: Caret, context: DataContext, count: Int, rawCount: Int, argument: Argument?): TextRange? { override fun getRange(editor: Editor, caret: Caret, context: DataContext, count: Int, rawCount: Int, argument: Argument?): TextRange {
return VimPlugin.getMotion().getWordRange(editor, caret, count, true, false) return VimPlugin.getMotion().getWordRange(editor, caret, count, true, false)
} }
} }

View File

@@ -24,6 +24,8 @@ import com.maddyhome.idea.vim.VimPlugin
import com.maddyhome.idea.vim.action.ComplicatedKeysAction import com.maddyhome.idea.vim.action.ComplicatedKeysAction
import com.maddyhome.idea.vim.command.Command import com.maddyhome.idea.vim.command.Command
import com.maddyhome.idea.vim.command.CommandFlags import com.maddyhome.idea.vim.command.CommandFlags
import com.maddyhome.idea.vim.command.CommandFlags.FLAG_CLEAR_STROKES
import com.maddyhome.idea.vim.command.CommandFlags.FLAG_IGNORE_SCROLL_JUMP
import com.maddyhome.idea.vim.handler.VimActionHandler import com.maddyhome.idea.vim.handler.VimActionHandler
import com.maddyhome.idea.vim.helper.enumSetOf import com.maddyhome.idea.vim.helper.enumSetOf
import java.awt.event.KeyEvent import java.awt.event.KeyEvent
@@ -35,7 +37,7 @@ class MotionScrollPageDownAction : VimActionHandler.SingleExecution() {
override val type: Command.Type = Command.Type.OTHER_READONLY override val type: Command.Type = Command.Type.OTHER_READONLY
override val flags: EnumSet<CommandFlags> = enumSetOf(CommandFlags.FLAG_IGNORE_SCROLL_JUMP) override val flags: EnumSet<CommandFlags> = enumSetOf(FLAG_IGNORE_SCROLL_JUMP)
override fun execute(editor: Editor, context: DataContext, cmd: Command): Boolean { override fun execute(editor: Editor, context: DataContext, cmd: Command): Boolean {
return VimPlugin.getMotion().scrollFullPage(editor, cmd.count) return VimPlugin.getMotion().scrollFullPage(editor, cmd.count)
@@ -52,7 +54,7 @@ class MotionScrollPageDownInsertModeAction : VimActionHandler.SingleExecution(),
override val type: Command.Type = Command.Type.OTHER_READONLY override val type: Command.Type = Command.Type.OTHER_READONLY
override val flags: EnumSet<CommandFlags> = enumSetOf(CommandFlags.FLAG_IGNORE_SCROLL_JUMP, CommandFlags.FLAG_CLEAR_STROKES) override val flags: EnumSet<CommandFlags> = enumSetOf(FLAG_IGNORE_SCROLL_JUMP, FLAG_CLEAR_STROKES)
override fun execute(editor: Editor, context: DataContext, cmd: Command): Boolean { override fun execute(editor: Editor, context: DataContext, cmd: Command): Boolean {
return VimPlugin.getMotion().scrollFullPage(editor, cmd.count) return VimPlugin.getMotion().scrollFullPage(editor, cmd.count)

View File

@@ -24,6 +24,8 @@ import com.maddyhome.idea.vim.VimPlugin
import com.maddyhome.idea.vim.action.ComplicatedKeysAction import com.maddyhome.idea.vim.action.ComplicatedKeysAction
import com.maddyhome.idea.vim.command.Command import com.maddyhome.idea.vim.command.Command
import com.maddyhome.idea.vim.command.CommandFlags import com.maddyhome.idea.vim.command.CommandFlags
import com.maddyhome.idea.vim.command.CommandFlags.FLAG_CLEAR_STROKES
import com.maddyhome.idea.vim.command.CommandFlags.FLAG_IGNORE_SCROLL_JUMP
import com.maddyhome.idea.vim.handler.VimActionHandler import com.maddyhome.idea.vim.handler.VimActionHandler
import com.maddyhome.idea.vim.helper.enumSetOf import com.maddyhome.idea.vim.helper.enumSetOf
import java.awt.event.KeyEvent import java.awt.event.KeyEvent
@@ -35,7 +37,7 @@ class MotionScrollPageUpAction : VimActionHandler.SingleExecution() {
override val type: Command.Type = Command.Type.OTHER_READONLY override val type: Command.Type = Command.Type.OTHER_READONLY
override val flags: EnumSet<CommandFlags> = enumSetOf(CommandFlags.FLAG_IGNORE_SCROLL_JUMP) override val flags: EnumSet<CommandFlags> = enumSetOf(FLAG_IGNORE_SCROLL_JUMP)
override fun execute(editor: Editor, context: DataContext, cmd: Command): Boolean { override fun execute(editor: Editor, context: DataContext, cmd: Command): Boolean {
return VimPlugin.getMotion().scrollFullPage(editor, -cmd.count) return VimPlugin.getMotion().scrollFullPage(editor, -cmd.count)
@@ -52,7 +54,7 @@ class MotionScrollPageUpInsertModeAction : VimActionHandler.SingleExecution(), C
override val type: Command.Type = Command.Type.OTHER_READONLY override val type: Command.Type = Command.Type.OTHER_READONLY
override val flags: EnumSet<CommandFlags> = enumSetOf(CommandFlags.FLAG_IGNORE_SCROLL_JUMP, CommandFlags.FLAG_CLEAR_STROKES) override val flags: EnumSet<CommandFlags> = enumSetOf(FLAG_IGNORE_SCROLL_JUMP, FLAG_CLEAR_STROKES)
override fun execute(editor: Editor, context: DataContext, cmd: Command): Boolean { override fun execute(editor: Editor, context: DataContext, cmd: Command): Boolean {
return VimPlugin.getMotion().scrollFullPage(editor, -cmd.count) return VimPlugin.getMotion().scrollFullPage(editor, -cmd.count)

View File

@@ -42,12 +42,12 @@ class SelectMotionLeftAction : MotionActionHandler.ForEachCaret() {
override fun getOffset(editor: Editor, caret: Caret, context: DataContext, count: Int, rawCount: Int, argument: Argument?): Int { override fun getOffset(editor: Editor, caret: Caret, context: DataContext, count: Int, rawCount: Int, argument: Argument?): Int {
val keymodel = OptionsManager.keymodel val keymodel = OptionsManager.keymodel
if (KeyModelOptionData.stopsel in keymodel || KeyModelOptionData.stopselect in keymodel) { if (KeyModelOptionData.stopsel in keymodel || KeyModelOptionData.stopselect in keymodel) {
logger.info("Keymodel option has stopselect. Exiting select mode") logger.debug("Keymodel option has stopselect. Exiting select mode")
val startSelection = caret.selectionStart val startSelection = caret.selectionStart
val endSelection = caret.selectionEnd val endSelection = caret.selectionEnd
editor.exitSelectMode(false) editor.exitSelectMode(false)
if (editor.isTemplateActive()) { if (editor.isTemplateActive()) {
logger.info("Template is active. Activate insert mode") logger.debug("Template is active. Activate insert mode")
VimPlugin.getChange().insertBeforeCursor(editor, context) VimPlugin.getChange().insertBeforeCursor(editor, context)
if (caret.offset in startSelection..endSelection) { if (caret.offset in startSelection..endSelection) {
return startSelection return startSelection

View File

@@ -42,12 +42,12 @@ class SelectMotionRightAction : MotionActionHandler.ForEachCaret() {
override fun getOffset(editor: Editor, caret: Caret, context: DataContext, count: Int, rawCount: Int, argument: Argument?): Int { override fun getOffset(editor: Editor, caret: Caret, context: DataContext, count: Int, rawCount: Int, argument: Argument?): Int {
val keymodel = OptionsManager.keymodel val keymodel = OptionsManager.keymodel
if (KeyModelOptionData.stopsel in keymodel || KeyModelOptionData.stopselect in keymodel) { if (KeyModelOptionData.stopsel in keymodel || KeyModelOptionData.stopselect in keymodel) {
logger.info("Keymodel option has stopselect. Exiting select mode") logger.debug("Keymodel option has stopselect. Exiting select mode")
val startSelection = caret.selectionStart val startSelection = caret.selectionStart
val endSelection = caret.selectionEnd val endSelection = caret.selectionEnd
editor.exitSelectMode(false) editor.exitSelectMode(false)
if (editor.isTemplateActive()) { if (editor.isTemplateActive()) {
logger.info("Template is active. Activate insert mode") logger.debug("Template is active. Activate insert mode")
VimPlugin.getChange().insertBeforeCursor(editor, context) VimPlugin.getChange().insertBeforeCursor(editor, context)
if (caret.offset in startSelection..endSelection) { if (caret.offset in startSelection..endSelection) {
return endSelection return endSelection

View File

@@ -24,7 +24,8 @@ import com.maddyhome.idea.vim.VimPlugin
import com.maddyhome.idea.vim.command.Command import com.maddyhome.idea.vim.command.Command
import com.maddyhome.idea.vim.group.MotionGroup import com.maddyhome.idea.vim.group.MotionGroup
import com.maddyhome.idea.vim.handler.ShiftedArrowKeyHandler import com.maddyhome.idea.vim.handler.ShiftedArrowKeyHandler
import com.maddyhome.idea.vim.helper.* import com.maddyhome.idea.vim.helper.EditorHelper
import com.maddyhome.idea.vim.helper.vimForEachCaret
/** /**
* @author Alex Plate * @author Alex Plate

View File

@@ -24,7 +24,8 @@ import com.maddyhome.idea.vim.VimPlugin
import com.maddyhome.idea.vim.command.Command import com.maddyhome.idea.vim.command.Command
import com.maddyhome.idea.vim.group.MotionGroup import com.maddyhome.idea.vim.group.MotionGroup
import com.maddyhome.idea.vim.handler.ShiftedArrowKeyHandler import com.maddyhome.idea.vim.handler.ShiftedArrowKeyHandler
import com.maddyhome.idea.vim.helper.* import com.maddyhome.idea.vim.helper.EditorHelper
import com.maddyhome.idea.vim.helper.vimForEachCaret
/** /**
* @author Alex Plate * @author Alex Plate

View File

@@ -19,10 +19,14 @@ package com.maddyhome.idea.vim.action.motion.visual
import com.intellij.openapi.actionSystem.DataContext import com.intellij.openapi.actionSystem.DataContext
import com.intellij.openapi.editor.Editor import com.intellij.openapi.editor.Editor
import com.maddyhome.idea.vim.VimPlugin
import com.maddyhome.idea.vim.command.Command import com.maddyhome.idea.vim.command.Command
import com.maddyhome.idea.vim.group.MotionGroup
import com.maddyhome.idea.vim.handler.VimActionHandler import com.maddyhome.idea.vim.handler.VimActionHandler
import com.maddyhome.idea.vim.helper.EditorHelper
import com.maddyhome.idea.vim.helper.exitVisualMode import com.maddyhome.idea.vim.helper.exitVisualMode
import com.maddyhome.idea.vim.helper.getTopLevelEditor import com.maddyhome.idea.vim.helper.getTopLevelEditor
import com.maddyhome.idea.vim.helper.vimForEachCaret
/** /**
* @author vlan * @author vlan
@@ -32,6 +36,16 @@ class VisualExitModeAction : VimActionHandler.SingleExecution() {
override fun execute(editor: Editor, context: DataContext, cmd: Command): Boolean { override fun execute(editor: Editor, context: DataContext, cmd: Command): Boolean {
editor.getTopLevelEditor().exitVisualMode() editor.getTopLevelEditor().exitVisualMode()
// Should it be in [exitVisualMode]?
editor.vimForEachCaret { caret ->
val lineEnd = EditorHelper.getLineEndForOffset(editor, caret.offset)
if (lineEnd == caret.offset) {
val position = VimPlugin.getMotion().getOffsetOfHorizontalMotion(editor, caret, -1, false)
MotionGroup.moveCaret(editor, caret, position)
}
}
return true return true
} }
} }

View File

@@ -21,11 +21,12 @@ import com.intellij.openapi.diagnostic.Logger
import com.intellij.openapi.diagnostic.debug import com.intellij.openapi.diagnostic.debug
import com.intellij.openapi.editor.Editor import com.intellij.openapi.editor.Editor
import com.maddyhome.idea.vim.VimPlugin import com.maddyhome.idea.vim.VimPlugin
import com.maddyhome.idea.vim.action.motion.updown.* import com.maddyhome.idea.vim.helper.DigraphResult
import com.maddyhome.idea.vim.helper.* import com.maddyhome.idea.vim.helper.DigraphSequence
import com.maddyhome.idea.vim.helper.noneOfEnum
import com.maddyhome.idea.vim.helper.vimCommandState
import com.maddyhome.idea.vim.key.CommandPartNode import com.maddyhome.idea.vim.key.CommandPartNode
import com.maddyhome.idea.vim.option.OptionsManager.showmode import com.maddyhome.idea.vim.option.OptionsManager.showmode
import org.jetbrains.annotations.ApiStatus
import org.jetbrains.annotations.Contract import org.jetbrains.annotations.Contract
import java.util.* import java.util.*
import javax.swing.KeyStroke import javax.swing.KeyStroke
@@ -58,12 +59,6 @@ class CommandState private constructor() {
var executingCommand: Command? = null var executingCommand: Command? = null
private set private set
// Keep the compatibility with the IdeaVim-EasyMotion plugin before the stable release
@get:Deprecated("")
@get:ApiStatus.ScheduledForRemoval(inVersion = "0.58")
val mappingMode: MappingMode
get() = mappingState.mappingMode
val isOperatorPending: Boolean val isOperatorPending: Boolean
get() = mappingState.mappingMode == MappingMode.OP_PENDING && !commandBuilder.isEmpty get() = mappingState.mappingMode == MappingMode.OP_PENDING && !commandBuilder.isEmpty
@@ -80,7 +75,7 @@ class CommandState private constructor() {
fun pushModes(mode: Mode, submode: SubMode) { fun pushModes(mode: Mode, submode: SubMode) {
val newModeState = ModeState(mode, submode) val newModeState = ModeState(mode, submode)
logger.info("Push new mode state: ${newModeState.toSimpleString()}") logger.debug("Push new mode state: ${newModeState.toSimpleString()}")
logger.debug { "Stack of mode states before push: ${toSimpleString()}" } logger.debug { "Stack of mode states before push: ${toSimpleString()}" }
modeStates.push(newModeState) modeStates.push(newModeState)
setMappingMode() setMappingMode()
@@ -91,7 +86,7 @@ class CommandState private constructor() {
val popped = modeStates.pop() val popped = modeStates.pop()
setMappingMode() setMappingMode()
updateStatus() updateStatus()
logger.info("Popped mode state: ${popped.toSimpleString()}") logger.debug("Popped mode state: ${popped.toSimpleString()}")
logger.debug { "Stack of mode states after pop: ${toSimpleString()}" } logger.debug { "Stack of mode states after pop: ${toSimpleString()}" }
} }
@@ -183,7 +178,7 @@ class CommandState private constructor() {
executingCommand = null executingCommand = null
resetModes() resetModes()
commandBuilder.resetInProgressCommandPart(getKeyRootNode(mappingState.mappingMode)) commandBuilder.resetInProgressCommandPart(getKeyRootNode(mappingState.mappingMode))
startDigraphSequence() digraphSequence.reset()
updateStatus() updateStatus()
} }

View File

@@ -121,31 +121,8 @@ sealed class CommandHandler {
@Throws(ExException::class) @Throws(ExException::class)
fun process(editor: Editor, context: DataContext, cmd: ExCommand, count: Int): Boolean { fun process(editor: Editor, context: DataContext, cmd: ExCommand, count: Int): Boolean {
// No range allowed checkArgs(cmd)
if (RangeFlag.RANGE_FORBIDDEN == argFlags.rangeFlag && cmd.ranges.size() != 0) {
VimPlugin.showMessage(MessageHelper.message(Msg.e_norange))
throw NoRangeAllowedException()
}
if (RangeFlag.RANGE_REQUIRED == argFlags.rangeFlag && cmd.ranges.size() == 0) {
VimPlugin.showMessage(MessageHelper.message(Msg.e_rangereq))
throw MissingRangeException()
}
if (RangeFlag.RANGE_IS_COUNT == argFlags.rangeFlag) {
cmd.ranges.setDefaultLine(1)
}
// Argument required
if (ArgumentFlag.ARGUMENT_REQUIRED == argFlags.argumentFlag && cmd.argument.isEmpty()) {
VimPlugin.showMessage(MessageHelper.message(Msg.e_argreq))
throw MissingArgumentException()
}
if (ArgumentFlag.ARGUMENT_FORBIDDEN == argFlags.argumentFlag && cmd.argument.isNotEmpty()) {
VimPlugin.showMessage(MessageHelper.message(Msg.e_argforb))
throw NoArgumentAllowedException()
}
if (editor.inVisualMode && Flag.SAVE_VISUAL !in argFlags.flags) { if (editor.inVisualMode && Flag.SAVE_VISUAL !in argFlags.flags) {
editor.exitVisualMode() editor.exitVisualMode()
} }
@@ -179,6 +156,34 @@ sealed class CommandHandler {
return false return false
} }
} }
private fun checkArgs(cmd: ExCommand) {
// No range allowed
if (RangeFlag.RANGE_FORBIDDEN == argFlags.rangeFlag && cmd.ranges.size() != 0) {
VimPlugin.showMessage(MessageHelper.message(Msg.e_norange))
throw NoRangeAllowedException()
}
if (RangeFlag.RANGE_REQUIRED == argFlags.rangeFlag && cmd.ranges.size() == 0) {
VimPlugin.showMessage(MessageHelper.message(Msg.e_rangereq))
throw MissingRangeException()
}
if (RangeFlag.RANGE_IS_COUNT == argFlags.rangeFlag) {
cmd.ranges.setDefaultLine(1)
}
// Argument required
if (ArgumentFlag.ARGUMENT_REQUIRED == argFlags.argumentFlag && cmd.argument.isEmpty()) {
VimPlugin.showMessage(MessageHelper.message(Msg.e_argreq))
throw MissingArgumentException()
}
if (ArgumentFlag.ARGUMENT_FORBIDDEN == argFlags.argumentFlag && cmd.argument.isNotEmpty()) {
VimPlugin.showMessage(MessageHelper.message(Msg.e_argforb))
throw NoArgumentAllowedException()
}
}
} }
data class CommandHandlerFlags( data class CommandHandlerFlags(

View File

@@ -126,7 +126,6 @@ public class CommandParser {
private void processCommand(@NotNull Editor editor, @NotNull DataContext context, @NotNull String cmd, private void processCommand(@NotNull Editor editor, @NotNull DataContext context, @NotNull String cmd,
int count, int aliasCountdown) throws ExException { int count, int aliasCountdown) throws ExException {
// Nothing entered // Nothing entered
int result = 0;
if (cmd.length() == 0) { if (cmd.length() == 0) {
logger.warn("CMD is empty"); logger.warn("CMD is empty");
return; return;
@@ -326,13 +325,12 @@ public class CommandParser {
if (ch == '/' || ch == '?' || ch == '&') { if (ch == '/' || ch == '?' || ch == '&') {
location.append(ch); location.append(ch);
state = State.RANGE_PATTERN_MAYBE_DONE; state = State.RANGE_PATTERN_MAYBE_DONE;
reprocess = false;
} }
else { else {
error = MessageHelper.message(Msg.e_backslash); error = MessageHelper.message(Msg.e_backslash);
state = State.ERROR; state = State.ERROR;
reprocess = false;
} }
reprocess = false;
break; break;
case RANGE_PATTERN: // Reading a pattern range case RANGE_PATTERN: // Reading a pattern range
// No trailing / or ? required if there is no command so look for newline to tell us we are done // No trailing / or ? required if there is no command so look for newline to tell us we are done

View File

@@ -26,7 +26,10 @@ import com.intellij.openapi.editor.Editor
import com.maddyhome.idea.vim.KeyHandler import com.maddyhome.idea.vim.KeyHandler
import com.maddyhome.idea.vim.VimPlugin import com.maddyhome.idea.vim.VimPlugin
import com.maddyhome.idea.vim.ex.CommandHandler import com.maddyhome.idea.vim.ex.CommandHandler
import com.maddyhome.idea.vim.ex.CommandHandler.Access.READ_ONLY
import com.maddyhome.idea.vim.ex.CommandHandler.ArgumentFlag.ARGUMENT_OPTIONAL
import com.maddyhome.idea.vim.ex.CommandHandler.Flag.SAVE_VISUAL import com.maddyhome.idea.vim.ex.CommandHandler.Flag.SAVE_VISUAL
import com.maddyhome.idea.vim.ex.CommandHandler.RangeFlag.RANGE_OPTIONAL
import com.maddyhome.idea.vim.ex.CommandHandlerFlags import com.maddyhome.idea.vim.ex.CommandHandlerFlags
import com.maddyhome.idea.vim.ex.ExCommand import com.maddyhome.idea.vim.ex.ExCommand
import com.maddyhome.idea.vim.ex.flags import com.maddyhome.idea.vim.ex.flags
@@ -37,7 +40,7 @@ import com.maddyhome.idea.vim.helper.runAfterGotFocus
*/ */
class ActionHandler : CommandHandler.SingleExecution() { class ActionHandler : CommandHandler.SingleExecution() {
override val argFlags: CommandHandlerFlags = flags(RangeFlag.RANGE_OPTIONAL, ArgumentFlag.ARGUMENT_OPTIONAL, Access.READ_ONLY, SAVE_VISUAL) override val argFlags: CommandHandlerFlags = flags(RANGE_OPTIONAL, ARGUMENT_OPTIONAL, READ_ONLY, SAVE_VISUAL)
override fun execute(editor: Editor, context: DataContext, cmd: ExCommand): Boolean { override fun execute(editor: Editor, context: DataContext, cmd: ExCommand): Boolean {
val actionName = cmd.argument.trim() val actionName = cmd.argument.trim()

View File

@@ -23,6 +23,9 @@ import com.intellij.openapi.actionSystem.DataContext
import com.intellij.openapi.actionSystem.KeyboardShortcut import com.intellij.openapi.actionSystem.KeyboardShortcut
import com.intellij.openapi.editor.Editor import com.intellij.openapi.editor.Editor
import com.maddyhome.idea.vim.ex.CommandHandler import com.maddyhome.idea.vim.ex.CommandHandler
import com.maddyhome.idea.vim.ex.CommandHandler.Access.READ_ONLY
import com.maddyhome.idea.vim.ex.CommandHandler.ArgumentFlag.ARGUMENT_OPTIONAL
import com.maddyhome.idea.vim.ex.CommandHandler.RangeFlag.RANGE_FORBIDDEN
import com.maddyhome.idea.vim.ex.CommandHandlerFlags import com.maddyhome.idea.vim.ex.CommandHandlerFlags
import com.maddyhome.idea.vim.ex.ExCommand import com.maddyhome.idea.vim.ex.ExCommand
import com.maddyhome.idea.vim.ex.ExOutputModel import com.maddyhome.idea.vim.ex.ExOutputModel
@@ -33,7 +36,7 @@ import com.maddyhome.idea.vim.helper.StringHelper
* @author smartbomb * @author smartbomb
*/ */
class ActionListHandler : CommandHandler.SingleExecution() { class ActionListHandler : CommandHandler.SingleExecution() {
override val argFlags: CommandHandlerFlags = flags(RangeFlag.RANGE_FORBIDDEN, ArgumentFlag.ARGUMENT_OPTIONAL, Access.READ_ONLY) override val argFlags: CommandHandlerFlags = flags(RANGE_FORBIDDEN, ARGUMENT_OPTIONAL, READ_ONLY)
override fun execute(editor: Editor, context: DataContext, cmd: ExCommand): Boolean { override fun execute(editor: Editor, context: DataContext, cmd: ExCommand): Boolean {
val lineSeparator = "\n" val lineSeparator = "\n"

View File

@@ -22,12 +22,15 @@ import com.intellij.openapi.actionSystem.DataContext
import com.intellij.openapi.editor.Editor import com.intellij.openapi.editor.Editor
import com.maddyhome.idea.vim.VimPlugin import com.maddyhome.idea.vim.VimPlugin
import com.maddyhome.idea.vim.ex.CommandHandler import com.maddyhome.idea.vim.ex.CommandHandler
import com.maddyhome.idea.vim.ex.CommandHandler.Access.READ_ONLY
import com.maddyhome.idea.vim.ex.CommandHandler.ArgumentFlag.ARGUMENT_FORBIDDEN
import com.maddyhome.idea.vim.ex.CommandHandler.RangeFlag.RANGE_FORBIDDEN
import com.maddyhome.idea.vim.ex.CommandHandlerFlags import com.maddyhome.idea.vim.ex.CommandHandlerFlags
import com.maddyhome.idea.vim.ex.ExCommand import com.maddyhome.idea.vim.ex.ExCommand
import com.maddyhome.idea.vim.ex.flags import com.maddyhome.idea.vim.ex.flags
class AsciiHandler : CommandHandler.SingleExecution() { class AsciiHandler : CommandHandler.SingleExecution() {
override val argFlags: CommandHandlerFlags = flags(RangeFlag.RANGE_FORBIDDEN, ArgumentFlag.ARGUMENT_FORBIDDEN, Access.READ_ONLY) override val argFlags: CommandHandlerFlags = flags(RANGE_FORBIDDEN, ARGUMENT_FORBIDDEN, READ_ONLY)
override fun execute(editor: Editor, context: DataContext, cmd: ExCommand): Boolean { override fun execute(editor: Editor, context: DataContext, cmd: ExCommand): Boolean {
VimPlugin.getDigraph().displayAsciiInfo(editor) VimPlugin.getDigraph().displayAsciiInfo(editor)

View File

@@ -22,12 +22,15 @@ import com.intellij.openapi.actionSystem.DataContext
import com.intellij.openapi.editor.Editor import com.intellij.openapi.editor.Editor
import com.maddyhome.idea.vim.VimPlugin import com.maddyhome.idea.vim.VimPlugin
import com.maddyhome.idea.vim.ex.CommandHandler import com.maddyhome.idea.vim.ex.CommandHandler
import com.maddyhome.idea.vim.ex.CommandHandler.Access.READ_ONLY
import com.maddyhome.idea.vim.ex.CommandHandler.ArgumentFlag.ARGUMENT_FORBIDDEN
import com.maddyhome.idea.vim.ex.CommandHandler.RangeFlag.RANGE_FORBIDDEN
import com.maddyhome.idea.vim.ex.CommandHandlerFlags import com.maddyhome.idea.vim.ex.CommandHandlerFlags
import com.maddyhome.idea.vim.ex.ExCommand import com.maddyhome.idea.vim.ex.ExCommand
import com.maddyhome.idea.vim.ex.flags import com.maddyhome.idea.vim.ex.flags
class CmdClearHandler : CommandHandler.SingleExecution() { class CmdClearHandler : CommandHandler.SingleExecution() {
override val argFlags: CommandHandlerFlags = flags(RangeFlag.RANGE_FORBIDDEN, ArgumentFlag.ARGUMENT_FORBIDDEN, Access.READ_ONLY) override val argFlags: CommandHandlerFlags = flags(RANGE_FORBIDDEN, ARGUMENT_FORBIDDEN, READ_ONLY)
override fun execute(editor: Editor, context: DataContext, cmd: ExCommand): Boolean { override fun execute(editor: Editor, context: DataContext, cmd: ExCommand): Boolean {
VimPlugin.getCommand().resetAliases() VimPlugin.getCommand().resetAliases()

View File

@@ -34,7 +34,7 @@ import java.io.IOException
class CmdFilterHandler : CommandHandler.SingleExecution() { class CmdFilterHandler : CommandHandler.SingleExecution() {
override val argFlags = flags(RangeFlag.RANGE_OPTIONAL, ArgumentFlag.ARGUMENT_OPTIONAL, Access.WRITABLE) override val argFlags = flags(RangeFlag.RANGE_OPTIONAL, ArgumentFlag.ARGUMENT_OPTIONAL, Access.WRITABLE)
override fun execute(editor: Editor, context: DataContext, cmd: ExCommand): Boolean { override fun execute(editor: Editor, context: DataContext, cmd: ExCommand): Boolean {
logger.info("execute") logger.debug("execute")
var command = cmd.argument var command = cmd.argument
if (command.isEmpty()) { if (command.isEmpty()) {

View File

@@ -23,6 +23,9 @@ import com.intellij.openapi.editor.Editor
import com.maddyhome.idea.vim.VimPlugin import com.maddyhome.idea.vim.VimPlugin
import com.maddyhome.idea.vim.common.Alias import com.maddyhome.idea.vim.common.Alias
import com.maddyhome.idea.vim.ex.CommandHandler import com.maddyhome.idea.vim.ex.CommandHandler
import com.maddyhome.idea.vim.ex.CommandHandler.Access.READ_ONLY
import com.maddyhome.idea.vim.ex.CommandHandler.ArgumentFlag.ARGUMENT_OPTIONAL
import com.maddyhome.idea.vim.ex.CommandHandler.RangeFlag.RANGE_FORBIDDEN
import com.maddyhome.idea.vim.ex.CommandHandlerFlags import com.maddyhome.idea.vim.ex.CommandHandlerFlags
import com.maddyhome.idea.vim.ex.ExCommand import com.maddyhome.idea.vim.ex.ExCommand
import com.maddyhome.idea.vim.ex.ExOutputModel import com.maddyhome.idea.vim.ex.ExOutputModel
@@ -34,7 +37,7 @@ import com.maddyhome.idea.vim.group.CommandGroup.Companion.BLACKLISTED_ALIASES
* @author Elliot Courant * @author Elliot Courant
*/ */
class CmdHandler : CommandHandler.SingleExecution(), VimScriptCommandHandler { class CmdHandler : CommandHandler.SingleExecution(), VimScriptCommandHandler {
override val argFlags: CommandHandlerFlags = flags(RangeFlag.RANGE_FORBIDDEN, ArgumentFlag.ARGUMENT_OPTIONAL, Access.READ_ONLY) override val argFlags: CommandHandlerFlags = flags(RANGE_FORBIDDEN, ARGUMENT_OPTIONAL, READ_ONLY)
// Static definitions needed for aliases. // Static definitions needed for aliases.
private companion object { private companion object {

View File

@@ -31,6 +31,7 @@ import com.maddyhome.idea.vim.helper.EditorHelper
class CopyTextHandler : CommandHandler.SingleExecution() { class CopyTextHandler : CommandHandler.SingleExecution() {
override val argFlags = flags(RangeFlag.RANGE_OPTIONAL, ArgumentFlag.ARGUMENT_REQUIRED, Access.WRITABLE) override val argFlags = flags(RangeFlag.RANGE_OPTIONAL, ArgumentFlag.ARGUMENT_REQUIRED, Access.WRITABLE)
override fun execute(editor: Editor, context: DataContext, cmd: ExCommand): Boolean { override fun execute(editor: Editor, context: DataContext, cmd: ExCommand): Boolean {
val carets = EditorHelper.getOrderedCaretsList(editor) val carets = EditorHelper.getOrderedCaretsList(editor)
for (caret in carets) { for (caret in carets) {
@@ -42,7 +43,7 @@ class CopyTextHandler : CommandHandler.SingleExecution() {
val transferableData = VimPlugin.getRegister().getTransferableData(editor, range, text) val transferableData = VimPlugin.getRegister().getTransferableData(editor, range, text)
val textData = PutData.TextData(text, SelectionType.LINE_WISE, transferableData) val textData = PutData.TextData(text, SelectionType.LINE_WISE, transferableData)
val putData = PutData(textData, null, 1, insertTextBeforeCaret = false, _indent = true, caretAfterInsertedText = false, putToLine = line) val putData = PutData(textData, null, 1, insertTextBeforeCaret = false, rawIndent = true, caretAfterInsertedText = false, putToLine = line)
VimPlugin.getPut().putTextForCaret(editor, caret, context, putData) VimPlugin.getPut().putTextForCaret(editor, caret, context, putData)
} }
return true return true

View File

@@ -45,7 +45,7 @@ class EditFileHandler : CommandHandler.SingleExecution() {
} }
// Don't open a choose file dialog under a write action // Don't open a choose file dialog under a write action
ApplicationManager.getApplication().invokeLater { KeyHandler.executeAction("OpenFile", EditorDataContext(editor)) } ApplicationManager.getApplication().invokeLater { KeyHandler.executeAction("OpenFile", EditorDataContext(editor, context)) }
return true return true
} }

View File

@@ -23,13 +23,16 @@ import com.intellij.openapi.editor.Caret
import com.intellij.openapi.editor.Editor import com.intellij.openapi.editor.Editor
import com.maddyhome.idea.vim.VimPlugin import com.maddyhome.idea.vim.VimPlugin
import com.maddyhome.idea.vim.ex.CommandHandler import com.maddyhome.idea.vim.ex.CommandHandler
import com.maddyhome.idea.vim.ex.CommandHandler.Access.READ_ONLY
import com.maddyhome.idea.vim.ex.CommandHandler.ArgumentFlag.ARGUMENT_OPTIONAL
import com.maddyhome.idea.vim.ex.CommandHandler.RangeFlag.RANGE_IS_COUNT
import com.maddyhome.idea.vim.ex.CommandHandlerFlags import com.maddyhome.idea.vim.ex.CommandHandlerFlags
import com.maddyhome.idea.vim.ex.ExCommand import com.maddyhome.idea.vim.ex.ExCommand
import com.maddyhome.idea.vim.ex.flags import com.maddyhome.idea.vim.ex.flags
import com.maddyhome.idea.vim.group.MotionGroup import com.maddyhome.idea.vim.group.MotionGroup
class GotoCharacterHandler : CommandHandler.ForEachCaret() { class GotoCharacterHandler : CommandHandler.ForEachCaret() {
override val argFlags: CommandHandlerFlags = flags(RangeFlag.RANGE_IS_COUNT, ArgumentFlag.ARGUMENT_OPTIONAL, Access.READ_ONLY) override val argFlags: CommandHandlerFlags = flags(RANGE_IS_COUNT, ARGUMENT_OPTIONAL, READ_ONLY)
override fun execute(editor: Editor, caret: Caret, context: DataContext, cmd: ExCommand): Boolean { override fun execute(editor: Editor, caret: Caret, context: DataContext, cmd: ExCommand): Boolean {
val count = cmd.getCount(editor, caret, 1, true) val count = cmd.getCount(editor, caret, 1, true)

View File

@@ -23,6 +23,9 @@ import com.intellij.openapi.editor.Caret
import com.intellij.openapi.editor.Editor import com.intellij.openapi.editor.Editor
import com.maddyhome.idea.vim.VimPlugin import com.maddyhome.idea.vim.VimPlugin
import com.maddyhome.idea.vim.ex.CommandHandler import com.maddyhome.idea.vim.ex.CommandHandler
import com.maddyhome.idea.vim.ex.CommandHandler.Access.READ_ONLY
import com.maddyhome.idea.vim.ex.CommandHandler.ArgumentFlag.ARGUMENT_OPTIONAL
import com.maddyhome.idea.vim.ex.CommandHandler.RangeFlag.RANGE_REQUIRED
import com.maddyhome.idea.vim.ex.CommandHandlerFlags import com.maddyhome.idea.vim.ex.CommandHandlerFlags
import com.maddyhome.idea.vim.ex.ExCommand import com.maddyhome.idea.vim.ex.ExCommand
import com.maddyhome.idea.vim.ex.flags import com.maddyhome.idea.vim.ex.flags
@@ -35,7 +38,7 @@ import kotlin.math.min
* range. * range.
*/ */
class GotoLineHandler : CommandHandler.ForEachCaret() { class GotoLineHandler : CommandHandler.ForEachCaret() {
override val argFlags: CommandHandlerFlags = flags(RangeFlag.RANGE_REQUIRED, ArgumentFlag.ARGUMENT_OPTIONAL, Access.READ_ONLY) override val argFlags: CommandHandlerFlags = flags(RANGE_REQUIRED, ARGUMENT_OPTIONAL, READ_ONLY)
/** /**
* Moves the cursor to the line entered by the user * Moves the cursor to the line entered by the user

View File

@@ -22,6 +22,9 @@ import com.intellij.openapi.actionSystem.DataContext
import com.intellij.openapi.editor.Editor import com.intellij.openapi.editor.Editor
import com.maddyhome.idea.vim.VimPlugin import com.maddyhome.idea.vim.VimPlugin
import com.maddyhome.idea.vim.ex.CommandHandler import com.maddyhome.idea.vim.ex.CommandHandler
import com.maddyhome.idea.vim.ex.CommandHandler.Access.READ_ONLY
import com.maddyhome.idea.vim.ex.CommandHandler.ArgumentFlag.ARGUMENT_OPTIONAL
import com.maddyhome.idea.vim.ex.CommandHandler.RangeFlag.RANGE_OPTIONAL
import com.maddyhome.idea.vim.ex.CommandHandlerFlags import com.maddyhome.idea.vim.ex.CommandHandlerFlags
import com.maddyhome.idea.vim.ex.ExCommand import com.maddyhome.idea.vim.ex.ExCommand
import com.maddyhome.idea.vim.ex.ExOutputModel import com.maddyhome.idea.vim.ex.ExOutputModel
@@ -31,7 +34,7 @@ import com.maddyhome.idea.vim.helper.StringHelper.stringToKeys
import com.maddyhome.idea.vim.helper.StringHelper.toPrintableCharacters import com.maddyhome.idea.vim.helper.StringHelper.toPrintableCharacters
class MarksHandler : CommandHandler.SingleExecution() { class MarksHandler : CommandHandler.SingleExecution() {
override val argFlags: CommandHandlerFlags = flags(RangeFlag.RANGE_OPTIONAL, ArgumentFlag.ARGUMENT_OPTIONAL, Access.READ_ONLY) override val argFlags: CommandHandlerFlags = flags(RANGE_OPTIONAL, ARGUMENT_OPTIONAL, READ_ONLY)
override fun execute(editor: Editor, context: DataContext, cmd: ExCommand): Boolean { override fun execute(editor: Editor, context: DataContext, cmd: ExCommand): Boolean {

View File

@@ -74,7 +74,7 @@ class MoveTextHandler : CommandHandler.SingleExecution() {
val text = texts[i] val text = texts[i]
val textData = PutData.TextData(text, SelectionType.LINE_WISE, emptyList()) val textData = PutData.TextData(text, SelectionType.LINE_WISE, emptyList())
val putData = PutData(textData, null, 1, insertTextBeforeCaret = false, _indent = true, caretAfterInsertedText = false, putToLine = line) val putData = PutData(textData, null, 1, insertTextBeforeCaret = false, rawIndent = true, caretAfterInsertedText = false, putToLine = line)
VimPlugin.getPut().putTextForCaret(editor, caret, context, putData) VimPlugin.getPut().putTextForCaret(editor, caret, context, putData)
} }

View File

@@ -22,12 +22,15 @@ import com.intellij.openapi.actionSystem.DataContext
import com.intellij.openapi.editor.Editor import com.intellij.openapi.editor.Editor
import com.maddyhome.idea.vim.VimPlugin import com.maddyhome.idea.vim.VimPlugin
import com.maddyhome.idea.vim.ex.CommandHandler import com.maddyhome.idea.vim.ex.CommandHandler
import com.maddyhome.idea.vim.ex.CommandHandler.Access.READ_ONLY
import com.maddyhome.idea.vim.ex.CommandHandler.ArgumentFlag.ARGUMENT_OPTIONAL
import com.maddyhome.idea.vim.ex.CommandHandler.RangeFlag.RANGE_OPTIONAL
import com.maddyhome.idea.vim.ex.CommandHandlerFlags import com.maddyhome.idea.vim.ex.CommandHandlerFlags
import com.maddyhome.idea.vim.ex.ExCommand import com.maddyhome.idea.vim.ex.ExCommand
import com.maddyhome.idea.vim.ex.flags import com.maddyhome.idea.vim.ex.flags
class OnlyHandler : CommandHandler.SingleExecution() { class OnlyHandler : CommandHandler.SingleExecution() {
override val argFlags: CommandHandlerFlags = flags(RangeFlag.RANGE_OPTIONAL, ArgumentFlag.ARGUMENT_OPTIONAL, Access.READ_ONLY) override val argFlags: CommandHandlerFlags = flags(RANGE_OPTIONAL, ARGUMENT_OPTIONAL, READ_ONLY)
override fun execute(editor: Editor, context: DataContext, cmd: ExCommand): Boolean { override fun execute(editor: Editor, context: DataContext, cmd: ExCommand): Boolean {
VimPlugin.getWindow().closeAllExceptCurrent(context) VimPlugin.getWindow().closeAllExceptCurrent(context)

View File

@@ -0,0 +1,56 @@
/*
* IdeaVim - Vim emulator for IDEs based on the IntelliJ platform
* Copyright (C) 2003-2020 The IdeaVim authors
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <https://www.gnu.org/licenses/>.
*/
package com.maddyhome.idea.vim.ex.handler
import com.intellij.openapi.actionSystem.DataContext
import com.intellij.openapi.editor.Editor
import com.maddyhome.idea.vim.ex.CommandHandler
import com.maddyhome.idea.vim.ex.CommandHandler.Access.READ_ONLY
import com.maddyhome.idea.vim.ex.CommandHandler.ArgumentFlag.ARGUMENT_REQUIRED
import com.maddyhome.idea.vim.ex.CommandHandler.RangeFlag.RANGE_FORBIDDEN
import com.maddyhome.idea.vim.ex.CommandHandlerFlags
import com.maddyhome.idea.vim.ex.ExCommand
import com.maddyhome.idea.vim.ex.flags
import com.maddyhome.idea.vim.ex.vimscript.VimScriptCommandHandler
import com.maddyhome.idea.vim.extension.VimExtensionRegistrar
/**
* This handler is created to support `Plug` command from vim-plug and `Plugin` command from vundle.
*/
class PlugHandler : CommandHandler.SingleExecution(), VimScriptCommandHandler {
override val argFlags: CommandHandlerFlags = flags(RANGE_FORBIDDEN, ARGUMENT_REQUIRED, READ_ONLY)
override fun execute(editor: Editor, context: DataContext, cmd: ExCommand): Boolean = doExecute(cmd)
override fun execute(cmd: ExCommand) {
doExecute(cmd)
}
private fun doExecute(cmd: ExCommand): Boolean {
val argument = cmd.argument
val firstChar = argument[0]
if (firstChar != '"' && firstChar != '\'') return false
val pluginAlias = argument.drop(1).takeWhile { it != firstChar }
val option = VimExtensionRegistrar.getToggleByAlias(pluginAlias) ?: return false
option.set()
return true
}
}

View File

@@ -45,7 +45,7 @@ class PutLinesHandler : CommandHandler.SingleExecution() {
val line = if (cmd.ranges.size() == 0) -1 else cmd.getLine(editor) val line = if (cmd.ranges.size() == 0) -1 else cmd.getLine(editor)
val textData = registerGroup.lastRegister?.let { PutData.TextData(it.text ?: StringHelper.toKeyNotation(it.keys), SelectionType.LINE_WISE, it.transferableData) } val textData = registerGroup.lastRegister?.let { PutData.TextData(it.text ?: StringHelper.toKeyNotation(it.keys), SelectionType.LINE_WISE, it.transferableData) }
val putData = PutData(textData, null, 1, insertTextBeforeCaret = false, _indent = false, caretAfterInsertedText = false, putToLine = line) val putData = PutData(textData, null, 1, insertTextBeforeCaret = false, rawIndent = false, caretAfterInsertedText = false, putToLine = line)
return VimPlugin.getPut().putText(editor, context, putData) return VimPlugin.getPut().putText(editor, context, putData)
} }
} }

View File

@@ -24,6 +24,9 @@ import com.intellij.openapi.editor.Editor
import com.maddyhome.idea.vim.VimPlugin import com.maddyhome.idea.vim.VimPlugin
import com.maddyhome.idea.vim.common.TextRange import com.maddyhome.idea.vim.common.TextRange
import com.maddyhome.idea.vim.ex.CommandHandler import com.maddyhome.idea.vim.ex.CommandHandler
import com.maddyhome.idea.vim.ex.CommandHandler.Access.WRITABLE
import com.maddyhome.idea.vim.ex.CommandHandler.ArgumentFlag.ARGUMENT_OPTIONAL
import com.maddyhome.idea.vim.ex.CommandHandler.RangeFlag.RANGE_OPTIONAL
import com.maddyhome.idea.vim.ex.CommandHandlerFlags import com.maddyhome.idea.vim.ex.CommandHandlerFlags
import com.maddyhome.idea.vim.ex.CommandName import com.maddyhome.idea.vim.ex.CommandName
import com.maddyhome.idea.vim.ex.ComplicatedNameExCommand import com.maddyhome.idea.vim.ex.ComplicatedNameExCommand
@@ -33,7 +36,7 @@ import com.maddyhome.idea.vim.ex.flags
class ShiftLeftHandler : CommandHandler.ForEachCaret(), ComplicatedNameExCommand { class ShiftLeftHandler : CommandHandler.ForEachCaret(), ComplicatedNameExCommand {
override val names: Array<CommandName> = commands("<[${"<".repeat(31)}]") override val names: Array<CommandName> = commands("<[${"<".repeat(31)}]")
override val argFlags: CommandHandlerFlags = flags(RangeFlag.RANGE_OPTIONAL, ArgumentFlag.ARGUMENT_OPTIONAL, Access.WRITABLE) override val argFlags: CommandHandlerFlags = flags(RANGE_OPTIONAL, ARGUMENT_OPTIONAL, WRITABLE)
override fun execute(editor: Editor, caret: Caret, context: DataContext, cmd: ExCommand): Boolean { override fun execute(editor: Editor, caret: Caret, context: DataContext, cmd: ExCommand): Boolean {
val range = cmd.getTextRange(editor, caret, true) val range = cmd.getTextRange(editor, caret, true)

View File

@@ -24,6 +24,9 @@ import com.intellij.openapi.editor.Editor
import com.maddyhome.idea.vim.VimPlugin import com.maddyhome.idea.vim.VimPlugin
import com.maddyhome.idea.vim.common.TextRange import com.maddyhome.idea.vim.common.TextRange
import com.maddyhome.idea.vim.ex.CommandHandler import com.maddyhome.idea.vim.ex.CommandHandler
import com.maddyhome.idea.vim.ex.CommandHandler.Access.WRITABLE
import com.maddyhome.idea.vim.ex.CommandHandler.ArgumentFlag.ARGUMENT_OPTIONAL
import com.maddyhome.idea.vim.ex.CommandHandler.RangeFlag.RANGE_OPTIONAL
import com.maddyhome.idea.vim.ex.CommandHandlerFlags import com.maddyhome.idea.vim.ex.CommandHandlerFlags
import com.maddyhome.idea.vim.ex.CommandName import com.maddyhome.idea.vim.ex.CommandName
import com.maddyhome.idea.vim.ex.ComplicatedNameExCommand import com.maddyhome.idea.vim.ex.ComplicatedNameExCommand
@@ -33,7 +36,7 @@ import com.maddyhome.idea.vim.ex.flags
class ShiftRightHandler : CommandHandler.ForEachCaret(), ComplicatedNameExCommand { class ShiftRightHandler : CommandHandler.ForEachCaret(), ComplicatedNameExCommand {
override val names: Array<CommandName> = commands(">[${">".repeat(31)}]") override val names: Array<CommandName> = commands(">[${">".repeat(31)}]")
override val argFlags: CommandHandlerFlags = flags(RangeFlag.RANGE_OPTIONAL, ArgumentFlag.ARGUMENT_OPTIONAL, Access.WRITABLE) override val argFlags: CommandHandlerFlags = flags(RANGE_OPTIONAL, ARGUMENT_OPTIONAL, WRITABLE)
override fun execute(editor: Editor, caret: Caret, context: DataContext, cmd: ExCommand): Boolean { override fun execute(editor: Editor, caret: Caret, context: DataContext, cmd: ExCommand): Boolean {
val range = cmd.getTextRange(editor, caret, true) val range = cmd.getTextRange(editor, caret, true)

View File

@@ -95,6 +95,10 @@ object VimScriptParser {
return data return data
} }
fun executeText(vararg text: String) {
executeText(listOf(*text))
}
fun executeText(text: List<String>) { fun executeText(text: List<String>) {
for (line in text) { for (line in text) {
// TODO: Build a proper parse tree for a VimL file instead of ignoring potentially nested lines (VIM-669) // TODO: Build a proper parse tree for a VimL file instead of ignoring potentially nested lines (VIM-669)

View File

@@ -0,0 +1,64 @@
/*
* IdeaVim - Vim emulator for IDEs based on the IntelliJ platform
* Copyright (C) 2003-2020 The IdeaVim authors
*
* This program is free software: you can redistribute it and/or modify
* it under the terms of the GNU General Public License as published by
* the Free Software Foundation, either version 2 of the License, or
* (at your option) any later version.
*
* This program is distributed in the hope that it will be useful,
* but WITHOUT ANY WARRANTY; without even the implied warranty of
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
* GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License
* along with this program. If not, see <https://www.gnu.org/licenses/>.
*/
package com.maddyhome.idea.vim.extension
import com.intellij.openapi.application.ApplicationManager
import com.intellij.openapi.extensions.AbstractExtensionPointBean
import com.intellij.util.xmlb.annotations.Attribute
import com.intellij.util.xmlb.annotations.CollectionBean
import com.intellij.util.xmlb.annotations.Tag
import com.intellij.util.xmlb.annotations.XCollection
import java.util.concurrent.atomic.AtomicBoolean
// [Version Update] 202+
@Suppress("DEPRECATION")
class ExtensionBeanClass : AbstractExtensionPointBean() {
init {
println()
}
@Attribute("implementation")
var implementation: String? = null
@Attribute("name")
var name: String? = null
/**
* List of aliases for the extension. These aliases are used to support `Plug` and `Plugin` commands.
* Technically, it would be enough to save here github link and short version of it ('author/plugin'),
* but it may contain more aliases just in case.
*/
@Tag("aliases")
@XCollection
var aliases: List<Alias>? = null
var initialized = AtomicBoolean(false)
val handler: VimExtension by lazy {
initialized.set(true)
this.instantiateClass<VimExtension>(
implementation ?: "", ApplicationManager.getApplication().picoContainer
)
}
}
@Tag("alias")
class Alias {
@Attribute("name")
var name: String? = null
}

View File

@@ -21,16 +21,22 @@ package com.maddyhome.idea.vim.extension;
import com.intellij.openapi.extensions.ExtensionPointName; import com.intellij.openapi.extensions.ExtensionPointName;
import com.maddyhome.idea.vim.VimPlugin; import com.maddyhome.idea.vim.VimPlugin;
import com.maddyhome.idea.vim.key.MappingOwner; import com.maddyhome.idea.vim.key.MappingOwner;
import org.jetbrains.annotations.ApiStatus;
import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.NotNull;
/** /**
* @author vlan * @author vlan
*/ */
public interface VimExtension { public interface VimExtension {
@NotNull ExtensionPointName<VimExtension> EP_NAME = ExtensionPointName.create("IdeaVIM.vimExtension"); @NotNull ExtensionPointName<ExtensionBeanClass> EP_NAME = ExtensionPointName.create("IdeaVIM.vimExtension");
@NotNull /**
String getName(); * @deprecated This property is not used anymore, but we'll remove it much later to keep the compatibility of IdeaVim
* extensions with previous versions of IdeaVim.
*/
@Deprecated
@ApiStatus.ScheduledForRemoval(inVersion = "0.65")
@NotNull String getName();
default MappingOwner getOwner() { default MappingOwner getOwner() {
return MappingOwner.Plugin.Companion.get(getName()); return MappingOwner.Plugin.Companion.get(getName());
@@ -40,5 +46,5 @@ public interface VimExtension {
default void dispose() { default void dispose() {
VimPlugin.getKey().removeKeyMapping(getOwner()); VimPlugin.getKey().removeKeyMapping(getOwner());
}; }
} }

View File

@@ -32,7 +32,6 @@ import com.maddyhome.idea.vim.key.MappingOwner
import com.maddyhome.idea.vim.key.OperatorFunction import com.maddyhome.idea.vim.key.OperatorFunction
import com.maddyhome.idea.vim.ui.ExEntryPanel import com.maddyhome.idea.vim.ui.ExEntryPanel
import com.maddyhome.idea.vim.ui.ModalEntry import com.maddyhome.idea.vim.ui.ModalEntry
import org.jetbrains.annotations.ApiStatus.ScheduledForRemoval
import java.awt.event.KeyEvent import java.awt.event.KeyEvent
import javax.swing.KeyStroke import javax.swing.KeyStroke
@@ -44,22 +43,6 @@ import javax.swing.KeyStroke
* @author vlan * @author vlan
*/ */
object VimExtensionFacade { object VimExtensionFacade {
/** The 'map' command for mapping keys to handlers defined in extensions. */
@JvmStatic
@ScheduledForRemoval(inVersion = "0.58")
@Deprecated("Only for EasyMotion support")
fun putExtensionHandlerMapping(modes: Set<MappingMode>, fromKeys: List<KeyStroke>, extensionHandler: VimExtensionHandler, recursive: Boolean) {
VimPlugin.getKey().putKeyMapping(modes, fromKeys, MappingOwner.Plugin.get("easymotion"), extensionHandler, recursive)
}
@ScheduledForRemoval(inVersion = "0.58")
@Deprecated("Only for EasyMotion support")
@JvmStatic
fun putKeyMapping(modes: Set<MappingMode>, fromKeys: List<KeyStroke>,
toKeys: List<KeyStroke>, recursive: Boolean) {
VimPlugin.getKey().putKeyMapping(modes, fromKeys, MappingOwner.Plugin.get("easymotion"), toKeys, recursive)
}
/** The 'map' command for mapping keys to handlers defined in extensions. */ /** The 'map' command for mapping keys to handlers defined in extensions. */
@JvmStatic @JvmStatic
fun putExtensionHandlerMapping(modes: Set<MappingMode>, fromKeys: List<KeyStroke>, fun putExtensionHandlerMapping(modes: Set<MappingMode>, fromKeys: List<KeyStroke>,
@@ -98,8 +81,7 @@ object VimExtensionFacade {
fun inputKeyStroke(editor: Editor): KeyStroke { fun inputKeyStroke(editor: Editor): KeyStroke {
if (editor.commandState.isDotRepeatInProgress) { if (editor.commandState.isDotRepeatInProgress) {
val input = VimRepeater.Extension.consumeKeystroke() val input = VimRepeater.Extension.consumeKeystroke()
return input return input ?: error("Not enough keystrokes saved: ${VimRepeater.Extension.lastExtensionHandler}")
?: throw RuntimeException("Not enough keystrokes saved: ${VimRepeater.Extension.lastExtensionHandler}")
} }
val key: KeyStroke? = if (ApplicationManager.getApplication().isUnitTestMode) { val key: KeyStroke? = if (ApplicationManager.getApplication().isUnitTestMode) {
@@ -122,7 +104,7 @@ object VimExtensionFacade {
fun inputString(editor: Editor, prompt: String, finishOn: Char?): String { fun inputString(editor: Editor, prompt: String, finishOn: Char?): String {
if (editor.commandState.isDotRepeatInProgress) { if (editor.commandState.isDotRepeatInProgress) {
val input = VimRepeater.Extension.consumeString() val input = VimRepeater.Extension.consumeString()
return input ?: throw RuntimeException("Not enough strings saved: ${VimRepeater.Extension.lastExtensionHandler}") return input ?: error("Not enough strings saved: ${VimRepeater.Extension.lastExtensionHandler}")
} }
if (ApplicationManager.getApplication().isUnitTestMode) { if (ApplicationManager.getApplication().isUnitTestMode) {

View File

@@ -22,14 +22,15 @@ import com.intellij.openapi.extensions.ExtensionPointListener
import com.intellij.openapi.extensions.PluginDescriptor import com.intellij.openapi.extensions.PluginDescriptor
import com.maddyhome.idea.vim.VimPlugin import com.maddyhome.idea.vim.VimPlugin
import com.maddyhome.idea.vim.key.MappingOwner.Plugin.Companion.remove import com.maddyhome.idea.vim.key.MappingOwner.Plugin.Companion.remove
import com.maddyhome.idea.vim.option.OptionsManager
import com.maddyhome.idea.vim.option.OptionsManager.addOption import com.maddyhome.idea.vim.option.OptionsManager.addOption
import com.maddyhome.idea.vim.option.OptionsManager.isSet import com.maddyhome.idea.vim.option.OptionsManager.isSet
import com.maddyhome.idea.vim.option.OptionsManager.removeOption import com.maddyhome.idea.vim.option.OptionsManager.removeOption
import com.maddyhome.idea.vim.option.ToggleOption import com.maddyhome.idea.vim.option.ToggleOption
import java.util.*
object VimExtensionRegistrar { object VimExtensionRegistrar {
private val registeredExtensions: MutableSet<String> = HashSet() private val registeredExtensions: MutableSet<String> = HashSet()
private val extensionAliases = HashMap<String, String>()
private var extensionRegistered = false private var extensionRegistered = false
private val logger = logger<VimExtensionRegistrar>() private val logger = logger<VimExtensionRegistrar>()
@@ -37,48 +38,67 @@ object VimExtensionRegistrar {
fun registerExtensions() { fun registerExtensions() {
if (extensionRegistered) return if (extensionRegistered) return
extensionRegistered = true extensionRegistered = true
VimExtension.EP_NAME.extensions.forEach(this::registerExtension)
// [VERSION UPDATE] 202+ // [VERSION UPDATE] 202+
@Suppress("DEPRECATION") @Suppress("DEPRECATION")
VimExtension.EP_NAME.getPoint(null).addExtensionPointListener(object : ExtensionPointListener<VimExtension> { VimExtension.EP_NAME.getPoint(null).addExtensionPointListener(object : ExtensionPointListener<ExtensionBeanClass> {
override fun extensionAdded(extension: VimExtension, pluginDescriptor: PluginDescriptor) { override fun extensionAdded(extension: ExtensionBeanClass, pluginDescriptor: PluginDescriptor) {
registerExtension(extension) registerExtension(extension)
} }
override fun extensionRemoved(extension: VimExtension, pluginDescriptor: PluginDescriptor) { override fun extensionRemoved(extension: ExtensionBeanClass, pluginDescriptor: PluginDescriptor) {
unregisterExtension(extension) unregisterExtension(extension)
} }
}, true, VimPlugin.getInstance()) }, false, VimPlugin.getInstance())
} }
@Synchronized @Synchronized
private fun registerExtension(extension: VimExtension) { private fun registerExtension(extensionBean: ExtensionBeanClass) {
val name = extension.name val name = extensionBean.name ?: extensionBean.handler.name
if (name in registeredExtensions) return if (name in registeredExtensions) return
registeredExtensions.add(name) registeredExtensions.add(name)
registerAliases(extensionBean)
val option = ToggleOption(name, name, false) val option = ToggleOption(name, name, false)
option.addOptionChangeListener { _, _ -> option.addOptionChangeListener { _, _ ->
for (extensionInListener in VimExtension.EP_NAME.extensionList) { if (isSet(name)) {
if (name != extensionInListener.name) continue extensionBean.handler.init()
if (isSet(name)) { logger.info("IdeaVim extension '$name' initialized")
extensionInListener.init() } else {
logger.info("IdeaVim extension '$name' initialized") extensionBean.handler.dispose()
} else {
extensionInListener.dispose()
}
} }
} }
addOption(option) addOption(option)
} }
@Synchronized @Synchronized
private fun unregisterExtension(extension: VimExtension) { private fun unregisterExtension(extension: ExtensionBeanClass) {
val name = extension.name val name = extension.name ?: extension.handler.name
if (name !in registeredExtensions) return if (name !in registeredExtensions) return
registeredExtensions.remove(name) registeredExtensions.remove(name)
extension.dispose() removeAliases(extension)
if (extension.initialized.get()) {
extension.handler.dispose()
}
removeOption(name) removeOption(name)
remove(name) remove(name)
logger.info("IdeaVim extension '$name' disposed") logger.info("IdeaVim extension '$name' disposed")
} }
fun getToggleByAlias(alias: String): ToggleOption? {
val name = extensionAliases[alias] ?: return null
return OptionsManager.getOption(name) as ToggleOption?
}
private fun registerAliases(extension: ExtensionBeanClass) {
extension.aliases
?.mapNotNull { it.name }
?.forEach { alias -> extensionAliases[alias] = extension.name ?: extension.handler.name }
}
private fun removeAliases(extension: ExtensionBeanClass) {
extension.aliases?.mapNotNull { it.name }?.forEach { extensionAliases.remove(it) }
}
} }

View File

@@ -17,8 +17,7 @@ import com.maddyhome.idea.vim.listener.VimListenerSuppressor;
import org.jetbrains.annotations.NotNull; import org.jetbrains.annotations.NotNull;
import org.jetbrains.annotations.Nullable; import org.jetbrains.annotations.Nullable;
import java.util.EnumSet; import java.util.*;
import java.util.Stack;
import static com.maddyhome.idea.vim.extension.VimExtensionFacade.putExtensionHandlerMapping; import static com.maddyhome.idea.vim.extension.VimExtensionFacade.putExtensionHandlerMapping;
import static com.maddyhome.idea.vim.extension.VimExtensionFacade.putKeyMapping; import static com.maddyhome.idea.vim.extension.VimExtensionFacade.putKeyMapping;
@@ -50,13 +49,13 @@ public class VimArgTextObjExtension implements VimExtension {
/** /**
* The pairs of brackets that delimit different types of argument lists. * The pairs of brackets that delimit different types of argument lists.
*/ */
static private class BracketPairs { private static class BracketPairs {
// NOTE: brackets must match by the position, and ordered by rank (highest to lowest). // NOTE: brackets must match by the position, and ordered by rank (highest to lowest).
@NotNull private final String openBrackets; @NotNull private final String openBrackets;
@NotNull private final String closeBrackets; @NotNull private final String closeBrackets;
static class ParseError extends Exception { static class ParseException extends Exception {
public ParseError(@NotNull String message) { public ParseException(@NotNull String message) {
super(message); super(message);
} }
} }
@@ -73,10 +72,10 @@ public class VimArgTextObjExtension implements VimExtension {
* as VIM's @c matchpairs option: "(:),{:},[:]" * as VIM's @c matchpairs option: "(:),{:},[:]"
* *
* @param bracketPairs comma-separated list of colon-separated bracket pairs. * @param bracketPairs comma-separated list of colon-separated bracket pairs.
* @throws ParseError if a syntax error is detected. * @throws ParseException if a syntax error is detected.
*/ */
@NotNull @NotNull
static BracketPairs fromBracketPairList(@NotNull final String bracketPairs) throws ParseError { static BracketPairs fromBracketPairList(@NotNull final String bracketPairs) throws ParseException {
StringBuilder openBrackets = new StringBuilder(); StringBuilder openBrackets = new StringBuilder();
StringBuilder closeBrackets = new StringBuilder(); StringBuilder closeBrackets = new StringBuilder();
ParseState state = ParseState.OPEN; ParseState state = ParseState.OPEN;
@@ -90,13 +89,13 @@ public class VimArgTextObjExtension implements VimExtension {
if (ch == ':') { if (ch == ':') {
state = ParseState.CLOSE; state = ParseState.CLOSE;
} else { } else {
throw new ParseError("expecting ':', but got '" + ch + "' instead"); throw new ParseException("expecting ':', but got '" + ch + "' instead");
} }
break; break;
case CLOSE: case CLOSE:
final char lastOpenBracket = openBrackets.charAt(openBrackets.length() - 1); final char lastOpenBracket = openBrackets.charAt(openBrackets.length() - 1);
if (lastOpenBracket == ch) { if (lastOpenBracket == ch) {
throw new ParseError("open and close brackets must be different"); throw new ParseException("open and close brackets must be different");
} }
closeBrackets.append(ch); closeBrackets.append(ch);
state = ParseState.COMMA; state = ParseState.COMMA;
@@ -105,13 +104,13 @@ public class VimArgTextObjExtension implements VimExtension {
if (ch == ',') { if (ch == ',') {
state = ParseState.OPEN; state = ParseState.OPEN;
} else { } else {
throw new ParseError("expecting ',', but got '" + ch + "' instead"); throw new ParseException("expecting ',', but got '" + ch + "' instead");
} }
break; break;
} }
} }
if (state != ParseState.COMMA) { if (state != ParseState.COMMA) {
throw new ParseError("list of pairs is incomplete"); throw new ParseException("list of pairs is incomplete");
} }
return new BracketPairs(openBrackets.toString(), closeBrackets.toString()); return new BracketPairs(openBrackets.toString(), closeBrackets.toString());
} }
@@ -183,8 +182,8 @@ public class VimArgTextObjExtension implements VimExtension {
if (bracketPairsVar != null) { if (bracketPairsVar != null) {
try { try {
bracketPairs = BracketPairs.fromBracketPairList(bracketPairsVar); bracketPairs = BracketPairs.fromBracketPairList(bracketPairsVar);
} catch (BracketPairs.ParseError parseError) { } catch (BracketPairs.ParseException parseException) {
VimPlugin.showMessage("argtextobj: Invalid value of g:argtextobj_pairs -- " + parseError.getMessage()); VimPlugin.showMessage("argtextobj: Invalid value of g:argtextobj_pairs -- " + parseException.getMessage());
VimPlugin.indicateError(); VimPlugin.indicateError();
return null; return null;
} }
@@ -590,20 +589,20 @@ public class VimArgTextObjExtension implements VimExtension {
private int skipSexp(final int start, final int end, SexpDirection dir) { private int skipSexp(final int start, final int end, SexpDirection dir) {
char lastChar = getCharAt(start); char lastChar = getCharAt(start);
assert dir.isOpenBracket(lastChar); assert dir.isOpenBracket(lastChar);
Stack<Character> bracketStack = new Stack<>(); Deque<Character> bracketStack = new ArrayDeque<>();
bracketStack.push(lastChar); bracketStack.push(lastChar);
int i = start + dir.delta(); int i = start + dir.delta();
while (!bracketStack.empty() && i != end) { while (!bracketStack.isEmpty() && i != end) {
final char ch = getCharAt(i); final char ch = getCharAt(i);
if (dir.isOpenBracket(ch)) { if (dir.isOpenBracket(ch)) {
bracketStack.push(ch); bracketStack.push(ch);
} else { } else {
if (dir.isCloseBracket(ch)) { if (dir.isCloseBracket(ch)) {
if (bracketStack.lastElement() == brackets.matchingBracket(ch)) { if (bracketStack.getLast() == brackets.matchingBracket(ch)) {
bracketStack.pop(); bracketStack.pop();
} else { } else {
//noinspection StatementWithEmptyBody //noinspection StatementWithEmptyBody
if (brackets.getBracketPrio(ch) < brackets.getBracketPrio(bracketStack.lastElement())) { if (brackets.getBracketPrio(ch) < brackets.getBracketPrio(bracketStack.getLast())) {
// (<...) -> (...) // (<...) -> (...)
bracketStack.pop(); bracketStack.pop();
// Retry the same character again for cases like (...<<...). // Retry the same character again for cases like (...<<...).
@@ -621,7 +620,7 @@ public class VimArgTextObjExtension implements VimExtension {
} }
i += dir.delta(); i += dir.delta();
} }
if (bracketStack.empty()) { if (bracketStack.isEmpty()) {
return i; return i;
} else { } else {
return start + dir.delta(); return start + dir.delta();

View File

@@ -43,9 +43,13 @@ import com.maddyhome.idea.vim.extension.VimExtensionFacade.setOperatorFunction
import com.maddyhome.idea.vim.extension.VimExtensionFacade.setRegister import com.maddyhome.idea.vim.extension.VimExtensionFacade.setRegister
import com.maddyhome.idea.vim.extension.VimExtensionHandler import com.maddyhome.idea.vim.extension.VimExtensionHandler
import com.maddyhome.idea.vim.group.MarkGroup import com.maddyhome.idea.vim.group.MarkGroup
import com.maddyhome.idea.vim.helper.* import com.maddyhome.idea.vim.helper.EditorHelper
import com.maddyhome.idea.vim.helper.StringHelper.parseKeys import com.maddyhome.idea.vim.helper.StringHelper.parseKeys
import com.maddyhome.idea.vim.helper.StringHelper.stringToKeys import com.maddyhome.idea.vim.helper.StringHelper.stringToKeys
import com.maddyhome.idea.vim.helper.fileSize
import com.maddyhome.idea.vim.helper.moveToInlayAwareLogicalPosition
import com.maddyhome.idea.vim.helper.moveToInlayAwareOffset
import com.maddyhome.idea.vim.helper.subMode
import com.maddyhome.idea.vim.key.OperatorFunction import com.maddyhome.idea.vim.key.OperatorFunction
/** /**
@@ -59,7 +63,8 @@ import com.maddyhome.idea.vim.key.OperatorFunction
* It just won't work if the binding is defined after `set exchange`. * It just won't work if the binding is defined after `set exchange`.
*/ */
class VimExchangeExtension: VimExtension { class VimExchangeExtension : VimExtension {
override fun getName() = "exchange" override fun getName() = "exchange"
override fun init() { override fun init() {
@@ -105,17 +110,17 @@ class VimExchangeExtension: VimExtension {
override fun execute(editor: Editor, context: DataContext) { override fun execute(editor: Editor, context: DataContext) {
setOperatorFunction(Operator(false)) setOperatorFunction(Operator(false))
executeNormalWithoutMapping(parseKeys(if(isLine) "g@_" else "g@"), editor) executeNormalWithoutMapping(parseKeys(if (isLine) "g@_" else "g@"), editor)
} }
} }
private class ExchangeClearHandler: VimExtensionHandler { private class ExchangeClearHandler : VimExtensionHandler {
override fun execute(editor: Editor, context: DataContext) { override fun execute(editor: Editor, context: DataContext) {
clearExchange(editor) clearExchange(editor)
} }
} }
private class VExchangeHandler: VimExtensionHandler { private class VExchangeHandler : VimExtensionHandler {
override fun execute(editor: Editor, context: DataContext) { override fun execute(editor: Editor, context: DataContext) {
runWriteAction { runWriteAction {
val subMode = editor.subMode val subMode = editor.subMode
@@ -126,19 +131,19 @@ class VimExchangeExtension: VimExtension {
} }
} }
private class Operator(private val isVisual: Boolean): OperatorFunction { private class Operator(private val isVisual: Boolean) : OperatorFunction {
fun Editor.getMarkOffset(mark: Mark) = EditorHelper.getOffset(this, mark.logicalLine, mark.col) fun Editor.getMarkOffset(mark: Mark) = EditorHelper.getOffset(this, mark.logicalLine, mark.col)
fun CommandState.SubMode.getString() = when(this) { fun CommandState.SubMode.getString() = when (this) {
CommandState.SubMode.VISUAL_CHARACTER -> "v" CommandState.SubMode.VISUAL_CHARACTER -> "v"
CommandState.SubMode.VISUAL_LINE -> "V" CommandState.SubMode.VISUAL_LINE -> "V"
CommandState.SubMode.VISUAL_BLOCK -> "\\<C-V>" CommandState.SubMode.VISUAL_BLOCK -> "\\<C-V>"
else -> throw Error("Invalid SubMode: $this") else -> error("Invalid SubMode: $this")
} }
override fun apply(editor: Editor, context: DataContext, selectionType: SelectionType): Boolean { override fun apply(editor: Editor, context: DataContext, selectionType: SelectionType): Boolean {
fun highlightExchange(ex: Exchange): RangeHighlighter { fun highlightExchange(ex: Exchange): RangeHighlighter {
val attributes = editor.colorsScheme.getAttributes(EditorColors.TEXT_SEARCH_RESULT_ATTRIBUTES) val attributes = editor.colorsScheme.getAttributes(EditorColors.TEXT_SEARCH_RESULT_ATTRIBUTES)
val hlArea = when(ex.type) { val hlArea = when (ex.type) {
CommandState.SubMode.VISUAL_LINE -> HighlighterTargetArea.LINES_IN_RANGE CommandState.SubMode.VISUAL_LINE -> HighlighterTargetArea.LINES_IN_RANGE
// TODO: handle other modes // TODO: handle other modes
else -> HighlighterTargetArea.EXACT_RANGE else -> HighlighterTargetArea.EXACT_RANGE
@@ -151,6 +156,7 @@ class VimExchangeExtension: VimExtension {
hlArea hlArea
) )
} }
val currentExchange = getExchange(editor, isVisual, selectionType) val currentExchange = getExchange(editor, isVisual, selectionType)
val exchange1 = editor.getUserData(EXCHANGE_KEY) val exchange1 = editor.getUserData(EXCHANGE_KEY)
if (exchange1 == null) { if (exchange1 == null) {
@@ -162,7 +168,7 @@ class VimExchangeExtension: VimExtension {
val cmp = compareExchanges(exchange1, currentExchange) val cmp = compareExchanges(exchange1, currentExchange)
var reverse = false var reverse = false
var expand = false var expand = false
val (ex1, ex2) = when(cmp) { val (ex1, ex2) = when (cmp) {
ExchangeCompareResult.OVERLAP -> return false ExchangeCompareResult.OVERLAP -> return false
ExchangeCompareResult.OUTER -> { ExchangeCompareResult.OUTER -> {
reverse = true reverse = true
@@ -189,25 +195,27 @@ class VimExchangeExtension: VimExtension {
private fun exchange(editor: Editor, ex1: Exchange, ex2: Exchange, reverse: Boolean, expand: Boolean) { private fun exchange(editor: Editor, ex1: Exchange, ex2: Exchange, reverse: Boolean, expand: Boolean) {
fun pasteExchange(sourceExchange: Exchange, targetExchange: Exchange) { fun pasteExchange(sourceExchange: Exchange, targetExchange: Exchange) {
VimPlugin.getMark().setChangeMarks(editor, TextRange(editor.getMarkOffset(targetExchange.start), editor.getMarkOffset(targetExchange.end)+1)) VimPlugin.getMark().setChangeMarks(editor, TextRange(editor.getMarkOffset(targetExchange.start), editor.getMarkOffset(targetExchange.end) + 1))
// do this instead of direct text manipulation to set change marks // do this instead of direct text manipulation to set change marks
setRegister('z', stringToKeys(sourceExchange.text), SelectionType.fromSubMode(sourceExchange.type)) setRegister('z', stringToKeys(sourceExchange.text), SelectionType.fromSubMode(sourceExchange.type))
executeNormalWithoutMapping(stringToKeys("`[${targetExchange.type.getString()}`]\"zp"), editor) executeNormalWithoutMapping(stringToKeys("`[${targetExchange.type.getString()}`]\"zp"), editor)
} }
fun fixCursor(ex1: Exchange, ex2: Exchange, reverse: Boolean) { fun fixCursor(ex1: Exchange, ex2: Exchange, reverse: Boolean) {
val primaryCaret = editor.caretModel.primaryCaret val primaryCaret = editor.caretModel.primaryCaret
if(reverse) { if (reverse) {
primaryCaret.moveToInlayAwareOffset(editor.getMarkOffset(ex1.start)) primaryCaret.moveToInlayAwareOffset(editor.getMarkOffset(ex1.start))
} else { } else {
if (ex1.start.logicalLine == ex2.start.logicalLine) { if (ex1.start.logicalLine == ex2.start.logicalLine) {
val horizontalOffset = ex1.end.col - ex2.end.col val horizontalOffset = ex1.end.col - ex2.end.col
primaryCaret.moveToInlayAwareLogicalPosition(LogicalPosition(ex1.start.logicalLine, ex1.start.col - horizontalOffset)) primaryCaret.moveToInlayAwareLogicalPosition(LogicalPosition(ex1.start.logicalLine, ex1.start.col - horizontalOffset))
} else if(ex1.end.logicalLine - ex1.start.logicalLine != ex2.end.logicalLine - ex2.start.logicalLine) { } else if (ex1.end.logicalLine - ex1.start.logicalLine != ex2.end.logicalLine - ex2.start.logicalLine) {
val verticalOffset = ex1.end.logicalLine - ex2.end.logicalLine val verticalOffset = ex1.end.logicalLine - ex2.end.logicalLine
primaryCaret.moveToInlayAwareLogicalPosition(LogicalPosition(ex1.start.logicalLine - verticalOffset, ex1.start.col)) primaryCaret.moveToInlayAwareLogicalPosition(LogicalPosition(ex1.start.logicalLine - verticalOffset, ex1.start.col))
} }
} }
} }
val zRegText = getRegister('z') val zRegText = getRegister('z')
val unnRegText = getRegister('"') val unnRegText = getRegister('"')
val startRegText = getRegister('*') val startRegText = getRegister('*')
@@ -247,24 +255,24 @@ class VimExchangeExtension: VimExtension {
return if (x.type == CommandState.SubMode.VISUAL_BLOCK && y.type == CommandState.SubMode.VISUAL_BLOCK) { return if (x.type == CommandState.SubMode.VISUAL_BLOCK && y.type == CommandState.SubMode.VISUAL_BLOCK) {
when { when {
intersects(x, y) -> { intersects(x, y) -> {
ExchangeCompareResult.OVERLAP ExchangeCompareResult.OVERLAP
} }
x.start.col <= y.start.col -> { x.start.col <= y.start.col -> {
ExchangeCompareResult.LT ExchangeCompareResult.LT
} }
else -> { else -> {
ExchangeCompareResult.GT ExchangeCompareResult.GT
} }
} }
} else if (comparePos(x.start, y.start) <=0 && comparePos(x.end, y.end) >=0) { } else if (comparePos(x.start, y.start) <= 0 && comparePos(x.end, y.end) >= 0) {
ExchangeCompareResult.OUTER ExchangeCompareResult.OUTER
} else if (comparePos(y.start, x.start) <=0 && comparePos(y.end, x.end) >=0) { } else if (comparePos(y.start, x.start) <= 0 && comparePos(y.end, x.end) >= 0) {
ExchangeCompareResult.INNER ExchangeCompareResult.INNER
} else if (comparePos(x.start, y.end) <=0 && comparePos(y.start, x.end) <=0 || } else if (comparePos(x.start, y.end) <= 0 && comparePos(y.start, x.end) <= 0 ||
comparePos(y.start, x.end) <=0 && comparePos(x.start, y.end) <=0 comparePos(y.start, x.end) <= 0 && comparePos(x.start, y.end) <= 0
) { ) {
ExchangeCompareResult.OVERLAP ExchangeCompareResult.OVERLAP
} else { } else {
val cmp = comparePos(x.start, y.start) val cmp = comparePos(x.start, y.start)
when { when {
@@ -291,6 +299,7 @@ class VimExchangeExtension: VimExtension {
selectionEnd.col selectionEnd.col
} }
} }
// TODO: improve KeyStroke list to sting conversion // TODO: improve KeyStroke list to sting conversion
fun getRegisterText(reg: Char): String = getRegister(reg)?.map { it.keyChar }?.joinToString("") ?: "" fun getRegisterText(reg: Char): String = getRegister(reg)?.map { it.keyChar }?.joinToString("") ?: ""
fun getMarks(isVisual: Boolean): Pair<Mark, Mark> { fun getMarks(isVisual: Boolean): Pair<Mark, Mark> {

View File

@@ -18,6 +18,8 @@
package com.maddyhome.idea.vim.extension.highlightedyank package com.maddyhome.idea.vim.extension.highlightedyank
import com.intellij.ide.ui.LafManager
import com.intellij.ide.ui.LafManagerListener
import com.intellij.openapi.Disposable import com.intellij.openapi.Disposable
import com.intellij.openapi.application.ApplicationManager import com.intellij.openapi.application.ApplicationManager
import com.intellij.openapi.editor.Editor import com.intellij.openapi.editor.Editor
@@ -44,8 +46,19 @@ import java.util.concurrent.TimeUnit
const val DEFAULT_HIGHLIGHT_DURATION: Long = 300 const val DEFAULT_HIGHLIGHT_DURATION: Long = 300
private const val HIGHLIGHT_DURATION_VARIABLE_NAME = "g:highlightedyank_highlight_duration" private const val HIGHLIGHT_DURATION_VARIABLE_NAME = "g:highlightedyank_highlight_duration"
private const val HIGHLIGHT_COLOR_VARIABLE_NAME = "g:highlightedyank_highlight_color" private const val HIGHLIGHT_COLOR_VARIABLE_NAME = "g:highlightedyank_highlight_color"
private val DEFAULT_HIGHLIGHT_TEXT_COLOR: Color = EditorColors.TEXT_SEARCH_RESULT_ATTRIBUTES.defaultAttributes.backgroundColor private var defaultHighlightTextColor: Color? = null
private fun getDefaultHighlightTextColor(): Color {
return defaultHighlightTextColor
?: return EditorColors.TEXT_SEARCH_RESULT_ATTRIBUTES.defaultAttributes.backgroundColor
.also { defaultHighlightTextColor = it }
}
class HighlightColorResetter : LafManagerListener {
override fun lookAndFeelChanged(source: LafManager) {
defaultHighlightTextColor = null
}
}
/** /**
* @author KostkaBrukowa (@kostkabrukowa) * @author KostkaBrukowa (@kostkabrukowa)
@@ -164,7 +177,7 @@ class VimHighlightedYank: VimExtension, VimYankListener, VimInsertListener {
} }
private fun extractUsersHighlightColor(): Color { private fun extractUsersHighlightColor(): Color {
return extractVariable(HIGHLIGHT_COLOR_VARIABLE_NAME, DEFAULT_HIGHLIGHT_TEXT_COLOR) { value -> return extractVariable(HIGHLIGHT_COLOR_VARIABLE_NAME, getDefaultHighlightTextColor()) { value ->
val rgba = value val rgba = value
.substring(4) .substring(4)
.filter { it != '(' && it != ')' && !it.isWhitespace() } .filter { it != '(' && it != ')' && !it.isWhitespace() }

View File

@@ -57,6 +57,7 @@ private const val ALL_OCCURRENCES = "<Plug>AllOccurrences"
* See https://github.com/terryma/vim-multiple-cursors * See https://github.com/terryma/vim-multiple-cursors
* */ * */
class VimMultipleCursorsExtension : VimExtension { class VimMultipleCursorsExtension : VimExtension {
override fun getName() = "multiple-cursors" override fun getName() = "multiple-cursors"
override fun init() { override fun init() {

View File

@@ -34,7 +34,6 @@ import com.maddyhome.idea.vim.extension.VimExtensionFacade.putKeyMapping
import com.maddyhome.idea.vim.extension.VimExtensionFacade.setOperatorFunction import com.maddyhome.idea.vim.extension.VimExtensionFacade.setOperatorFunction
import com.maddyhome.idea.vim.extension.VimExtensionHandler import com.maddyhome.idea.vim.extension.VimExtensionHandler
import com.maddyhome.idea.vim.group.MotionGroup import com.maddyhome.idea.vim.group.MotionGroup
import com.maddyhome.idea.vim.group.RegisterGroup
import com.maddyhome.idea.vim.group.copy.PutData import com.maddyhome.idea.vim.group.copy.PutData
import com.maddyhome.idea.vim.group.visual.VimSelection import com.maddyhome.idea.vim.group.visual.VimSelection
import com.maddyhome.idea.vim.helper.EditorDataContext import com.maddyhome.idea.vim.helper.EditorDataContext
@@ -46,6 +45,7 @@ import com.maddyhome.idea.vim.key.OperatorFunction
class ReplaceWithRegister : VimExtension { class ReplaceWithRegister : VimExtension {
override fun getName(): String = "ReplaceWithRegister" override fun getName(): String = "ReplaceWithRegister"
override fun init() { override fun init() {
@@ -140,11 +140,11 @@ class ReplaceWithRegister : VimExtension {
val textData = PutData.TextData(usedText, usedType, savedRegister.transferableData) val textData = PutData.TextData(usedText, usedType, savedRegister.transferableData)
val putData = PutData(textData, visualSelection, 1, insertTextBeforeCaret = true, _indent = true, caretAfterInsertedText = false, putToLine = -1) val putData = PutData(textData, visualSelection, 1, insertTextBeforeCaret = true, rawIndent = true, caretAfterInsertedText = false, putToLine = -1)
VimPlugin.getPut().putText(editor, EditorDataContext(editor), putData) VimPlugin.getPut().putText(editor, EditorDataContext(editor), putData)
VimPlugin.getRegister().saveRegister(savedRegister.name, savedRegister) VimPlugin.getRegister().saveRegister(savedRegister.name, savedRegister)
VimPlugin.getRegister().saveRegister(RegisterGroup.DEFAULT_REGISTER, savedRegister) VimPlugin.getRegister().saveRegister(VimPlugin.getRegister().defaultRegister, savedRegister)
} }
} }
} }

View File

@@ -52,6 +52,7 @@ import javax.swing.KeyStroke
* @author vlan * @author vlan
*/ */
class VimSurroundExtension : VimExtension { class VimSurroundExtension : VimExtension {
override fun getName() = "surround" override fun getName() = "surround"
override fun init() { override fun init() {

View File

@@ -61,12 +61,14 @@ import static com.maddyhome.idea.vim.helper.StringHelper.parseKeys;
* @author Alexandre Grison (@agrison) * @author Alexandre Grison (@agrison)
*/ */
public class VimTextObjEntireExtension implements VimExtension { public class VimTextObjEntireExtension implements VimExtension {
@Override @Override
public @NotNull public @NotNull
String getName() { String getName() {
return "textobj-entire"; return "textobj-entire";
} }
@Override @Override
public void init() { public void init() {
putExtensionHandlerMapping(MappingMode.XO, parseKeys("<Plug>textobj-entire-a"), getOwner(), putExtensionHandlerMapping(MappingMode.XO, parseKeys("<Plug>textobj-entire-a"), getOwner(),

View File

@@ -636,7 +636,9 @@ public class ChangeGroup {
repeatInsertText(editor, context, started ? (i == 0 ? count : count + 1) : count); repeatInsertText(editor, context, started ? (i == 0 ? count : count + 1) : count);
} }
else if (EditorHelper.getVisualLineLength(editor, visualLine + i) >= repeatColumn) { else if (EditorHelper.getVisualLineLength(editor, visualLine + i) >= repeatColumn) {
caret.moveToVisualPosition(new VisualPosition(visualLine + i, repeatColumn)); VisualPosition visualPosition = new VisualPosition(visualLine + i, repeatColumn);
int inlaysCount = InlayHelperKt.amountOfInlaysBeforeVisualPosition(editor, visualPosition);
caret.moveToVisualPosition(new VisualPosition(visualLine + i, repeatColumn + inlaysCount));
repeatInsertText(editor, context, started ? (i == 0 ? count : count + 1) : count); repeatInsertText(editor, context, started ? (i == 0 ? count : count + 1) : count);
} }
} }
@@ -768,9 +770,10 @@ public class ChangeGroup {
public boolean deleteEndOfLine(@NotNull Editor editor, @NotNull Caret caret, int count) { public boolean deleteEndOfLine(@NotNull Editor editor, @NotNull Caret caret, int count) {
int initialOffset = caret.getOffset(); int initialOffset = caret.getOffset();
int offset = VimPlugin.getMotion().moveCaretToLineEndOffset(editor, caret, count - 1, true); int offset = VimPlugin.getMotion().moveCaretToLineEndOffset(editor, caret, count - 1, true);
int lineStart = VimPlugin.getMotion().moveCaretToLineStart(editor, caret);
int startOffset = initialOffset; int startOffset = initialOffset;
if (offset == initialOffset) startOffset--; // handle delete from virtual space if (offset == initialOffset && offset != lineStart) startOffset--; // handle delete from virtual space
if (offset != -1) { if (offset != -1) {
final TextRange rangeToDelete = new TextRange(startOffset, offset); final TextRange rangeToDelete = new TextRange(startOffset, offset);
@@ -1251,10 +1254,9 @@ public class ChangeGroup {
} }
if (kludge) { if (kludge) {
int size = fileSize;
int cnt = count * motion.getCount(); int cnt = count * motion.getCount();
int pos1 = SearchHelper.findNextWordEnd(chars, offset, size, cnt, bigWord, false); int pos1 = SearchHelper.findNextWordEnd(chars, offset, fileSize, cnt, bigWord, false);
int pos2 = SearchHelper.findNextWordEnd(chars, pos1, size, -cnt, bigWord, false); int pos2 = SearchHelper.findNextWordEnd(chars, pos1, fileSize, -cnt, bigWord, false);
if (logger.isDebugEnabled()) { if (logger.isDebugEnabled()) {
logger.debug("pos=" + offset); logger.debug("pos=" + offset);
logger.debug("pos1=" + pos1); logger.debug("pos1=" + pos1);
@@ -1770,7 +1772,7 @@ public class ChangeGroup {
} }
private static void resetCaret(@NotNull VirtualFile virtualFile, Project proj, boolean insert) { private static void resetCaret(@NotNull VirtualFile virtualFile, Project proj, boolean insert) {
logger.info("Reset caret to a " + (insert ? "non-block" : "block") + " shape"); logger.debug("Reset caret to a " + (insert ? "non-block" : "block") + " shape");
Document doc = FileDocumentManager.getInstance().getDocument(virtualFile); Document doc = FileDocumentManager.getInstance().getDocument(virtualFile);
if (doc == null) return; // Must be no text editor (such as image) if (doc == null) return; // Must be no text editor (such as image)
Editor[] editors = EditorFactory.getInstance().getEditors(doc, proj); Editor[] editors = EditorFactory.getInstance().getEditors(doc, proj);
@@ -1975,7 +1977,7 @@ public class ChangeGroup {
if (!Character.isLetter(ch)) throw new RuntimeException("Not alpha number : " + text); if (!Character.isLetter(ch)) throw new RuntimeException("Not alpha number : " + text);
ch += count; ch += count;
if (Character.isLetter(ch)) { if (Character.isLetter(ch)) {
number = "" + ch; number = String.valueOf(ch);
} }
} }
else if (SearchHelper.NumberType.DEC.equals(numberType)) { else if (SearchHelper.NumberType.DEC.equals(numberType)) {

Some files were not shown because too many files have changed in this diff Show More