mirror of
				https://github.com/go-gitea/gitea
				synced 2025-10-31 11:28:24 +00:00 
			
		
		
		
	Context menus for comments (#9043)
* Add quote replies Signed-off-by: jolheiser <john.olheiser@gmail.com>
This commit is contained in:
		| @@ -867,6 +867,10 @@ issues.closed_title = Closed | |||||||
| issues.num_comments = %d comments | issues.num_comments = %d comments | ||||||
| issues.commented_at = `commented <a href="#%s">%s</a>` | issues.commented_at = `commented <a href="#%s">%s</a>` | ||||||
| issues.delete_comment_confirm = Are you sure you want to delete this comment? | issues.delete_comment_confirm = Are you sure you want to delete this comment? | ||||||
|  | issues.context.copy_link = Copy Link | ||||||
|  | issues.context.quote_reply = Quote Reply | ||||||
|  | issues.context.edit = Edit | ||||||
|  | issues.context.delete = Delete | ||||||
| issues.no_content = There is no content yet. | issues.no_content = There is no content yet. | ||||||
| issues.close_issue = Close | issues.close_issue = Close | ||||||
| issues.close_comment_issue = Comment and Close | issues.close_comment_issue = Comment and Close | ||||||
|   | |||||||
| @@ -573,6 +573,7 @@ i.icon.centerlock{top:1.5em} | |||||||
| .repository.view.issue .comment-list .comment .tag{color:#767676;margin-top:3px;padding:2px 5px;font-size:12px;border:1px solid rgba(0,0,0,.1);border-radius:3px} | .repository.view.issue .comment-list .comment .tag{color:#767676;margin-top:3px;padding:2px 5px;font-size:12px;border:1px solid rgba(0,0,0,.1);border-radius:3px} | ||||||
| .repository.view.issue .comment-list .comment .tag.pending{color:#000;background-color:#fffbb2;margin-left:5px} | .repository.view.issue .comment-list .comment .tag.pending{color:#000;background-color:#fffbb2;margin-left:5px} | ||||||
| .repository.view.issue .comment-list .comment .actions .item{float:left} | .repository.view.issue .comment-list .comment .actions .item{float:left} | ||||||
|  | .repository.view.issue .comment-list .comment .actions .item.context{float:none} | ||||||
| .repository.view.issue .comment-list .comment .actions .item.tag{margin-right:5px} | .repository.view.issue .comment-list .comment .actions .item.tag{margin-right:5px} | ||||||
| .repository.view.issue .comment-list .comment .actions .item.action{margin-top:6px;margin-left:10px} | .repository.view.issue .comment-list .comment .actions .item.action{margin-top:6px;margin-left:10px} | ||||||
| .repository.view.issue .comment-list .comment .content{margin-left:4em} | .repository.view.issue .comment-list .comment .content{margin-left:4em} | ||||||
|   | |||||||
										
											
												File diff suppressed because one or more lines are too long
											
										
									
								
							
										
											
												File diff suppressed because one or more lines are too long
											
										
									
								
							| @@ -21,12 +21,7 @@ | |||||||
| 				{{end}} | 				{{end}} | ||||||
| 			{{end}} | 			{{end}} | ||||||
| 			{{template "repo/issue/view_content/add_reaction" Dict "ctx" $ "ActionURL" (Printf "%s/comments/%d/reactions" $.root.RepoLink .ID) }} | 			{{template "repo/issue/view_content/add_reaction" Dict "ctx" $ "ActionURL" (Printf "%s/comments/%d/reactions" $.root.RepoLink .ID) }} | ||||||
| 			{{if or $.root.Permission.IsAdmin (eq .Poster.ID $.root.SignedUserID)}} | 			{{template "repo/issue/view_content/context_menu" Dict "ctx" $.root "item" . "delete" true "diff" true }} | ||||||
| 				<div class="item action"> |  | ||||||
| 					<a class="edit-content" href="#"><i class="octicon octicon-pencil"></i></a> |  | ||||||
| 					<a class="delete-comment" href="#" data-comment-id={{.HashTag}} data-url="{{$.root.RepoLink}}/comments/{{.ID}}/delete" data-locale="{{$.root.i18n.Tr "repo.issues.delete_comment_confirm"}}"><i class="octicon octicon-x"></i></a> |  | ||||||
| 				</div> |  | ||||||
| 			{{end}} |  | ||||||
| 			</div> | 			</div> | ||||||
| 		</div> | 		</div> | ||||||
| 		<div class="ui attached segment"> | 		<div class="ui attached segment"> | ||||||
| @@ -37,7 +32,7 @@ | |||||||
| 				<span class="no-content">{{$.root.i18n.Tr "repo.issues.no_content"}}</span> | 				<span class="no-content">{{$.root.i18n.Tr "repo.issues.no_content"}}</span> | ||||||
| 			{{end}} | 			{{end}} | ||||||
| 			</div> | 			</div> | ||||||
| 			<div class="raw-content hide">{{.Content}}</div> | 			<div id="comment-{{.ID}}" class="raw-content hide">{{.Content}}</div> | ||||||
| 			<div class="edit-content-zone hide" data-write="issuecomment-{{.ID}}-write" data-preview="issuecomment-{{.ID}}-preview" data-update-url="{{$.root.RepoLink}}/comments/{{.ID}}" data-context="{{$.root.RepoLink}}"></div> | 			<div class="edit-content-zone hide" data-write="issuecomment-{{.ID}}-write" data-preview="issuecomment-{{.ID}}-preview" data-update-url="{{$.root.RepoLink}}/comments/{{.ID}}" data-context="{{$.root.RepoLink}}"></div> | ||||||
| 		</div> | 		</div> | ||||||
| 		{{$reactions := .Reactions.GroupByType}} | 		{{$reactions := .Reactions.GroupByType}} | ||||||
|   | |||||||
| @@ -29,11 +29,7 @@ | |||||||
| 						{{if not $.Repository.IsArchived}} | 						{{if not $.Repository.IsArchived}} | ||||||
| 							<div class="ui right actions"> | 							<div class="ui right actions"> | ||||||
| 								{{template "repo/issue/view_content/add_reaction" Dict "ctx" $ "ActionURL" (Printf "%s/issues/%d/reactions" $.RepoLink .Issue.Index) }} | 								{{template "repo/issue/view_content/add_reaction" Dict "ctx" $ "ActionURL" (Printf "%s/issues/%d/reactions" $.RepoLink .Issue.Index) }} | ||||||
| 								{{if or .IsIssueWriter .IsIssuePoster}} | 								{{template "repo/issue/view_content/context_menu" Dict "ctx" $ "item" .Issue "delete" false "diff" false }} | ||||||
| 									<div class="item action"> |  | ||||||
| 										<a class="edit-content" href="#"><i class="octicon octicon-pencil"></i></a> |  | ||||||
| 									</div> |  | ||||||
| 								{{end}} |  | ||||||
| 							</div> | 							</div> | ||||||
| 						{{end}} | 						{{end}} | ||||||
| 					</div> | 					</div> | ||||||
| @@ -45,7 +41,7 @@ | |||||||
| 								<span class="no-content">{{.i18n.Tr "repo.issues.no_content"}}</span> | 								<span class="no-content">{{.i18n.Tr "repo.issues.no_content"}}</span> | ||||||
| 							{{end}} | 							{{end}} | ||||||
| 						</div> | 						</div> | ||||||
| 						<div class="raw-content hide">{{.Issue.Content}}</div> | 						<div id="comment-{{.Issue.ID}}" class="raw-content hide">{{.Issue.Content}}</div> | ||||||
| 						<div class="edit-content-zone hide" data-write="issue-{{.Issue.ID}}-write" data-preview="issue-{{.Issue.ID}}-preview" data-update-url="{{$.RepoLink}}/issues/{{.Issue.Index}}/content" data-context="{{.RepoLink}}" data-attachment-url="{{$.RepoLink}}/issues/{{.Issue.Index}}/attachments" data-view-attachment-url="{{$.RepoLink}}/issues/{{.Issue.Index}}/view-attachments"></div> | 						<div class="edit-content-zone hide" data-write="issue-{{.Issue.ID}}-write" data-preview="issue-{{.Issue.ID}}-preview" data-update-url="{{$.RepoLink}}/issues/{{.Issue.Index}}/content" data-context="{{.RepoLink}}" data-attachment-url="{{$.RepoLink}}/issues/{{.Issue.Index}}/attachments" data-view-attachment-url="{{$.RepoLink}}/issues/{{.Issue.Index}}/view-attachments"></div> | ||||||
| 					</div> | 					</div> | ||||||
| 					{{$reactions := .Issue.Reactions.GroupByType}} | 					{{$reactions := .Issue.Reactions.GroupByType}} | ||||||
|   | |||||||
| @@ -23,28 +23,23 @@ | |||||||
| 				{{else}} | 				{{else}} | ||||||
| 					<span class="text grey"><a {{if gt .Poster.ID 0}}href="{{.Poster.HomeLink}}"{{end}}>{{.Poster.GetDisplayName}}</a> {{$.i18n.Tr "repo.issues.commented_at" .HashTag $createdStr | Safe}}</span> | 					<span class="text grey"><a {{if gt .Poster.ID 0}}href="{{.Poster.HomeLink}}"{{end}}>{{.Poster.GetDisplayName}}</a> {{$.i18n.Tr "repo.issues.commented_at" .HashTag $createdStr | Safe}}</span> | ||||||
| 				{{end}} | 				{{end}} | ||||||
|                     {{if not $.Repository.IsArchived}} | 					{{if not $.Repository.IsArchived}} | ||||||
|                         <div class="ui right actions"> | 						<div class="ui right actions"> | ||||||
|                             {{if gt .ShowTag 0}} | 							{{if gt .ShowTag 0}} | ||||||
|                                 <div class="item tag"> | 								<div class="item tag"> | ||||||
|                                     {{if eq .ShowTag 1}} | 									{{if eq .ShowTag 1}} | ||||||
|                                         {{$.i18n.Tr "repo.issues.poster"}} | 										{{$.i18n.Tr "repo.issues.poster"}} | ||||||
|                                     {{else if eq .ShowTag 2}} | 									{{else if eq .ShowTag 2}} | ||||||
|                                         {{$.i18n.Tr "repo.issues.collaborator"}} | 										{{$.i18n.Tr "repo.issues.collaborator"}} | ||||||
|                                     {{else if eq .ShowTag 3}} | 									{{else if eq .ShowTag 3}} | ||||||
|                                         {{$.i18n.Tr "repo.issues.owner"}} | 										{{$.i18n.Tr "repo.issues.owner"}} | ||||||
|                                     {{end}} | 									{{end}} | ||||||
|                                 </div> | 								</div> | ||||||
|                             {{end}} | 							{{end}} | ||||||
|                             {{template "repo/issue/view_content/add_reaction" Dict "ctx" $ "ActionURL" (Printf "%s/comments/%d/reactions" $.RepoLink .ID) }} | 							{{template "repo/issue/view_content/add_reaction" Dict "ctx" $ "ActionURL" (Printf "%s/comments/%d/reactions" $.RepoLink .ID) }} | ||||||
|                             {{if or $.Permission.IsAdmin (eq .Poster.ID $.SignedUserID)}} | 							{{template "repo/issue/view_content/context_menu" Dict "ctx" $ "item" . "delete" true "diff" false }} | ||||||
|                                 <div class="item action"> | 						</div> | ||||||
|                                     <a class="edit-content" href="#"><i class="octicon octicon-pencil"></i></a> | 					{{end}} | ||||||
|                                     <a class="delete-comment" href="#" data-comment-id={{.HashTag}} data-url="{{$.RepoLink}}/comments/{{.ID}}/delete" data-locale="{{$.i18n.Tr "repo.issues.delete_comment_confirm"}}"><i class="octicon octicon-x"></i></a> |  | ||||||
|                                 </div> |  | ||||||
|                             {{end}} |  | ||||||
|                         </div> |  | ||||||
|                     {{end}} |  | ||||||
| 				</div> | 				</div> | ||||||
| 				<div class="ui attached segment"> | 				<div class="ui attached segment"> | ||||||
| 					<div class="render-content markdown has-emoji"> | 					<div class="render-content markdown has-emoji"> | ||||||
| @@ -54,7 +49,7 @@ | |||||||
| 							<span class="no-content">{{$.i18n.Tr "repo.issues.no_content"}}</span> | 							<span class="no-content">{{$.i18n.Tr "repo.issues.no_content"}}</span> | ||||||
| 						{{end}} | 						{{end}} | ||||||
| 					</div> | 					</div> | ||||||
| 					<div class="raw-content hide">{{.Content}}</div> | 					<div id="comment-{{.ID}}" class="raw-content hide">{{.Content}}</div> | ||||||
| 					<div class="edit-content-zone hide" data-write="issuecomment-{{.ID}}-write" data-preview="issuecomment-{{.ID}}-preview" data-update-url="{{$.RepoLink}}/comments/{{.ID}}" data-context="{{$.RepoLink}}" data-attachment-url="{{$.RepoLink}}/comments/{{.ID}}/attachments"></div> | 					<div class="edit-content-zone hide" data-write="issuecomment-{{.ID}}-write" data-preview="issuecomment-{{.ID}}-preview" data-update-url="{{$.RepoLink}}/comments/{{.ID}}" data-context="{{$.RepoLink}}" data-attachment-url="{{$.RepoLink}}/comments/{{.ID}}/attachments"></div> | ||||||
| 				</div> | 				</div> | ||||||
| 				{{$reactions := .Reactions.GroupByType}} | 				{{$reactions := .Reactions.GroupByType}} | ||||||
| @@ -277,29 +272,29 @@ | |||||||
| 			<span class="octicon octicon-primitive-dot"></span> | 			<span class="octicon octicon-primitive-dot"></span> | ||||||
| 			<a class="ui avatar image" href="{{.Poster.HomeLink}}"> | 			<a class="ui avatar image" href="{{.Poster.HomeLink}}"> | ||||||
| 				<img src="{{.Poster.RelAvatarLink}}"> | 				<img src="{{.Poster.RelAvatarLink}}"> | ||||||
| 		 	</a> | 			</a> | ||||||
| 		 	<span class="text grey"> | 			<span class="text grey"> | ||||||
| 			 	{{$.i18n.Tr "repo.issues.dependency.added_dependency" .Poster.HomeLink (.Poster.GetDisplayName|Escape) $createdStr | Safe}} | 				{{$.i18n.Tr "repo.issues.dependency.added_dependency" .Poster.HomeLink (.Poster.GetDisplayName|Escape) $createdStr | Safe}} | ||||||
| 		 	</span> | 			</span> | ||||||
| 		 	<div class="detail"> | 			<div class="detail"> | ||||||
| 				<span class="octicon octicon-plus"></span> | 				<span class="octicon octicon-plus"></span> | ||||||
| 			 	<span class="text grey"><a href="{{$.RepoLink}}/issues/{{.DependentIssue.Index}}">#{{.DependentIssue.Index}} {{.DependentIssue.Title}}</a></span> | 				<span class="text grey"><a href="{{$.RepoLink}}/issues/{{.DependentIssue.Index}}">#{{.DependentIssue.Index}} {{.DependentIssue.Title}}</a></span> | ||||||
| 		 	</div> | 			</div> | ||||||
| 	 	</div> | 		</div> | ||||||
| 	{{else if eq .Type 20}} | 	{{else if eq .Type 20}} | ||||||
| 		<div class="event" id="{{.HashTag}}"> | 		<div class="event" id="{{.HashTag}}"> | ||||||
| 		 	<span class="octicon octicon-primitive-dot"></span> | 			<span class="octicon octicon-primitive-dot"></span> | ||||||
| 		 	<a class="ui avatar image" href="{{.Poster.HomeLink}}"> | 			<a class="ui avatar image" href="{{.Poster.HomeLink}}"> | ||||||
| 			 	<img src="{{.Poster.RelAvatarLink}}"> | 				<img src="{{.Poster.RelAvatarLink}}"> | ||||||
| 		 	</a> | 			</a> | ||||||
| 		 	<span class="text grey"> | 			<span class="text grey"> | ||||||
| 			 	{{$.i18n.Tr "repo.issues.dependency.removed_dependency" .Poster.HomeLink (.Poster.GetDisplayName|Escape) $createdStr | Safe}} | 				{{$.i18n.Tr "repo.issues.dependency.removed_dependency" .Poster.HomeLink (.Poster.GetDisplayName|Escape) $createdStr | Safe}} | ||||||
| 		 	</span> | 			</span> | ||||||
| 		 	<div class="detail"> | 			<div class="detail"> | ||||||
| 			 	<span class="text grey octicon octicon-trashcan"></span> | 				<span class="text grey octicon octicon-trashcan"></span> | ||||||
| 			 	<span class="text grey"><a href="{{$.RepoLink}}/issues/{{.DependentIssue.Index}}">#{{.DependentIssue.Index}} {{.DependentIssue.Title}}</a></span> | 				<span class="text grey"><a href="{{$.RepoLink}}/issues/{{.DependentIssue.Index}}">#{{.DependentIssue.Index}} {{.DependentIssue.Title}}</a></span> | ||||||
| 		 	</div> | 			</div> | ||||||
| 	 	</div> | 		</div> | ||||||
| 	{{else if eq .Type 22}} | 	{{else if eq .Type 22}} | ||||||
| 		<div class="event" id="{{.HashTag}}"> | 		<div class="event" id="{{.HashTag}}"> | ||||||
| 			<span class="octicon octicon-{{.Review.Type.Icon}} issue-symbol"></span> | 			<span class="octicon octicon-{{.Review.Type.Icon}} issue-symbol"></span> | ||||||
|   | |||||||
							
								
								
									
										22
									
								
								templates/repo/issue/view_content/context_menu.tmpl
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										22
									
								
								templates/repo/issue/view_content/context_menu.tmpl
									
									
									
									
									
										Normal file
									
								
							| @@ -0,0 +1,22 @@ | |||||||
|  | {{if .ctx.IsSigned}} | ||||||
|  | <div class="item action ui pointing top right custom dropdown context-dropdown"> | ||||||
|  | 	<a class="context-menu"> | ||||||
|  | 		<i class="fa fa-ellipsis-h"></i> | ||||||
|  | 	</a> | ||||||
|  | 	<div class="menu"> | ||||||
|  | 		{{if .diff}} | ||||||
|  | 			<div class="item context clipboard" data-clipboard-text="{{Printf "%s%s/pulls/%d/files#%s" AppUrl .ctx.Repository.FullName .ctx.Issue.Index .item.HashTag}}">{{.ctx.i18n.Tr "repo.issues.context.copy_link"}}</div> | ||||||
|  | 		{{else}} | ||||||
|  | 			<div class="item context clipboard" data-clipboard-text="{{Printf "%s%s/issues/%d#%s" AppUrl .ctx.Repository.FullName .ctx.Issue.Index .item.HashTag}}">{{.ctx.i18n.Tr "repo.issues.context.copy_link"}}</div> | ||||||
|  | 		{{end}} | ||||||
|  | 		<div class="item context quote-reply {{if .diff}}quote-reply-diff{{end}}" data-target="{{.item.ID}}">{{.ctx.i18n.Tr "repo.issues.context.quote_reply"}}</div> | ||||||
|  | 		{{if or .ctx.Permission.IsAdmin (eq .item.Poster.ID .ctx.SignedUserID)}} | ||||||
|  | 			<div class="divider"></div> | ||||||
|  | 			<div class="item context edit-content">{{.ctx.i18n.Tr "repo.issues.context.edit"}}</div> | ||||||
|  | 			{{if .delete}} | ||||||
|  | 				<div class="item context delete-comment" data-comment-id={{.item.HashTag}} data-url="{{.ctx.RepoLink}}/comments/{{.item.ID}}/delete" data-locale="{{.ctx.i18n.Tr "repo.issues.delete_comment_confirm"}}">{{.ctx.i18n.Tr "repo.issues.context.delete"}}</div> | ||||||
|  | 			{{end}} | ||||||
|  | 		{{end}} | ||||||
|  | 	</div> | ||||||
|  | </div> | ||||||
|  | {{end}} | ||||||
| @@ -732,10 +732,41 @@ function initRepository() { | |||||||
|       return false; |       return false; | ||||||
|     }); |     }); | ||||||
|  |  | ||||||
|  |     // Issue/PR Context Menus | ||||||
|  |     $('.context-dropdown').dropdown({ | ||||||
|  |       action: 'hide' | ||||||
|  |     }); | ||||||
|  |  | ||||||
|  |     // Quote reply | ||||||
|  |     $('.quote-reply').click(function (event) { | ||||||
|  |       $(this).closest('.dropdown').find('.menu').toggle('visible'); | ||||||
|  |       const target = $(this).data('target'); | ||||||
|  |  | ||||||
|  |       let $content; | ||||||
|  |       if ($(this).hasClass('quote-reply-diff')) { | ||||||
|  |         const $parent = $(this).closest('.comment-code-cloud'); | ||||||
|  |         $parent.find('button.comment-form-reply').click(); | ||||||
|  |         $content = $parent.find('[name="content"]'); | ||||||
|  |       } else { | ||||||
|  |         $content = $('#content'); | ||||||
|  |       } | ||||||
|  |  | ||||||
|  |       const quote = $(`#comment-${target}`).text().replace(/\n/g, '\n> '); | ||||||
|  |       const content = `> ${quote}\n\n`; | ||||||
|  |  | ||||||
|  |       if ($content.val() !== '') { | ||||||
|  |         $content.val(`${$content.val()}\n\n${content}`); | ||||||
|  |       } else { | ||||||
|  |         $content.val(`${content}`); | ||||||
|  |       } | ||||||
|  |       $content.focus(); | ||||||
|  |       event.preventDefault(); | ||||||
|  |     }); | ||||||
|  |  | ||||||
|     // Edit issue or comment content |     // Edit issue or comment content | ||||||
|     $('.edit-content').click(function () { |     $('.edit-content').click(function (event) { | ||||||
|       const $segment = $(this).parent().parent().parent() |       $(this).closest('.dropdown').find('.menu').toggle('visible'); | ||||||
|         .next(); |       const $segment = $(this).closest('.header').next(); | ||||||
|       const $editContentZone = $segment.find('.edit-content-zone'); |       const $editContentZone = $segment.find('.edit-content-zone'); | ||||||
|       const $renderContent = $segment.find('.render-content'); |       const $renderContent = $segment.find('.render-content'); | ||||||
|       const $rawContent = $segment.find('.raw-content'); |       const $rawContent = $segment.find('.raw-content'); | ||||||
| @@ -881,7 +912,7 @@ function initRepository() { | |||||||
|         $textarea.val($rawContent.text()); |         $textarea.val($rawContent.text()); | ||||||
|       } |       } | ||||||
|       $textarea.focus(); |       $textarea.focus(); | ||||||
|       return false; |       event.preventDefault(); | ||||||
|     }); |     }); | ||||||
|  |  | ||||||
|     // Delete comment |     // Delete comment | ||||||
| @@ -931,7 +962,6 @@ function initRepository() { | |||||||
|       $(this).closest('.form').hide(); |       $(this).closest('.form').hide(); | ||||||
|       $mergeButton.parent().show(); |       $mergeButton.parent().show(); | ||||||
|     }); |     }); | ||||||
|  |  | ||||||
|     initReactionSelector(); |     initReactionSelector(); | ||||||
|   } |   } | ||||||
|  |  | ||||||
|   | |||||||
| @@ -748,6 +748,10 @@ | |||||||
|                     .item { |                     .item { | ||||||
|                         float: left; |                         float: left; | ||||||
|  |  | ||||||
|  |                         &.context { | ||||||
|  |                             float: none; | ||||||
|  |                         } | ||||||
|  |  | ||||||
|                         &.tag { |                         &.tag { | ||||||
|                             margin-right: 5px; |                             margin-right: 5px; | ||||||
|                         } |                         } | ||||||
|   | |||||||
		Reference in New Issue
	
	Block a user