2017-09-10 17:25:29 +05:30
|
|
|
<script>
|
2023-07-09 08:55:56 +05:30
|
|
|
import { GlPopover, GlButton, GlTooltipDirective } from '@gitlab/ui';
|
2021-03-11 19:13:27 +05:30
|
|
|
import $ from 'jquery';
|
2022-05-07 20:08:51 +05:30
|
|
|
import {
|
|
|
|
keysFor,
|
|
|
|
BOLD_TEXT,
|
|
|
|
ITALIC_TEXT,
|
|
|
|
STRIKETHROUGH_TEXT,
|
|
|
|
LINK_TEXT,
|
2022-11-25 23:54:43 +05:30
|
|
|
INDENT_LINE,
|
|
|
|
OUTDENT_LINE,
|
2022-05-07 20:08:51 +05:30
|
|
|
} from '~/behaviors/shortcuts/keybindings';
|
2023-05-27 22:25:52 +05:30
|
|
|
import glFeatureFlagsMixin from '~/vue_shared/mixins/gl_feature_flags_mixin';
|
2023-03-17 16:20:25 +05:30
|
|
|
import { getModifierKey } from '~/constants';
|
2020-10-24 23:57:45 +05:30
|
|
|
import { getSelectedFragment } from '~/lib/utils/common_utils';
|
2022-04-04 11:22:00 +05:30
|
|
|
import { s__, __ } from '~/locale';
|
2022-06-21 17:19:12 +05:30
|
|
|
import { CopyAsGFM } from '~/behaviors/markdown/copy_as_gfm';
|
2023-07-09 08:55:56 +05:30
|
|
|
import { updateText } from '~/lib/utils/text_markdown';
|
2018-12-13 13:39:08 +05:30
|
|
|
import ToolbarButton from './toolbar_button.vue';
|
2023-05-27 22:25:52 +05:30
|
|
|
import DrawioToolbarButton from './drawio_toolbar_button.vue';
|
2023-06-20 00:43:36 +05:30
|
|
|
import CommentTemplatesDropdown from './comment_templates_dropdown.vue';
|
2023-07-09 08:55:56 +05:30
|
|
|
import EditorModeSwitcher from './editor_mode_switcher.vue';
|
2017-09-10 17:25:29 +05:30
|
|
|
|
2018-12-13 13:39:08 +05:30
|
|
|
export default {
|
|
|
|
components: {
|
|
|
|
ToolbarButton,
|
2019-09-04 21:01:54 +05:30
|
|
|
GlPopover,
|
2020-10-24 23:57:45 +05:30
|
|
|
GlButton,
|
2023-05-27 22:25:52 +05:30
|
|
|
DrawioToolbarButton,
|
2023-06-20 00:43:36 +05:30
|
|
|
CommentTemplatesDropdown,
|
2023-07-09 08:55:56 +05:30
|
|
|
AiActionsDropdown: () => import('ee_component/ai/components/ai_actions_dropdown.vue'),
|
|
|
|
EditorModeSwitcher,
|
2018-12-13 13:39:08 +05:30
|
|
|
},
|
|
|
|
directives: {
|
|
|
|
GlTooltip: GlTooltipDirective,
|
|
|
|
},
|
2023-05-27 22:25:52 +05:30
|
|
|
mixins: [glFeatureFlagsMixin()],
|
|
|
|
inject: {
|
2023-06-20 00:43:36 +05:30
|
|
|
newCommentTemplatePath: {
|
2023-05-27 22:25:52 +05:30
|
|
|
default: null,
|
|
|
|
},
|
2023-07-09 08:55:56 +05:30
|
|
|
editorAiActions: { default: () => [] },
|
2023-05-27 22:25:52 +05:30
|
|
|
},
|
2018-12-13 13:39:08 +05:30
|
|
|
props: {
|
|
|
|
previewMarkdown: {
|
|
|
|
type: Boolean,
|
|
|
|
required: true,
|
2017-09-10 17:25:29 +05:30
|
|
|
},
|
2019-02-15 15:39:39 +05:30
|
|
|
lineContent: {
|
|
|
|
type: String,
|
|
|
|
required: false,
|
|
|
|
default: '',
|
|
|
|
},
|
|
|
|
canSuggest: {
|
|
|
|
type: Boolean,
|
|
|
|
required: false,
|
|
|
|
default: true,
|
|
|
|
},
|
2019-09-04 21:01:54 +05:30
|
|
|
showSuggestPopover: {
|
|
|
|
type: Boolean,
|
|
|
|
required: false,
|
|
|
|
default: false,
|
|
|
|
},
|
2021-04-29 21:17:54 +05:30
|
|
|
suggestionStartIndex: {
|
|
|
|
type: Number,
|
|
|
|
required: false,
|
|
|
|
default: 0,
|
|
|
|
},
|
2022-05-07 20:08:51 +05:30
|
|
|
enablePreview: {
|
|
|
|
type: Boolean,
|
|
|
|
required: false,
|
|
|
|
default: true,
|
|
|
|
},
|
2022-07-16 23:28:13 +05:30
|
|
|
restrictedToolBarItems: {
|
|
|
|
type: Array,
|
|
|
|
required: false,
|
|
|
|
default: () => [],
|
|
|
|
},
|
2023-05-27 22:25:52 +05:30
|
|
|
uploadsPath: {
|
|
|
|
type: String,
|
|
|
|
required: false,
|
|
|
|
default: '',
|
|
|
|
},
|
|
|
|
markdownPreviewPath: {
|
|
|
|
type: String,
|
|
|
|
required: false,
|
|
|
|
default: '',
|
|
|
|
},
|
|
|
|
drawioEnabled: {
|
|
|
|
type: Boolean,
|
|
|
|
required: false,
|
|
|
|
default: false,
|
|
|
|
},
|
2023-07-09 08:55:56 +05:30
|
|
|
showContentEditorSwitcher: {
|
|
|
|
type: Boolean,
|
|
|
|
required: false,
|
|
|
|
default: false,
|
|
|
|
},
|
2018-12-13 13:39:08 +05:30
|
|
|
},
|
2020-10-24 23:57:45 +05:30
|
|
|
data() {
|
|
|
|
return {
|
|
|
|
tag: '> ',
|
2021-10-27 15:23:28 +05:30
|
|
|
suggestPopoverVisible: false,
|
2023-03-17 16:20:25 +05:30
|
|
|
modifierKey: getModifierKey(),
|
2020-10-24 23:57:45 +05:30
|
|
|
};
|
|
|
|
},
|
2018-12-13 13:39:08 +05:30
|
|
|
computed: {
|
|
|
|
mdTable() {
|
2022-11-25 23:54:43 +05:30
|
|
|
const header = s__('MarkdownEditor|header');
|
|
|
|
const divider = '-'.repeat(header.length);
|
|
|
|
const cell = ' '.repeat(header.length);
|
|
|
|
|
2018-12-13 13:39:08 +05:30
|
|
|
return [
|
2022-11-25 23:54:43 +05:30
|
|
|
`| ${header} | ${header} |`,
|
|
|
|
`| ${divider} | ${divider} |`,
|
|
|
|
`| ${cell} | ${cell} |`,
|
|
|
|
`| ${cell} | ${cell} |`,
|
2018-12-13 13:39:08 +05:30
|
|
|
].join('\n');
|
2017-09-10 17:25:29 +05:30
|
|
|
},
|
2019-02-15 15:39:39 +05:30
|
|
|
mdSuggestion() {
|
2021-04-29 21:17:54 +05:30
|
|
|
return [['```', `suggestion:-${this.suggestionStartIndex}+0`].join(''), `{text}`, '```'].join(
|
|
|
|
'\n',
|
|
|
|
);
|
2019-02-15 15:39:39 +05:30
|
|
|
},
|
2021-06-08 01:23:25 +05:30
|
|
|
mdCollapsibleSection() {
|
2022-11-25 23:54:43 +05:30
|
|
|
const expandText = s__('MarkdownEditor|Click to expand');
|
|
|
|
return [`<details><summary>${expandText}</summary>`, `{text}`, '</details>'].join('\n');
|
2021-06-08 01:23:25 +05:30
|
|
|
},
|
2023-07-09 08:55:56 +05:30
|
|
|
showEditorModeSwitcher() {
|
|
|
|
return this.showContentEditorSwitcher && !this.previewMarkdown;
|
2023-06-20 00:43:36 +05:30
|
|
|
},
|
2018-12-13 13:39:08 +05:30
|
|
|
},
|
2021-10-27 15:23:28 +05:30
|
|
|
watch: {
|
|
|
|
showSuggestPopover() {
|
|
|
|
this.updateSuggestPopoverVisibility();
|
|
|
|
},
|
|
|
|
},
|
2018-12-13 13:39:08 +05:30
|
|
|
mounted() {
|
2023-07-09 08:55:56 +05:30
|
|
|
$(document).on('markdown-preview:show.vue', this.showMarkdownPreview);
|
|
|
|
$(document).on('markdown-preview:hide.vue', this.hideMarkdownPreview);
|
2021-10-27 15:23:28 +05:30
|
|
|
|
|
|
|
this.updateSuggestPopoverVisibility();
|
2018-12-13 13:39:08 +05:30
|
|
|
},
|
|
|
|
beforeDestroy() {
|
2023-07-09 08:55:56 +05:30
|
|
|
$(document).off('markdown-preview:show.vue', this.showMarkdownPreview);
|
|
|
|
$(document).off('markdown-preview:hide.vue', this.hideMarkdownPreview);
|
2018-12-13 13:39:08 +05:30
|
|
|
},
|
|
|
|
methods: {
|
2021-10-27 15:23:28 +05:30
|
|
|
async updateSuggestPopoverVisibility() {
|
|
|
|
await this.$nextTick();
|
|
|
|
|
|
|
|
this.suggestPopoverVisible = this.showSuggestPopover && this.canSuggest;
|
|
|
|
},
|
2018-12-13 13:39:08 +05:30
|
|
|
isValid(form) {
|
|
|
|
return (
|
|
|
|
!form ||
|
|
|
|
(form.find('.js-vue-markdown-field').length && $(this.$el).closest('form')[0] === form[0])
|
|
|
|
);
|
2017-09-10 17:25:29 +05:30
|
|
|
},
|
2023-07-09 08:55:56 +05:30
|
|
|
showMarkdownPreview(_, form) {
|
2018-12-13 13:39:08 +05:30
|
|
|
if (!this.isValid(form)) return;
|
2018-03-17 18:26:18 +05:30
|
|
|
|
2023-07-09 08:55:56 +05:30
|
|
|
this.$emit('showPreview');
|
2018-12-13 13:39:08 +05:30
|
|
|
},
|
2023-07-09 08:55:56 +05:30
|
|
|
hideMarkdownPreview(_, form) {
|
2018-12-13 13:39:08 +05:30
|
|
|
if (!this.isValid(form)) return;
|
2018-03-17 18:26:18 +05:30
|
|
|
|
2023-07-09 08:55:56 +05:30
|
|
|
this.$emit('hidePreview');
|
2017-09-10 17:25:29 +05:30
|
|
|
},
|
2019-09-04 21:01:54 +05:30
|
|
|
handleSuggestDismissed() {
|
|
|
|
this.$emit('handleSuggestDismissed');
|
|
|
|
},
|
2020-10-24 23:57:45 +05:30
|
|
|
handleQuote() {
|
|
|
|
const documentFragment = getSelectedFragment();
|
|
|
|
|
|
|
|
if (!documentFragment || !documentFragment.textContent) {
|
|
|
|
this.tag = '> ';
|
|
|
|
return;
|
|
|
|
}
|
|
|
|
this.tag = '';
|
|
|
|
|
|
|
|
const transformed = CopyAsGFM.transformGFMSelection(documentFragment);
|
|
|
|
const area = this.$el.parentNode.querySelector('textarea');
|
|
|
|
|
|
|
|
CopyAsGFM.nodeToGFM(transformed)
|
2021-03-08 18:12:59 +05:30
|
|
|
.then((gfm) => {
|
2020-10-24 23:57:45 +05:30
|
|
|
CopyAsGFM.insertPastedText(area, documentFragment.textContent, CopyAsGFM.quoted(gfm));
|
|
|
|
})
|
|
|
|
.catch(() => {});
|
|
|
|
},
|
2022-08-27 11:52:29 +05:30
|
|
|
handleAttachFile(e) {
|
|
|
|
e.preventDefault();
|
|
|
|
const $gfmForm = $(this.$el).closest('.gfm-form');
|
|
|
|
const $gfmTextarea = $gfmForm.find('.js-gfm-input');
|
|
|
|
|
|
|
|
$gfmForm.find('.div-dropzone').click();
|
|
|
|
$gfmTextarea.focus();
|
|
|
|
},
|
2023-07-09 08:55:56 +05:30
|
|
|
insertIntoTextarea(text) {
|
|
|
|
const textArea = this.$el.closest('.md-area')?.querySelector('textarea');
|
|
|
|
if (textArea) {
|
|
|
|
const generatedByText = `${text}\n\n---\n\n_${__('This comment was generated using AI')}_`;
|
|
|
|
updateText({
|
|
|
|
textArea,
|
|
|
|
tag: generatedByText,
|
|
|
|
cursorOffset: 0,
|
|
|
|
wrap: false,
|
|
|
|
});
|
|
|
|
}
|
|
|
|
},
|
|
|
|
handleEditorModeChanged() {
|
|
|
|
this.$emit('enableContentEditor');
|
|
|
|
},
|
|
|
|
switchPreview() {
|
|
|
|
if (this.previewMarkdown) {
|
|
|
|
this.hideMarkdownPreview();
|
|
|
|
} else {
|
|
|
|
this.showMarkdownPreview();
|
|
|
|
}
|
|
|
|
},
|
2018-12-13 13:39:08 +05:30
|
|
|
},
|
2021-04-29 21:17:54 +05:30
|
|
|
shortcuts: {
|
|
|
|
bold: keysFor(BOLD_TEXT),
|
|
|
|
italic: keysFor(ITALIC_TEXT),
|
2022-05-07 20:08:51 +05:30
|
|
|
strikethrough: keysFor(STRIKETHROUGH_TEXT),
|
2021-04-29 21:17:54 +05:30
|
|
|
link: keysFor(LINK_TEXT),
|
2022-11-25 23:54:43 +05:30
|
|
|
indent: keysFor(INDENT_LINE),
|
|
|
|
outdent: keysFor(OUTDENT_LINE),
|
2021-04-29 21:17:54 +05:30
|
|
|
},
|
2022-04-04 11:22:00 +05:30
|
|
|
i18n: {
|
2023-07-09 08:55:56 +05:30
|
|
|
preview: __('Preview'),
|
|
|
|
hidePreview: __('Continue editing'),
|
2022-04-04 11:22:00 +05:30
|
|
|
},
|
2018-12-13 13:39:08 +05:30
|
|
|
};
|
2017-09-10 17:25:29 +05:30
|
|
|
</script>
|
|
|
|
|
|
|
|
<template>
|
2023-07-09 08:55:56 +05:30
|
|
|
<div class="md-header gl-bg-gray-50 gl-px-2 gl-rounded-base gl-mx-2 gl-mt-2">
|
|
|
|
<div
|
|
|
|
class="gl-display-flex gl-align-items-center gl-flex-wrap"
|
|
|
|
:class="{
|
|
|
|
'gl-justify-content-end': previewMarkdown,
|
|
|
|
'gl-justify-content-space-between': !previewMarkdown,
|
|
|
|
}"
|
|
|
|
>
|
|
|
|
<div
|
|
|
|
data-testid="md-header-toolbar"
|
|
|
|
class="md-header-toolbar gl-display-flex gl-py-2 gl-flex-wrap"
|
|
|
|
:class="{ 'gl-display-none!': previewMarkdown }"
|
|
|
|
>
|
|
|
|
<template v-if="canSuggest">
|
2022-04-04 11:22:00 +05:30
|
|
|
<toolbar-button
|
2023-07-09 08:55:56 +05:30
|
|
|
ref="suggestButton"
|
|
|
|
:tag="mdSuggestion"
|
2022-04-04 11:22:00 +05:30
|
|
|
:prepend="true"
|
2023-07-09 08:55:56 +05:30
|
|
|
:button-title="__('Insert suggestion')"
|
|
|
|
:cursor-offset="4"
|
|
|
|
:tag-content="lineContent"
|
|
|
|
icon="doc-code"
|
|
|
|
data-qa-selector="suggestion_button"
|
|
|
|
class="js-suggestion-btn"
|
|
|
|
@click="handleSuggestDismissed"
|
2022-04-04 11:22:00 +05:30
|
|
|
/>
|
2023-07-09 08:55:56 +05:30
|
|
|
<gl-popover
|
|
|
|
v-if="suggestPopoverVisible"
|
|
|
|
:target="$refs.suggestButton.$el"
|
|
|
|
:css-classes="['diff-suggest-popover']"
|
|
|
|
placement="bottom"
|
|
|
|
:show="suggestPopoverVisible"
|
|
|
|
>
|
|
|
|
<strong>{{ __('New! Suggest changes directly') }}</strong>
|
|
|
|
<p class="mb-2">
|
|
|
|
{{
|
|
|
|
__(
|
|
|
|
'Suggest code changes which can be immediately applied in one click. Try it out!',
|
|
|
|
)
|
|
|
|
}}
|
|
|
|
</p>
|
|
|
|
<gl-button
|
|
|
|
variant="confirm"
|
|
|
|
category="primary"
|
|
|
|
size="small"
|
|
|
|
data-qa-selector="dismiss_suggestion_popover_button"
|
|
|
|
@click="handleSuggestDismissed"
|
|
|
|
>
|
|
|
|
{{ __('Got it') }}
|
|
|
|
</gl-button>
|
|
|
|
</gl-popover>
|
|
|
|
</template>
|
|
|
|
<ai-actions-dropdown
|
|
|
|
v-if="editorAiActions.length"
|
|
|
|
:actions="editorAiActions"
|
|
|
|
@input="insertIntoTextarea"
|
|
|
|
/>
|
|
|
|
<toolbar-button
|
|
|
|
tag="**"
|
|
|
|
:button-title="
|
|
|
|
/* eslint-disable @gitlab/vue-no-new-non-primitive-in-template */
|
|
|
|
sprintf(s__('MarkdownEditor|Add bold text (%{modifierKey}B)'), {
|
|
|
|
modifierKey,
|
|
|
|
}) /* eslint-enable @gitlab/vue-no-new-non-primitive-in-template */
|
|
|
|
"
|
|
|
|
:shortcuts="$options.shortcuts.bold"
|
|
|
|
icon="bold"
|
|
|
|
/>
|
|
|
|
<toolbar-button
|
|
|
|
tag="_"
|
|
|
|
:button-title="
|
|
|
|
/* eslint-disable @gitlab/vue-no-new-non-primitive-in-template */
|
|
|
|
sprintf(s__('MarkdownEditor|Add italic text (%{modifierKey}I)'), {
|
|
|
|
modifierKey,
|
|
|
|
}) /* eslint-enable @gitlab/vue-no-new-non-primitive-in-template */
|
|
|
|
"
|
|
|
|
:shortcuts="$options.shortcuts.italic"
|
|
|
|
icon="italic"
|
|
|
|
/>
|
|
|
|
<toolbar-button
|
|
|
|
v-if="!restrictedToolBarItems.includes('strikethrough')"
|
|
|
|
tag="~~"
|
|
|
|
:button-title="
|
|
|
|
/* eslint-disable @gitlab/vue-no-new-non-primitive-in-template */
|
|
|
|
sprintf(s__('MarkdownEditor|Add strikethrough text (%{modifierKey}⇧X)'), {
|
|
|
|
modifierKey /* eslint-enable @gitlab/vue-no-new-non-primitive-in-template */,
|
|
|
|
})
|
|
|
|
"
|
|
|
|
:shortcuts="$options.shortcuts.strikethrough"
|
|
|
|
icon="strikethrough"
|
|
|
|
/>
|
|
|
|
<toolbar-button
|
|
|
|
v-if="!restrictedToolBarItems.includes('quote')"
|
|
|
|
:prepend="true"
|
|
|
|
:tag="tag"
|
|
|
|
:button-title="__('Insert a quote')"
|
|
|
|
icon="quote"
|
|
|
|
@click="handleQuote"
|
|
|
|
/>
|
|
|
|
<toolbar-button tag="`" tag-block="```" :button-title="__('Insert code')" icon="code" />
|
|
|
|
<toolbar-button
|
|
|
|
tag="[{text}](url)"
|
|
|
|
tag-select="url"
|
|
|
|
:button-title="
|
|
|
|
/* eslint-disable @gitlab/vue-no-new-non-primitive-in-template */
|
|
|
|
sprintf(s__('MarkdownEditor|Add a link (%{modifierKey}K)'), {
|
|
|
|
modifierKey,
|
|
|
|
}) /* eslint-enable @gitlab/vue-no-new-non-primitive-in-template */
|
|
|
|
"
|
|
|
|
:shortcuts="$options.shortcuts.link"
|
|
|
|
icon="link"
|
|
|
|
/>
|
|
|
|
<toolbar-button
|
|
|
|
v-if="!restrictedToolBarItems.includes('bullet-list')"
|
|
|
|
:prepend="true"
|
|
|
|
tag="- "
|
|
|
|
:button-title="__('Add a bullet list')"
|
|
|
|
icon="list-bulleted"
|
|
|
|
/>
|
|
|
|
<toolbar-button
|
|
|
|
v-if="!restrictedToolBarItems.includes('numbered-list')"
|
|
|
|
:prepend="true"
|
|
|
|
tag="1. "
|
|
|
|
:button-title="__('Add a numbered list')"
|
|
|
|
icon="list-numbered"
|
|
|
|
/>
|
|
|
|
<toolbar-button
|
|
|
|
v-if="!restrictedToolBarItems.includes('task-list')"
|
|
|
|
:prepend="true"
|
|
|
|
tag="- [ ] "
|
|
|
|
:button-title="__('Add a checklist')"
|
|
|
|
icon="list-task"
|
|
|
|
/>
|
|
|
|
<toolbar-button
|
|
|
|
v-if="!restrictedToolBarItems.includes('indent')"
|
|
|
|
class="gl-display-none"
|
|
|
|
:button-title="
|
|
|
|
/* eslint-disable @gitlab/vue-no-new-non-primitive-in-template */
|
|
|
|
sprintf(s__('MarkdownEditor|Indent line (%{modifierKey}])'), {
|
|
|
|
modifierKey /* eslint-enable @gitlab/vue-no-new-non-primitive-in-template */,
|
|
|
|
})
|
|
|
|
"
|
|
|
|
:shortcuts="$options.shortcuts.indent"
|
|
|
|
command="indentLines"
|
|
|
|
icon="list-indent"
|
|
|
|
/>
|
|
|
|
<toolbar-button
|
|
|
|
v-if="!restrictedToolBarItems.includes('outdent')"
|
|
|
|
class="gl-display-none"
|
|
|
|
:button-title="
|
|
|
|
/* eslint-disable @gitlab/vue-no-new-non-primitive-in-template */
|
|
|
|
sprintf(s__('MarkdownEditor|Outdent line (%{modifierKey}[)'), {
|
|
|
|
modifierKey /* eslint-enable @gitlab/vue-no-new-non-primitive-in-template */,
|
|
|
|
})
|
|
|
|
"
|
|
|
|
:shortcuts="$options.shortcuts.outdent"
|
|
|
|
command="outdentLines"
|
|
|
|
icon="list-outdent"
|
|
|
|
/>
|
|
|
|
<toolbar-button
|
|
|
|
v-if="!restrictedToolBarItems.includes('collapsible-section')"
|
|
|
|
:tag="mdCollapsibleSection"
|
|
|
|
:prepend="true"
|
|
|
|
tag-select="Click to expand"
|
|
|
|
:button-title="__('Add a collapsible section')"
|
|
|
|
icon="details-block"
|
|
|
|
/>
|
|
|
|
<toolbar-button
|
|
|
|
v-if="!restrictedToolBarItems.includes('table')"
|
|
|
|
:tag="mdTable"
|
|
|
|
:prepend="true"
|
|
|
|
:button-title="__('Add a table')"
|
|
|
|
icon="table"
|
|
|
|
/>
|
|
|
|
<gl-button
|
|
|
|
v-if="!restrictedToolBarItems.includes('attach-file')"
|
|
|
|
v-gl-tooltip
|
|
|
|
:aria-label="__('Attach a file or image')"
|
|
|
|
:title="__('Attach a file or image')"
|
|
|
|
class="gl-mr-2"
|
|
|
|
data-testid="button-attach-file"
|
|
|
|
category="tertiary"
|
|
|
|
icon="paperclip"
|
|
|
|
size="small"
|
|
|
|
@click="handleAttachFile"
|
|
|
|
/>
|
|
|
|
<drawio-toolbar-button
|
|
|
|
v-if="drawioEnabled"
|
|
|
|
:uploads-path="uploadsPath"
|
|
|
|
:markdown-preview-path="markdownPreviewPath"
|
|
|
|
/>
|
|
|
|
<comment-templates-dropdown
|
|
|
|
v-if="newCommentTemplatePath && glFeatures.savedReplies"
|
|
|
|
:new-comment-template-path="newCommentTemplatePath"
|
|
|
|
/>
|
|
|
|
</div>
|
|
|
|
<div class="switch-preview gl-py-2 gl-display-flex gl-align-items-center gl-ml-auto">
|
|
|
|
<editor-mode-switcher
|
|
|
|
v-if="showEditorModeSwitcher"
|
|
|
|
size="small"
|
|
|
|
class="gl-mr-2"
|
|
|
|
value="markdown"
|
|
|
|
@input="handleEditorModeChanged"
|
|
|
|
/>
|
|
|
|
<gl-button
|
|
|
|
v-if="enablePreview"
|
|
|
|
data-testid="preview-toggle"
|
|
|
|
value="preview"
|
|
|
|
:label="$options.i18n.previewTabTitle"
|
|
|
|
class="js-md-preview-button gl-flex-direction-row-reverse gl-align-items-center gl-font-weight-normal!"
|
|
|
|
size="small"
|
|
|
|
category="tertiary"
|
|
|
|
@click="switchPreview"
|
|
|
|
>{{ previewMarkdown ? $options.i18n.hidePreview : $options.i18n.preview }}</gl-button
|
|
|
|
>
|
|
|
|
<gl-button
|
|
|
|
v-if="!restrictedToolBarItems.includes('full-screen')"
|
|
|
|
v-gl-tooltip
|
|
|
|
:class="{ 'gl-display-none!': previewMarkdown }"
|
|
|
|
class="js-zen-enter gl-ml-2"
|
|
|
|
category="tertiary"
|
|
|
|
icon="maximize"
|
|
|
|
size="small"
|
|
|
|
:title="__('Go full screen')"
|
|
|
|
:prepend="true"
|
|
|
|
:aria-label="__('Go full screen')"
|
|
|
|
/>
|
|
|
|
</div>
|
|
|
|
</div>
|
2017-09-10 17:25:29 +05:30
|
|
|
</div>
|
|
|
|
</template>
|