layerindex-web/templates/rrs/recipes.html
Paul Eggleton aa10299356 Replace uitablefilter usage with jQuery
We were using uitablefilter.js to provide live filtering of table rows
based upon a search field value, but it turns out this module really
isn't necessary - we can accomplish the same thing using simple jQuery
code. While we're at it, enable the search field on the layers list page
to work in conjunction with with the drop-down layer type selection, fix
pasting into the search field and refreshing with a search specified.

Signed-off-by: Paul Eggleton <paul.eggleton@linux.intel.com>
2018-11-19 16:44:42 +13:00

364 lines
12 KiB
HTML

{% extends "rrs/base_toplevel.html" %}
{% load i18n %}
{% load staticfiles %}
{% comment %}
rrs-web - top level page template
Copyright (C) 2015 Intel Corporation
Licensed under the MIT license, see COPYING.MIT for details
{% endcomment %}
{% block navs %}
{% endblock %}
<!--
{% block title_append %} - recipe maintenance - {{ maintplan_name }}{% endblock %}
-->
{% block content_inner %}
<nav class="navbar navbar-default navbar-table-controls">
<div class="container-fluid table-controls">
<ul class="nav navbar-nav">
<li>
<span class="badge navbar-badge" id="recipe-count"></span>
</li>
<li class="dropdown">
<a data-toggle="dropdown" href="#" class="dropdown-toggle" id="selected-status">
Upstream status: <strong></strong>
<b class="caret"></b>
</a>
<ul class="dropdown-menu" id="select-status">
{% for us in upstream_status_set_choices %}
<li><a href="#">{{ us }}</a></li>
{% endfor %}
<li class="divider"/>
{% for us in upstream_status_choices %}
<li><a href="#">{{ us }}</a></li>
{% endfor %}
</ul>
</li>
{% if maintplan.per_recipe_maintainers %}
<li class="navbar-text">and</li>
<li class="dropdown">
<a data-toggle="dropdown" href="#" class="dropdown-toggle" id="selected-maintainer">
Maintainer: <strong></strong>
<b class="caret"></b>
</a>
<ul class="dropdown-menu" id="select-maintainer" style="overflow:scroll;max-height:40em;">
{% for m in set_maintainers %}
<li><a href="#">{{ m }}</a></li>
{% endfor %}
<li class="divider"/>
{% for m in all_maintainers %}
<li class="active"><a href="#">{{ m }}</a></li>
{% endfor %}
</ul>
</li>
{% endif %}
</ul>
<form id="form-search" class="pull-right navbar-form">
<div class="input-group">
<input type="text" class="form-control" placeholder="Search all recipes" id="filter"/>
<div class="input-group-btn">
<a class="input-group-addon btn btn-default" style="display:none" id="clear-search-btn">
<i class="glyphicon glyphicon-remove" aria-hidden="true"></i>
</a>
<button type="submit" value="Search" class="btn btn-default" id="btn-search">Search</button>
</div>
</div>
</form>
</div>
</nav>
<div id="no_recipes_alert" class="alert alert-warning" style="display:none">
No recipes found <a href="#" id="view-all-recipes" style="margin-left:10px;">View all recipes</a>
</div>
<table class="table tablesorter table-bordered table-hover" id="recipestable">
<thead>
<tr>
<th class="recipe_column">Recipe</th>
<th class="version_column text-muted">Version</th>
<th class="upstream_version_column text-muted">Upstream version</th>
<th class="upstream_status_column span2">Upstream status</th>
<th class="last_updated_column">Last Updated</th>
<th class="patches_column">Patches</th>
{% if maintplan.per_recipe_maintainers %}
<th class="maintainer_column">Maintainer</th>
{% endif %}
<th class="summary_column text-muted span5">Summary</th>
<th class="no_update_reason_column text-muted span5" style="display:none">No update reason</th>
</tr>
</thead>
<tbody>
{% for r in recipe_list %}
<tr>
<td class="recipe_column"><a href="{% url "rrs_recipedetail" maintplan_name r.pk %}">{{ r.name }}</a></td>
<td class="version_column">{{ r.version }}</td>
<td class="upstream_version_column">{{ r.upstream_version }}</td>
{% if r.upstream_status == "Up-to-date" %}
<td class="text-success">
{% elif r.upstream_status == "Not updated" %}
<td class="text-danger">
{% elif r.upstream_status == "Can't be updated" %}
<td class="text-muted">
{% else %}
<td class="text-warning">
{% endif %}
{{ r.upstream_status }}
</td>
<td class="last_updated_column">{{r.outdated}}</td>
<td class="patches_column">{% if r.patches_total %}<span {% if not r.patches_pending %}class="text-muted"{% endif %}>{{ r.patches_pending }}<span class="text-muted"> / {{ r.patches_total }}</span>{% endif %}</td>
{% if maintplan.per_recipe_maintainers %}
<td class="maintainer_column">{{ r.maintainer_name }}</td>
{% endif %}
<td class="summary_column">{{ r.summary }}</td>
<td class="no_update_reason_column" style="display:none">{{ r.no_update_reason }}</td>
</tr>
{% endfor %}
</tbody>
</table>
<style>
th.header {
background-image: url({{ STATIC_URL }}/img/small.gif);
cursor: pointer;
font-weight: bold;
background-repeat: no-repeat;
background-position: center left;
padding-left: 20px;
border-right: 1px solid #dad9c7;
margin-left: -1px;
}
th.headerSortUp {
background-image: url({{ STATIC_URL }}/img/small_asc.gif);
}
th.headerSortDown {
background-image: url({{ STATIC_URL }}/img/small_desc.gif);
}
</style>
{% endblock %}
{% block scripts %}
<script src="{% static "js/jquery.tablesorter.js" %}"></script>
<script>
(function($) {
$.fn.multiFilter = function(filters) {
var $table = $(this);
return $table.find('tbody > tr').each(function() {
var tr = $(this);
// Make it an array to avoid special cases later.
if(!$.isArray(filters))
filters = [ filters ];
howMany = 0;
for(i = 0, f = filters[0]; i < filters.length; f = filters[++i]) {
var index = 0;
$table.find('thead > tr > th').each(function(i) {
if($(this).text() == f.column) {
index = i;
return false;
}
});
var text = tr.find('td:eq(' + index + ')').text();
if(text.toLowerCase().indexOf(f.word.toLowerCase()) != -1)
++howMany;
}
if(howMany == filters.length)
tr.show();
else
tr.hide();
});
};
})(jQuery);
</script>
<script>
$(document).ready(function() {
recipesTable = $('#recipestable')
upstreamStatus = $("<div/>").html('{{ upstream_status }}').text()
maintainer = $("<div/>").html('{{ maintainer_name }}').text()
search = '{{ search }}'
function updateQueryString(queryString) {
if (window.history.pushState) {
var newurl = window.location.protocol + "//" +
window.location.host + window.location.pathname +
queryString
window.history.pushState({path:newurl}, '', newurl);
}
}
function updateRecipeCount() {
$('#recipestable').show()
$('#no_recipes_alert').hide()
var count = 0;
$('tr:visible').each(function() {
count++
});
if (count == 1) {
$('#recipestable').hide()
$('#no_recipes_alert').show()
}
if (count == 2) {
$('#recipe-count').html("1 recipe");
} else {
$('#recipe-count').html((count - 1) + " recipes");
}
}
function updateStatusSelected() {
$("#selected-status strong").html(upstreamStatus)
statusList = document.getElementById("select-status").getElementsByTagName("li")
for (var i = 0; i < statusList.length; i++) {
if (statusList[i].textContent == upstreamStatus) {
$(statusList[i]).addClass("active")
} else {
$(statusList[i]).removeClass("active")
}
}
}
function updateMaintainerSelected() {
{% if maintplan.per_recipe_maintainers %}
$("#selected-maintainer strong").html(maintainer)
maintainerList = document.getElementById("select-maintainer").getElementsByTagName("li")
for (var i = 0; i < maintainerList.length; i++) {
if (maintainerList[i].textContent == maintainer) {
$(maintainerList[i]).addClass("active")
} else {
$(maintainerList[i]).removeClass("active")
}
}
{% endif %}
}
function applyFilters() {
if (upstreamStatus == 'Can\'t be updated') {
$('.no_update_reason_column').show()
$('.summary_column').hide()
} else {
$('.no_update_reason_column').hide()
$('.summary_column').show()
}
if (upstreamStatus == 'Up-to-date' || upstreamStatus == 'All') {
$('.upstream_version_column').hide();
} else {
$('.upstream_version_column').show();
}
if (upstreamStatus == 'All') {
upstreamStatusFilter = ''
} else {
upstreamStatusFilter = upstreamStatus
}
if (maintainer == 'All') {
maintainerFilter = ''
} else {
maintainerFilter = maintainer
}
$(recipesTable).multiFilter([
{ column: 'Upstream status', word: upstreamStatusFilter },
{ column: 'Maintainer', word: maintainerFilter },
]);
updateStatusSelected()
updateMaintainerSelected()
queryString = ''
if (search != '') {
var value = search.toLowerCase();
$("#recipestable > tbody > tr").filter(function() {
$(this).toggle($(this).text().toLowerCase().indexOf(value) > -1)
});
queryString = '?search=' + search
} else {
if (upstreamStatus != 'All' && maintainer != 'All') {
queryString = '?upstream_status=' + upstreamStatus +
'&maintainer_name=' + maintainer
} else if (upstreamStatus != 'All') {
queryString = '?upstream_status=' + upstreamStatus
} else if (maintainer != 'All') {
queryString = '?maintainer_name=' + maintainer
}
}
updateQueryString(queryString)
}
$("#form-search").submit(function( event ) {
upstreamStatus = 'All'
maintainer = 'All'
search = $("#filter").val()
$("#clear-search-btn").show()
applyFilters()
updateRecipeCount()
event.preventDefault();
});
function clearSearch() {
$("#filter").val('')
search = $("#filter").val()
$("#clear-search-btn").hide()
applyFilters()
updateRecipeCount()
}
$("#select-status a").click(function() {
upstreamStatus = this.text
clearSearch()
});
{% if maintplan.per_recipe_maintainers %}
$("#select-maintainer a").click(function() {
maintainer = this.text
clearSearch()
});
{% endif %}
$("#view-all-recipes").click(function() {
upstreamStatus = 'All'
maintainer = 'All'
clearSearch()
});
$("#clear-search-btn").click(function() {
upstreamStatus = 'All'
maintainer = 'All'
clearSearch()
});
$(".glyphicon-remove").tooltip( {container: 'body', html: true, title: "Clear search" });
{% if recipe_list_count > 0 %}
$(recipesTable).tablesorter({
sortList: [[0,0]],
headers: {
1: { sorter: false },
2: { sorter: false },
6: { sorter: false },
7: { sorter: false },
}
});
{% endif %}
if (search != '') {
$("#filter").val(search)
$("#clear-search-btn").show()
}
applyFilters()
updateRecipeCount()
});
</script>
{% endblock %}