scinote-web/app/assets/javascripts/sidebar.js

294 lines
8.6 KiB
JavaScript
Raw Normal View History

2018-07-19 23:56:42 +08:00
/**
* The functions here are global because they need to be
* accesed from outside (in reports view).
*/
2018-07-19 23:56:42 +08:00
/* global I18n _ */
(function(global) {
var STORAGE_TREE_KEY = 'scinote-sidebar-tree-collapsed-ids';
/**
* Get all collapsed sidebar elements.
* @return An array of sidebar element IDs.
*/
global.sessionGetCollapsedSidebarElements = function() {
var val = sessionStorage.getItem(STORAGE_TREE_KEY);
if (val === null) {
2018-07-19 23:56:42 +08:00
val = '[]';
sessionStorage.setItem(STORAGE_TREE_KEY, val);
2016-08-31 21:13:17 +08:00
}
return JSON.parse(val);
2018-07-19 23:56:42 +08:00
};
2016-08-31 21:13:17 +08:00
/**
* Collapse a specified element in the sidebar.
* @param id - The collapsed element's ID.
*/
global.sessionCollapseSidebarElement = function(project, id) {
2018-07-19 23:56:42 +08:00
var ids = global.sessionGetCollapsedSidebarElements();
var item = _.findWhere(ids, { prid: project });
var collapsed = { prid: project, ids: [] };
2018-07-19 23:56:42 +08:00
var storedProjects = _.pluck(ids, 'prid');
2018-07-19 23:56:42 +08:00
if (_.contains(storedProjects, project)) {
if (item && _.indexOf(item.ids, id) === -1) {
_.findWhere(ids, { prid: project }).ids.push(id);
}
} else {
collapsed.ids.push(id);
ids.push(collapsed);
}
2016-08-31 22:34:08 +08:00
sessionStorage.setItem(STORAGE_TREE_KEY, JSON.stringify(ids));
2018-07-19 23:56:42 +08:00
};
/**
* Expand a specified element in the sidebar.
* @param id - The expanded element's ID.
*/
global.sessionExpandSidebarElement = function(project, id, elements) {
2018-07-19 23:56:42 +08:00
var ids = global.sessionGetCollapsedSidebarElements();
var item = _.findWhere(ids, { prid: project});
var index = -1;
2018-07-19 23:56:42 +08:00
if (item) {
index = _.indexOf(item.ids, id);
2018-07-19 23:56:42 +08:00
global.recalculateElementsPositions(ids, item, elements);
}
2018-07-19 23:56:42 +08:00
if (index !== -1) {
item.ids.splice(index, 1);
sessionStorage.setItem(STORAGE_TREE_KEY, JSON.stringify(ids));
}
2018-07-19 23:56:42 +08:00
};
/**
* Recalculate the position of the elements after an experiment
* is added or archived.
*/
global.recalculateElementsPositions = function(ids, item, elements) {
var diff;
2018-07-19 23:56:42 +08:00
if (item.eleNum > elements) {
diff = item.eleNum - elements;
2018-07-19 23:56:42 +08:00
_.map(item.ids, function(element, index) {
item.ids[index] = element - diff;
});
2018-07-19 23:56:42 +08:00
} else if (item.eleNum < elements) {
diff = elements - item.eleNum;
_.map(item.ids, function(element, index) {
item.ids[index] = element + diff;
});
}
2018-07-19 23:56:42 +08:00
if (item.eleNum !== elements) {
item.eleNum = elements;
sessionStorage.setItem(STORAGE_TREE_KEY, JSON.stringify(ids));
2016-02-12 23:52:43 +08:00
}
}
/**
* Setup the sidebar collapsing & expanding functionality.
*/
global.setupSidebarTree = function() {
function toggleLi(el, collapse, animate) {
2018-07-19 23:56:42 +08:00
var children = el.find(' > ul > li');
2016-02-12 23:52:43 +08:00
if (collapse) {
if (animate) {
2018-07-19 23:56:42 +08:00
children.hide('fast');
} else {
children.hide();
}
2018-07-19 23:56:42 +08:00
el.find(' > span i')
.attr('title', I18n.t('sidebar.branch_expand'))
.removeClass('expanded');
2016-09-01 16:38:20 +08:00
} else {
if (animate) {
2018-07-19 23:56:42 +08:00
children.show('fast');
} else {
children.show();
}
2018-07-19 23:56:42 +08:00
el.find(' > span i')
.attr('title', I18n.t('sidebar.branch_collapse'))
.addClass('expanded');
2016-09-01 16:38:20 +08:00
}
}
// Make active current project/experiment/task
function activateCurrent() {
var sidebar = $('#slide-panel');
var projectId = sidebar.data('current-project');
var experimentId = sidebar.data('current-experiment');
var taskId = sidebar.data('current-task');
var currentPage = sidebar.data('page');
var li;
if (currentPage === 'project') {
li = sidebar.find('li[data-project-id="' + projectId + '"]');
} else if (currentPage === 'experiment') {
li = sidebar.find('[data-experiment-id="' + experimentId + '"]');
} else if (currentPage === 'canvas') {
li = sidebar.find('[data-experiment-id="' + experimentId + '"]');
li.find('.task-tree-link')
.append('<a href="" class="canvas-center-on">'
+ '<span class="fas fa-map-marker-alt"></span></a>');
} else if (currentPage === 'task') {
li = sidebar.find('[data-module-id="' + taskId + '"]');
}
li.find('a:first').addClass('disabled');
li.addClass('active');
}
activateCurrent();
// Add triangle icons and titles to every parent node
2018-07-19 23:56:42 +08:00
$('.tree li:has(ul)')
.addClass('parent_li')
.find(' > span i')
.attr('title', I18n.t('sidebar.branch_collapse'));
$('.tree li.parent_li ')
.find('> span i')
.removeClass('no-arrow')
.addClass('fas fa-caret-right expanded');
// Add IDs to all parent <lis>
var i = 0;
_.each($('[data-parent="candidate"]'), function(el) {
2018-07-19 23:56:42 +08:00
$(el).attr('data-toggle-id', i += 1);
2016-09-01 16:38:20 +08:00
});
// Get the current project
var project = $('[data-project-id]').data('projectId');
// Set number of elements
2018-07-19 23:56:42 +08:00
sessionExpandSidebarElement(
project, null, $('[data-parent="candidate"]').length
);
// Get the session-stored elements
2018-07-19 23:56:42 +08:00
var collapsedIds = global.sessionGetCollapsedSidebarElements();
// Get the current project stored elements
var currentProjectIds = _.findWhere(collapsedIds, { prid: project });
if ( currentProjectIds ){
currentProjectIds.ids = _.filter(currentProjectIds.ids,
function(val) {
return val !== null;
}).join(", ");
// Collapse session-stored elements
_.each($('li.parent_li[data-parent="candidate"]'), function(el) {
var id = $(el).data("toggle-id");
var li = $(".tree li.parent_li[data-toggle-id='" + id + "']");
if( li.hasClass("active") || li.find(".active").length > 0){
// Always expand the active element
toggleLi(li,
false,
false);
} else if ( $.inArray( id.toString(),
currentProjectIds.ids.split(", ")) !== -1 ) {
// Expande element
toggleLi(li,
false,
false);
} else {
// Collapse the session-stored element
toggleLi(li,
true,
false);
}
});
} else {
// Collapse all
_.each($('li.parent_li[data-parent="candidate"]'), function(el) {
var id = $(el).data("toggle-id");
var li = $(".tree li.parent_li[data-toggle-id='" + id + "']");
if( li.hasClass("active") ){
// Always expand the active element
toggleLi(li,
false,
false);
sessionCollapseSidebarElement(project, id);
} else {
// Element collapsed by default
toggleLi(li,
true,
false);
}
});
}
// Add onclick callback to every triangle icon
$(".tree li.parent_li ")
.find("> span i")
.on("click", function (e) {
var el = $(this)
.parent("span")
.parent("li.parent_li");
if (el.find(" > ul > li").is(":visible")) {
toggleLi(el, true, true);
sessionExpandSidebarElement(project,
el.data("toggle-id"),
$('[data-parent="candidate"]').length );
2016-09-01 16:38:20 +08:00
} else {
toggleLi(el, false, true);
sessionCollapseSidebarElement(project, el.data("toggle-id"));
2016-09-01 16:38:20 +08:00
}
e.stopPropagation();
return false;
2016-09-01 16:38:20 +08:00
});
// Add bold style to all levels of selected element
$(".tree li.active ")
.parents('.parent_li[data-parent="candidate"]')
.find("> span a")
.css("font-weight", "bold");
// Add custom borders to tree links
$(".tree li span.tree-link ").after("<div class='border-custom'></div>");
2016-09-01 16:38:20 +08:00
}
2016-02-12 23:52:43 +08:00
// Resize the sidebar to accomodate to the page size
global.resizeSidebarContents = function() {
var tree = $("#sidebar-wrapper .tree");
// Set vertical scrollbar on navigation tree
if (tree.length && tree.length == 1) {
tree.css(
"height",
($(window).height() - tree.position().top - 50) + "px"
);
2016-02-12 23:52:43 +08:00
}
}
2018-03-22 18:41:33 +08:00
function scrollToSelectedItem() {
2018-07-19 23:56:42 +08:00
var offset;
if ($('#slide-panel .active').length) {
offset = $('#slide-panel .active').offset().top - 50;
if (offset < 0) offset = 0;
2018-07-19 23:56:42 +08:00
$('#slide-panel .tree').scrollTo(offset, 10);
}
2016-02-12 23:52:43 +08:00
}
// Initialize click listeners
setupSidebarTree();
// Actually display wrapper, which is, up to now,
// hidden
2018-07-19 23:56:42 +08:00
$('#wrapper').show();
2016-02-12 23:52:43 +08:00
// Resize the sidebar automatically
resizeSidebarContents();
// Bind onto window resize function
$(window).resize(function() {
resizeSidebarContents();
2018-07-19 23:56:42 +08:00
scrollToSelectedItem();
2016-02-12 23:52:43 +08:00
});
2018-07-19 23:56:42 +08:00
scrollToSelectedItem();
}(window));