Refactor discussion edit widget to have only one at a time.
This commit is contained in:
parent
7c2a4699b8
commit
1100320b0c
6 changed files with 97 additions and 40 deletions
|
@ -129,4 +129,16 @@
|
|||
|
||||
})(window);
|
||||
|
||||
gl.utils.isElementVisibleInViewport = function(el) {
|
||||
var rect = el.getBoundingClientRect();
|
||||
var height = Math.max(document.documentElement.clientHeight, window.innerHeight);
|
||||
return !(rect.bottom - 110 < 0 || rect.top - height >= 0); // -110 for sticky GitLab navigation header
|
||||
}
|
||||
|
||||
gl.utils.animateToElement = function($el) {
|
||||
return $('body, html').animate({
|
||||
scrollTop: $el.offset().top - 110
|
||||
}, 200);
|
||||
}
|
||||
|
||||
}).call(this);
|
||||
|
|
|
@ -63,7 +63,7 @@
|
|||
// change note in UI after update
|
||||
$(document).on("ajax:success", "form.edit-note", this.updateNote);
|
||||
// Edit note link
|
||||
$(document).on("click", ".js-note-edit", this.showEditForm);
|
||||
$(document).on("click", ".js-note-edit", this.showEditForm.bind(this));
|
||||
$(document).on("click", ".note-edit-cancel", this.cancelEdit);
|
||||
// Reopen and close actions for Issue/MR combined with note form submit
|
||||
$(document).on("click", ".js-comment-button", this.updateCloseButton);
|
||||
|
@ -466,6 +466,9 @@
|
|||
var $html, $note_li;
|
||||
// Convert returned HTML to a jQuery object so we can modify it further
|
||||
$html = $(note.html);
|
||||
|
||||
$('.note-edit-form').insertBefore('.notes-form');
|
||||
|
||||
gl.utils.localTimeAgo($('.js-timeago', $html));
|
||||
$html.renderGFM();
|
||||
$html.find('.js-task-list-container').taskList('enable');
|
||||
|
@ -480,48 +483,73 @@
|
|||
};
|
||||
|
||||
|
||||
Notes.prototype.checkContentToAllowEditing = function($el) {
|
||||
var initialContent = $el.find('.original-note-content').text().trim();
|
||||
var currentContent = $el.find('.note-textarea').val();
|
||||
var isAllowed = true;
|
||||
|
||||
if (currentContent === initialContent) {
|
||||
this.removeNoteEditForm($el);
|
||||
$el.find('.js-md-write-button').trigger('click');
|
||||
}
|
||||
else {
|
||||
var $buttons = $el.find('.note-form-actions');
|
||||
var isButtonsVisible = gl.utils.isElementVisibleInViewport($buttons[0]);
|
||||
var isWidgetVisible = gl.utils.isElementVisibleInViewport($el[0]);
|
||||
|
||||
if (!isButtonsVisible || !isWidgetVisible) {
|
||||
gl.utils.animateToElement($el);
|
||||
}
|
||||
|
||||
$el.find('.js-edit-warning').show();
|
||||
$el.find('.js-md-write-button').trigger('click');
|
||||
isAllowed = false;
|
||||
}
|
||||
|
||||
return isAllowed;
|
||||
}
|
||||
|
||||
|
||||
/*
|
||||
Called in response to clicking the edit note link
|
||||
|
||||
Replaces the note text with the note edit form
|
||||
Adds a data attribute to the form with the original content of the note for cancellations
|
||||
*/
|
||||
|
||||
*/
|
||||
Notes.prototype.showEditForm = function(e, scrollTo, myLastNote) {
|
||||
var $noteText, done, form, note;
|
||||
e.preventDefault();
|
||||
note = $(this).closest(".note");
|
||||
note.addClass("is-editting");
|
||||
form = note.find(".note-edit-form");
|
||||
form.addClass('current-note-edit-form');
|
||||
// Show the attachment delete link
|
||||
note.find(".js-note-attachment-delete").show();
|
||||
done = function($noteText) {
|
||||
var noteTextVal;
|
||||
// Neat little trick to put the cursor at the end
|
||||
noteTextVal = $noteText.val();
|
||||
// Store the original note text in a data attribute to retrieve if a user cancels edit.
|
||||
form.find('form.edit-note').data('original-note', noteTextVal);
|
||||
return $noteText.val('').val(noteTextVal);
|
||||
};
|
||||
new GLForm(form);
|
||||
if ((scrollTo != null) && (myLastNote != null)) {
|
||||
// scroll to the bottom
|
||||
// so the open of the last element doesn't make a jump
|
||||
$('html, body').scrollTop($(document).height());
|
||||
return $('html, body').animate({
|
||||
scrollTop: myLastNote.offset().top - 150
|
||||
}, 500, function() {
|
||||
var $noteText;
|
||||
$noteText = form.find(".js-note-text");
|
||||
$noteText.focus();
|
||||
return done($noteText);
|
||||
});
|
||||
} else {
|
||||
$noteText = form.find('.js-note-text');
|
||||
$noteText.focus();
|
||||
return done($noteText);
|
||||
|
||||
var $currentlyEditing = $('.note.is-editting');
|
||||
if ($currentlyEditing.length) {
|
||||
var isEditAllowed = this.checkContentToAllowEditing($currentlyEditing);
|
||||
|
||||
if (!isEditAllowed) {
|
||||
return;
|
||||
}
|
||||
}
|
||||
|
||||
var note = $(e.target).closest('.note');
|
||||
var $editForm = $('.note-edit-form');
|
||||
var $originalContentEl = note.find('.original-note-content');
|
||||
var originalContent = $originalContentEl.text().trim();
|
||||
var postUrl = $originalContentEl.data('post-url');
|
||||
var form = note.find('.note-edit-form');
|
||||
var $noteText = form.find('.js-note-text');
|
||||
var noteTextVal = $noteText.val(); // Neat little trick to put the cursor at the end
|
||||
|
||||
note.addClass('is-editting');
|
||||
$editForm.insertAfter(note.find('.note-text'));
|
||||
$editForm.find('.js-note-text').val(originalContent);
|
||||
$editForm.find('form').attr('action', postUrl);
|
||||
|
||||
form.addClass('current-note-edit-form');
|
||||
note.find('.js-note-attachment-delete').show(); // Show the attachment delete link
|
||||
new GLForm(form);
|
||||
|
||||
$noteText.focus();
|
||||
// Store the original note text in a data attribute to retrieve if a user cancels edit.
|
||||
form.find('form.edit-note').data('original-note', noteTextVal);
|
||||
$noteText.val('').val(noteTextVal);
|
||||
};
|
||||
|
||||
|
||||
|
@ -532,15 +560,17 @@
|
|||
*/
|
||||
|
||||
Notes.prototype.cancelEdit = function(e) {
|
||||
var note;
|
||||
e.preventDefault();
|
||||
note = $(e.target).closest('.note');
|
||||
var note = $(e.target).closest('.note');
|
||||
note.find('.js-edit-warning').hide();
|
||||
note.find('.js-md-write-button').trigger('click');
|
||||
$('.note-edit-form').insertBefore('.notes-form');
|
||||
return this.removeNoteEditForm(note);
|
||||
};
|
||||
|
||||
|
||||
Notes.prototype.removeNoteEditForm = function(note) {
|
||||
var form;
|
||||
form = note.find(".current-note-edit-form");
|
||||
var form = note.find(".current-note-edit-form");
|
||||
note.removeClass("is-editting");
|
||||
form.removeClass("current-note-edit-form");
|
||||
// Replace markdown textarea text with original note text.
|
||||
|
|
|
@ -601,3 +601,12 @@ ul.notes {
|
|||
position: relative;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
.note-edit-warning.settings-message {
|
||||
display: none;
|
||||
position: relative;
|
||||
top: 1px;
|
||||
left: 7px;
|
||||
padding: 5px 10px;
|
||||
}
|
||||
|
|
|
@ -7,5 +7,7 @@
|
|||
|
||||
.note-form-actions.clearfix
|
||||
= f.submit 'Save Comment', class: 'btn btn-nr btn-save js-comment-button'
|
||||
%span.settings-message.note-edit-warning.js-edit-warning
|
||||
Finish editing this message first!
|
||||
%button.btn.btn-nr.btn-cancel.note-edit-cancel{ type: 'button' }
|
||||
Cancel
|
||||
|
|
|
@ -67,7 +67,8 @@
|
|||
= note.redacted_note_html
|
||||
= edited_time_ago_with_tooltip(note, placement: 'bottom', html_class: 'note_edited_ago', include_author: true)
|
||||
- if note_editable
|
||||
= render 'projects/notes/edit_form', note: note
|
||||
.original-note-content.hidden{data: {post_url: namespace_project_note_path(@project.namespace, @project, note), target_id: note.noteable.id, target_type: note.noteable.class.name.underscore}}
|
||||
#{note.note}
|
||||
.note-awards
|
||||
= render 'award_emoji/awards_block', awardable: note, inline: false
|
||||
- if note.system
|
||||
|
|
|
@ -6,3 +6,6 @@
|
|||
= render 'discussions/discussion', discussion: discussion
|
||||
- else
|
||||
= render partial: "projects/notes/note", collection: @notes, as: :note
|
||||
|
||||
= render 'projects/notes/edit_form', note: @notes[0]
|
||||
= hidden_field_tag :authenticity_token, form_authenticity_token
|
||||
|
|
Loading…
Reference in a new issue