895cfe968dc807722ecf1616e1e91811c7881f949ab5be01ebe83c841f1fae5b569629e2f0192ff05955dda4bbbd7dbf7498d46575f1563e709ff634bc6c6b 6.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146
  1. /*---------------------------------------------------------------------------------------------
  2. * Copyright (c) Microsoft Corporation. All rights reserved.
  3. * Licensed under the MIT License. See License.txt in the project root for license information.
  4. *--------------------------------------------------------------------------------------------*/
  5. import { KeyChord } from '../../../../base/common/keyCodes.js';
  6. import { EditorAction, registerEditorAction } from '../../../browser/editorExtensions.js';
  7. import { Range } from '../../../common/core/range.js';
  8. import { EditorContextKeys } from '../../../common/editorContextKeys.js';
  9. import { ILanguageConfigurationService } from '../../../common/languages/languageConfigurationRegistry.js';
  10. import { BlockCommentCommand } from './blockCommentCommand.js';
  11. import { LineCommentCommand } from './lineCommentCommand.js';
  12. import * as nls from '../../../../nls.js';
  13. import { MenuId } from '../../../../platform/actions/common/actions.js';
  14. class CommentLineAction extends EditorAction {
  15. constructor(type, opts) {
  16. super(opts);
  17. this._type = type;
  18. }
  19. run(accessor, editor) {
  20. const languageConfigurationService = accessor.get(ILanguageConfigurationService);
  21. if (!editor.hasModel()) {
  22. return;
  23. }
  24. const model = editor.getModel();
  25. const commands = [];
  26. const modelOptions = model.getOptions();
  27. const commentsOptions = editor.getOption(19 /* EditorOption.comments */);
  28. const selections = editor.getSelections().map((selection, index) => ({ selection, index, ignoreFirstLine: false }));
  29. selections.sort((a, b) => Range.compareRangesUsingStarts(a.selection, b.selection));
  30. // Remove selections that would result in copying the same line
  31. let prev = selections[0];
  32. for (let i = 1; i < selections.length; i++) {
  33. const curr = selections[i];
  34. if (prev.selection.endLineNumber === curr.selection.startLineNumber) {
  35. // these two selections would copy the same line
  36. if (prev.index < curr.index) {
  37. // prev wins
  38. curr.ignoreFirstLine = true;
  39. }
  40. else {
  41. // curr wins
  42. prev.ignoreFirstLine = true;
  43. prev = curr;
  44. }
  45. }
  46. }
  47. for (const selection of selections) {
  48. commands.push(new LineCommentCommand(languageConfigurationService, selection.selection, modelOptions.tabSize, this._type, commentsOptions.insertSpace, commentsOptions.ignoreEmptyLines, selection.ignoreFirstLine));
  49. }
  50. editor.pushUndoStop();
  51. editor.executeCommands(this.id, commands);
  52. editor.pushUndoStop();
  53. }
  54. }
  55. class ToggleCommentLineAction extends CommentLineAction {
  56. constructor() {
  57. super(0 /* Type.Toggle */, {
  58. id: 'editor.action.commentLine',
  59. label: nls.localize('comment.line', "Toggle Line Comment"),
  60. alias: 'Toggle Line Comment',
  61. precondition: EditorContextKeys.writable,
  62. kbOpts: {
  63. kbExpr: EditorContextKeys.editorTextFocus,
  64. primary: 2048 /* KeyMod.CtrlCmd */ | 85 /* KeyCode.Slash */,
  65. weight: 100 /* KeybindingWeight.EditorContrib */
  66. },
  67. menuOpts: {
  68. menuId: MenuId.MenubarEditMenu,
  69. group: '5_insert',
  70. title: nls.localize({ key: 'miToggleLineComment', comment: ['&& denotes a mnemonic'] }, "&&Toggle Line Comment"),
  71. order: 1
  72. }
  73. });
  74. }
  75. }
  76. class AddLineCommentAction extends CommentLineAction {
  77. constructor() {
  78. super(1 /* Type.ForceAdd */, {
  79. id: 'editor.action.addCommentLine',
  80. label: nls.localize('comment.line.add', "Add Line Comment"),
  81. alias: 'Add Line Comment',
  82. precondition: EditorContextKeys.writable,
  83. kbOpts: {
  84. kbExpr: EditorContextKeys.editorTextFocus,
  85. primary: KeyChord(2048 /* KeyMod.CtrlCmd */ | 41 /* KeyCode.KeyK */, 2048 /* KeyMod.CtrlCmd */ | 33 /* KeyCode.KeyC */),
  86. weight: 100 /* KeybindingWeight.EditorContrib */
  87. }
  88. });
  89. }
  90. }
  91. class RemoveLineCommentAction extends CommentLineAction {
  92. constructor() {
  93. super(2 /* Type.ForceRemove */, {
  94. id: 'editor.action.removeCommentLine',
  95. label: nls.localize('comment.line.remove', "Remove Line Comment"),
  96. alias: 'Remove Line Comment',
  97. precondition: EditorContextKeys.writable,
  98. kbOpts: {
  99. kbExpr: EditorContextKeys.editorTextFocus,
  100. primary: KeyChord(2048 /* KeyMod.CtrlCmd */ | 41 /* KeyCode.KeyK */, 2048 /* KeyMod.CtrlCmd */ | 51 /* KeyCode.KeyU */),
  101. weight: 100 /* KeybindingWeight.EditorContrib */
  102. }
  103. });
  104. }
  105. }
  106. class BlockCommentAction extends EditorAction {
  107. constructor() {
  108. super({
  109. id: 'editor.action.blockComment',
  110. label: nls.localize('comment.block', "Toggle Block Comment"),
  111. alias: 'Toggle Block Comment',
  112. precondition: EditorContextKeys.writable,
  113. kbOpts: {
  114. kbExpr: EditorContextKeys.editorTextFocus,
  115. primary: 1024 /* KeyMod.Shift */ | 512 /* KeyMod.Alt */ | 31 /* KeyCode.KeyA */,
  116. linux: { primary: 2048 /* KeyMod.CtrlCmd */ | 1024 /* KeyMod.Shift */ | 31 /* KeyCode.KeyA */ },
  117. weight: 100 /* KeybindingWeight.EditorContrib */
  118. },
  119. menuOpts: {
  120. menuId: MenuId.MenubarEditMenu,
  121. group: '5_insert',
  122. title: nls.localize({ key: 'miToggleBlockComment', comment: ['&& denotes a mnemonic'] }, "Toggle &&Block Comment"),
  123. order: 2
  124. }
  125. });
  126. }
  127. run(accessor, editor) {
  128. const languageConfigurationService = accessor.get(ILanguageConfigurationService);
  129. if (!editor.hasModel()) {
  130. return;
  131. }
  132. const commentsOptions = editor.getOption(19 /* EditorOption.comments */);
  133. const commands = [];
  134. const selections = editor.getSelections();
  135. for (const selection of selections) {
  136. commands.push(new BlockCommentCommand(selection, commentsOptions.insertSpace, languageConfigurationService));
  137. }
  138. editor.pushUndoStop();
  139. editor.executeCommands(this.id, commands);
  140. editor.pushUndoStop();
  141. }
  142. }
  143. registerEditorAction(ToggleCommentLineAction);
  144. registerEditorAction(AddLineCommentAction);
  145. registerEditorAction(RemoveLineCommentAction);
  146. registerEditorAction(BlockCommentAction);