mirror of
https://github.com/gitbucket/gitbucket.git
synced 2025-11-12 16:35:52 +01:00
add file finder
This commit is contained in:
@@ -14,11 +14,12 @@
|
||||
@html.main(s"${repository.owner}/${repository.name}", Some(repository)) {
|
||||
@html.menu("code", repository, Some(branch), pathList.isEmpty, groupNames.isEmpty, info, error){
|
||||
<div class="head">
|
||||
<div class="pull-right">
|
||||
<div class="pull-right"><div class="btn-group">
|
||||
<a href="@url(repository)/find/@encodeRefName(branch)" class="btn btn-mini" data-toggle="tooltip" data-placement="bottom" data-hotkey="t" title="Quickly jump between files"><i class="icon icon-th-list"></i></a>
|
||||
@if(pathList.nonEmpty){
|
||||
<a href="@url(repository)/commits/@encodeRefName(branch)/@pathList.mkString("/")" class="btn btn-mini" data-toggle="tooltip" data-placement="bottom" title="Browse commits for this branch"><i class="icon icon-time"></i></a>
|
||||
}
|
||||
</div>
|
||||
</div></div>
|
||||
@branchPullRequest.map{ case (pullRequest, issue) =>
|
||||
<a href="@url(repository)/pull/@pullRequest.issueId" class="btn btn-pullrequest-branch btn-mini" title="@issue.title" data-toggle="tooltip">#@pullRequest.issueId</a>
|
||||
}.getOrElse{
|
||||
|
||||
121
src/main/twirl/gitbucket/core/repo/find.scala.html
Normal file
121
src/main/twirl/gitbucket/core/repo/find.scala.html
Normal file
@@ -0,0 +1,121 @@
|
||||
@(branch: String,
|
||||
treeId: String,
|
||||
repository: gitbucket.core.service.RepositoryService.RepositoryInfo,
|
||||
groupNames: List[String]
|
||||
)(implicit context: gitbucket.core.controller.Context)
|
||||
@import context._
|
||||
@import gitbucket.core.view.helpers._
|
||||
@html.main(s"${repository.owner}/${repository.name}", Some(repository)) {
|
||||
@html.menu("code", repository, Some(branch), false, groupNames.isEmpty){
|
||||
|
||||
<div>
|
||||
<div class="find-input">
|
||||
<span class="bold"><a href="@url(repository)/tree/@encodeRefName(branch)">@repository.name</a></span>
|
||||
/
|
||||
<input type="text" name="query" autocomplete="off" spellcheck="false" autofocus id="tree-finder-field" />
|
||||
</div>
|
||||
</div>
|
||||
|
||||
<div class="alert alert-info">
|
||||
<button type="button" class="close" data-dismiss="alert">×</button>
|
||||
You've activated the <em>file finder</em>
|
||||
by pressing <code>t</code>.
|
||||
Start typing to filter the file list. Use <code>↑</code> and
|
||||
<code>↓</code> to navigate,
|
||||
<code>enter</code> to view files.
|
||||
</div>
|
||||
<table id="tree-finder-results" class="table table-file-list" data-url="@url(repository)/tree-list/@treeId">
|
||||
<tbody class="tree-browser-result-template">
|
||||
<tr class="tree-browser-result">
|
||||
<td class="icon"><span class="icon icon-chevron-right"></span></td>
|
||||
<td class="icon"><img src="@assets/common/images/file.png"/></td>
|
||||
<td>
|
||||
<a href="@url(repository)/blob/@encodeRefName(branch)"></a>
|
||||
</td>
|
||||
</tr>
|
||||
</tbody>
|
||||
<tbody class="no-results" style="display:none">
|
||||
<tr><th colspan="3">No matching files</th><tr>
|
||||
</tbody>
|
||||
</table>
|
||||
<script>
|
||||
$(function(){
|
||||
var paths = [];
|
||||
var template = $('.tree-browser-result-template tr').clone();
|
||||
var res = $('.tree-browser-result-template');
|
||||
var cursor = 0;
|
||||
var pathBase = template.find("a").attr("href");
|
||||
var preKeyword;
|
||||
$.ajax({
|
||||
url:$('#tree-finder-results').data('url'),
|
||||
cache: true,
|
||||
dataType: 'json',
|
||||
success:function(data){
|
||||
paths = data.paths;
|
||||
filter();
|
||||
}
|
||||
});
|
||||
var timer;
|
||||
$("#tree-finder-field").keydown(function(e){
|
||||
var target = $(this);
|
||||
if(e.keyCode == 40){ // DOWN
|
||||
e.preventDefault();
|
||||
e.stopPropagation();
|
||||
changeCursor(cursor+1);
|
||||
}else if(e.keyCode==38){ // UP
|
||||
e.preventDefault();
|
||||
e.stopPropagation();
|
||||
changeCursor(cursor-1);
|
||||
}else if(e.keyCode==13){ // ENTER
|
||||
e.preventDefault();
|
||||
e.stopPropagation();
|
||||
target = $(".tree-browser-result.navigation-focus a");
|
||||
if(target[0]){
|
||||
target[0].click();
|
||||
}
|
||||
}else if(e.keyCode==27){ // ESC
|
||||
e.preventDefault();
|
||||
e.stopPropagation();
|
||||
history.back();
|
||||
}else{
|
||||
clearTimeout(timer);
|
||||
timer=setTimeout(filter,300);
|
||||
}
|
||||
});
|
||||
function changeCursor(newPos){
|
||||
if(!$(".tree-browser-result")[newPos]){
|
||||
return $(".tree-browser-result.navigation-focus");
|
||||
}
|
||||
$(".tree-browser-result.navigation-focus").removeClass("navigation-focus");
|
||||
cursor=newPos;
|
||||
scrollIntoView($($(".tree-browser-result")[cursor]).addClass("navigation-focus"));
|
||||
}
|
||||
function filter(){
|
||||
var v = $('#tree-finder-field').val();
|
||||
if(v==preKeyword || paths.length==0){
|
||||
return;
|
||||
}
|
||||
scrollIntoView('#tree-finder-field');
|
||||
preKeyword=v;
|
||||
cursor=0;
|
||||
var p = string_score_sort(v, paths, 50);
|
||||
res.html("");
|
||||
if(p.length==0){
|
||||
$(".no-results").show();
|
||||
return;
|
||||
}else{
|
||||
$(".no-results").hide();
|
||||
for(var i=0;i < p.length;i++){
|
||||
var row = template.clone();
|
||||
row.find("a").attr("href",pathBase+"/"+p[i].string).html(string_score_hilight(p[i], '<b>'));
|
||||
if(cursor==i){
|
||||
row.addClass("navigation-focus");
|
||||
}
|
||||
row.appendTo(res);
|
||||
}
|
||||
}
|
||||
}
|
||||
});
|
||||
</script>
|
||||
}
|
||||
}
|
||||
Reference in New Issue
Block a user