I have a open function that once triggered, simply plays video in a dedicated panel.
This function can be triggered in two ways - one with a click and another one with a page load (window load) with url that contains a valid anchor tag.
They all work fine but some codes of the window load handler are repetitive and I'm not too sure how I can keep this DRY.
Please take a look and point me in some directions on how I can write this better.
I commented in open function which is for which.
$.videoWatch.prototype = {
init: function() {
this.$openLinks = this.$element.find(".open");
this.$closeLinks = this.$element.find(".close");
this.open();
this.close();
},
_getContent: function(element) {
var $parent = element.parent(),
id = element.attr('href').substring(1),
title = $parent.data('title'),
desc = $parent.data('desc');
return {
title: title,
desc: desc,
id: id
}
},
open: function() {
var self = this;
//open theatre with window load with #hash id
window.onload = function() {
var hash = location.hash;
var $a = $('a[href="' + hash + '"]'),
content = self._getContent($a),
$li = $a.parents("li"),
$theatreVideo = $(".playing"),
$theatreTitle = $(".theatre-title"),
$theatreText = $(".theatre-text");
$(".theatre").attr('id', content.id);
$theatreTitle.text(content.title);
$theatreText.text(content.desc);
if ($theatreText.text().length >= 90) {
$(".theatre-text").css({
'overflow': 'hidden',
'max-height': '90px',
});
$moreButton.insertAfter($theatreText);
}
$a.parent().addClass("active");
$(".theatre").insertAfter($li);
$(".theatre").slideDown('fast', scrollToTheatre);
oldIndex = $li.index();
}
//open theatre with click event
self.$openLinks.on("click", function(e) {
// e.preventDefault();
if (curID == $(this).parent().attr("id")) {
$("figure").removeClass("active");
$("button.more").remove();
$(".theatre").slideUp('fast');
$('.playing').attr("src", "");
removeHash();
oldIndex = -1;
curID = "";
return false
} else {
curID = $(this).parent().attr("id");
}
var $a = $(this),
content = self._getContent($a),
$li = $a.parents("li"),
$theatreVideo = $(".playing"),
$theatreTitle = $(".theatre-title"),
$theatreText = $(".theatre-text");
$(".theatre").attr('id', content.id);
$theatreTitle.text(content.title);
$theatreText.text(content.desc);
if ($theatreText.text().length >= 90) {
$(".theatre-text").css({
'overflow': 'hidden',
'max-height': '90px',
});
$moreButton.insertAfter($theatreText);
}
if (!($li.index() == oldIndex)) {
$("figure").removeClass("active");
$(".theatre").hide(function(){
$a.parent().addClass("active");
$(".theatre").insertAfter($li);
$(".theatre").slideDown('fast', scrollToTheatre);
oldIndex = $li.index();
});
} else {
$(".theatre").insertAfter($li);
scrollToTheatre();
$("figure").removeClass("active");
$a.parent().addClass("active");
}
});
},
...
Simplified and refactored open method:
open: function() {
var self = this;
var serviceObj = {
theatreVideo : $(".playing"),
theatre: $(".theatre"),
theatreTitle : $(".theatre-title"),
theatreText : $(".theatre-text"),
setTheatreContent: function(content){
this.theatre.attr('id', content.id);
this.theatreTitle.text(content.title);
this.theatreText.text(content.desc);
if (this.theatreText.text().length >= 90) {
this.theatreText.css({
'overflow': 'hidden',
'max-height': '90px',
});
$moreButton.insertAfter(this.theatreText);
}
},
activateTeatre: function(a, li){
a.parent().addClass("active");
this.theatre.insertAfter(li);
this.theatre.slideDown('fast', scrollToTheatre);
oldIndex = li.index();
}
};
//open theatre with window load with #hash id
window.onload = function() {
var hash = location.hash;
var $a = $('a[href="' + hash + '"]'),
content = self._getContent($a),
$li = $a.parents("li");
serviceObj.setTheatreContent(content);
serviceObj.activateTeatre($a, $li);
}
//open theatre with click event
self.$openLinks.on("click", function(e) {
// e.preventDefault();
if (curID == $(this).parent().attr("id")) {
$("figure").removeClass("active");
$("button.more").remove();
$(".theatre").slideUp('fast');
$('.playing').attr("src", "");
removeHash();
oldIndex = -1;
curID = "";
return false
} else {
curID = $(this).parent().attr("id");
}
var $a = $(this),
content = self._getContent($a),
$li = $a.parents("li");
serviceObj.setTheatreContent(content);
if (!($li.index() == oldIndex)) {
$("figure").removeClass("active");
$(".theatre").hide(function(){
serviceObj.activateTeatre($a, $li);
});
} else {
$(".theatre").insertAfter($li);
scrollToTheatre();
$("figure").removeClass("active");
$a.parent().addClass("active");
}
});
},
1st of all there are variables that don't depend on the input, you could pull them to the class (I'll show just one example, as you asked for directions):
init: function() {
this.$theatreVideo = $(".playing");
All the variables that do depend on the input, like $li could be moved to a function:
var $a = $(this),
$dependsOnA = self.dependsOnA($a);
self.actionDependsOnA($dependsOnA); // see below
function dependsOnA($a) {
return {
a: $a,
li: $a.parents("li"),
content: self._getContent($a)
}
}
Also the code that "repeats" can be moved to a function:
function actionDependsOnA($dependsOnA)
$(".theatre").attr('id', $dependsOnA.content.id);
$theatreTitle.text($dependsOnA.content.title);
$theatreText.text($dependsOnA.content.desc);
}
I am trying to use https://github.com/philogb/jit to create a treemap of data coming from top. The data looks like:
"{"rsyslogd":{"children":[{"children":[],"data":{"PID":"17670","$color":"#D40106","cmdinfo":"<br><b>USER</b>:syslog<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:383m<br><b>RES</b>:5412<br><b>SHR</b>:1108<br><b>S</b>:S<br><b>CPU</b>:177%<br>%<b>MEM</b>:0.3%<br><b>TIME+</b>:32230:25<br>","$area":4},"id":"proc-1-17670","name":"rsyslogd"}],"data":{"PID":"rsyslogd","$area":50},"id":"proc-rsyslogd","name":"rsyslogd(1)"},"init":{"children":[{"children":[],"data":{"PID":"1","$color":"#0EAB06","cmdinfo":"<br><b>USER</b>:root<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:23584<br><b>RES</b>:1324<br><b>SHR</b>:1044<br><b>S</b>:S<br><b>CPU</b>:0%<br>%<b>MEM</b>:0.1%<br><b>TIME+</b>:0:00.10<br>","$area":2},"id":"proc-1-1","name":"init"}],"data":{"PID":"init","$area":30},"id":"proc-init","name":"init(1)"},"dbus-daemon":{"children":[{"children":[],"data":{"PID":"88","$color":"#0EAB06","cmdinfo":"<br><b>USER</b>:messageb<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:23556<br><b>RES</b>:328<br><b>SHR</b>:324<br><b>S</b>:S<br><b>CPU</b>:0%<br>%<b>MEM</b>:0.0%<br><b>TIME+</b>:0:00.00<br>","$area":1},"id":"proc-1-88","name":"dbus-daemon"}],"data":{"PID":"dbus-daemon","$area":20},"id":"proc-dbus-daemon","name":"dbus-daemon(1)"},"sshd":{"children":[{"children":[],"data":{"PID":"183","$color":"#0EAB06","cmdinfo":"<br><b>USER</b>:root<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:49436<br><b>RES</b>:1640<br><b>SHR</b>:1528<br><b>S</b>:S<br><b>CPU</b>:0%<br>%<b>MEM</b>:0.1%<br><b>TIME+</b>:0:00.14<br>","$area":2},"id":"proc-1-183","name":"sshd"}],"data":{"PID":"sshd","$area":30},"id":"proc-sshd","name":"sshd(1)"},"cron":{"children":[{"children":[],"data":{"PID":"209","$color":"#0EAB06","cmdinfo":"<br><b>USER</b>:root<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:18900<br><b>RES</b>:704<br><b>SHR</b>:628<br><b>S</b>:S<br><b>CPU</b>:0%<br>%<b>MEM</b>:0.0%<br><b>TIME+</b>:0:01.34<br>","$area":1},"id":"proc-1-209","name":"cron"}],"data":{"PID":"cron","$area":20},"id":"proc-cron","name":"cron(1)"},"mysqld":{"children":[{"children":[],"data":{"PID":"240","$color":"#0EAB06","cmdinfo":"<br><b>USER</b>:mysql<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:334m<br><b>RES</b>:49m<br><b>SHR</b>:3988<br><b>S</b>:S<br><b>CPU</b>:0%<br>%<b>MEM</b>:3.2%<br><b>TIME+</b>:58:21.44<br>","$area":33},"id":"proc-1-240","name":"mysqld"}],"data":{"PID":"mysqld","$area":340},"id":"proc-mysqld","name":"mysqld(1)"},"sendmail-mta":{"children":[{"children":[],"data":{"PID":"317","$color":"#0EAB06","cmdinfo":"<br><b>USER</b>:root<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:68284<br><b>RES</b>:844<br><b>SHR</b>:648<br><b>S</b>:S<br><b>CPU</b>:0%<br>%<b>MEM</b>:0.1%<br><b>TIME+</b>:0:31.61<br>","$area":2},"id":"proc-1-317","name":"sendmail-mta"}],"data":{"PID":"sendmail-mta","$area":30},"id":"proc-sendmail-mta","name":"sendmail-mta(1)"},"apache2":{"children":[{"children":[],"data":{"PID":"372","$color":"#0EAB06","cmdinfo":"<br><b>USER</b>:root<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:342m<br><b>RES</b>:8404<br><b>SHR</b>:5412<br><b>S</b>:S<br><b>CPU</b>:0%<br>%<b>MEM</b>:0.5%<br><b>TIME+</b>:0:50.46<br>","$area":6},"id":"proc-1-372","name":"apache2"},{"children":[],"data":{"PID":"24804","$color":"#0EAB06","cmdinfo":"<br><b>USER</b>:www-data<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:369m<br><b>RES</b>:81m<br><b>SHR</b>:56m<br><b>S</b>:S<br><b>CPU</b>:0%<br>%<b>MEM</b>:5.3%<br><b>TIME+</b>:0:07.93<br>","$area":54},"id":"proc-1-24804","name":"apache2"},{"children":[],"data":{"PID":"24821","$color":"#0EAB06","cmdinfo":"<br><b>USER</b>:www-data<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:366m<br><b>RES</b>:66m<br><b>SHR</b>:41m<br><b>S</b>:S<br><b>CPU</b>:0%<br>%<b>MEM</b>:4.3%<br><b>TIME+</b>:0:06.27<br>","$area":44},"id":"proc-1-24821","name":"apache2"},{"children":[],"data":{"PID":"24828","$color":"#0EAB06","cmdinfo":"<br><b>USER</b>:www-data<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:359m<br><b>RES</b>:71m<br><b>SHR</b>:53m<br><b>S</b>:S<br><b>CPU</b>:0%<br>%<b>MEM</b>:4.7%<br><b>TIME+</b>:0:06.39<br>","$area":48},"id":"proc-1-24828","name":"apache2"},{"children":[],"data":{"PID":"24832","$color":"#0EAB06","cmdinfo":"<br><b>USER</b>:www-data<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:361m<br><b>RES</b>:70m<br><b>SHR</b>:52m<br><b>S</b>:S<br><b>CPU</b>:0%<br>%<b>MEM</b>:4.6%<br><b>TIME+</b>:0:04.18<br>","$area":47},"id":"proc-1-24832","name":"apache2"},{"children":[],"data":{"PID":"24860","$color":"#0EAB06","cmdinfo":"<br><b>USER</b>:www-data<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:368m<br><b>RES</b>:77m<br><b>SHR</b>:53m<br><b>S</b>:S<br><b>CPU</b>:0%<br>%<b>MEM</b>:5.1%<br><b>TIME+</b>:0:06.15<br>","$area":52},"id":"proc-1-24860","name":"apache2"},{"children":[],"data":{"PID":"24862","$color":"#0EAB06","cmdinfo":"<br><b>USER</b>:www-data<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:361m<br><b>RES</b>:58m<br><b>SHR</b>:41m<br><b>S</b>:S<br><b>CPU</b>:0%<br>%<b>MEM</b>:3.8%<br><b>TIME+</b>:0:03.86<br>","$area":39},"id":"proc-1-24862","name":"apache2"},{"children":[],"data":{"PID":"24878","$color":"#0EAB06","cmdinfo":"<br><b>USER</b>:www-data<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:359m<br><b>RES</b>:51m<br><b>SHR</b>:34m<br><b>S</b>:S<br><b>CPU</b>:0%<br>%<b>MEM</b>:3.4%<br><b>TIME+</b>:0:01.54<br>","$area":35},"id":"proc-1-24878","name":"apache2"},{"children":[],"data":{"PID":"24882","$color":"#0EAB06","cmdinfo":"<br><b>USER</b>:www-data<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:362m<br><b>RES</b>:53m<br><b>SHR</b>:34m<br><b>S</b>:S<br><b>CPU</b>:0%<br>%<b>MEM</b>:3.5%<br><b>TIME+</b>:0:01.60<br>","$area":36},"id":"proc-1-24882","name":"apache2"},{"children":[],"data":{"PID":"24885","$color":"#0EAB06","cmdinfo":"<br><b>USER</b>:www-data<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:366m<br><b>RES</b>:61m<br><b>SHR</b>:38m<br><b>S</b>:S<br><b>CPU</b>:0%<br>%<b>MEM</b>:4.0%<br><b>TIME+</b>:0:02.65<br>","$area":41},"id":"proc-1-24885","name":"apache2"},{"children":[],"data":{"PID":"24887","$color":"#0EAB06","cmdinfo":"<br><b>USER</b>:www-data<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:366m<br><b>RES</b>:73m<br><b>SHR</b>:50m<br><b>S</b>:S<br><b>CPU</b>:0%<br>%<b>MEM</b>:4.8%<br><b>TIME+</b>:0:02.04<br>","$area":49},"id":"proc-1-24887","name":"apache2"},{"children":[],"data":{"PID":"24888","$color":"#0EAB06","cmdinfo":"<br><b>USER</b>:www-data<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:363m<br><b>RES</b>:60m<br><b>SHR</b>:36m<br><b>S</b>:S<br><b>CPU</b>:0%<br>%<b>MEM</b>:3.9%<br><b>TIME+</b>:0:02.34<br>","$area":40},"id":"proc-1-24888","name":"apache2"},{"children":[],"data":{"PID":"24889","$color":"#0EAB06","cmdinfo":"<br><b>USER</b>:www-data<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:363m<br><b>RES</b>:61m<br><b>SHR</b>:39m<br><b>S</b>:S<br><b>CPU</b>:0%<br>%<b>MEM</b>:4.0%<br><b>TIME+</b>:0:02.81<br>","$area":41},"id":"proc-1-24889","name":"apache2"},{"children":[],"data":{"PID":"24892","$color":"#0EAB06","cmdinfo":"<br><b>USER</b>:www-data<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:356m<br><b>RES</b>:47m<br><b>SHR</b>:33m<br><b>S</b>:S<br><b>CPU</b>:0%<br>%<b>MEM</b>:3.1%<br><b>TIME+</b>:0:02.60<br>","$area":32},"id":"proc-1-24892","name":"apache2"},{"children":[],"data":{"PID":"24893","$color":"#0EAB06","cmdinfo":"<br><b>USER</b>:www-data<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:355m<br><b>RES</b>:49m<br><b>SHR</b>:33m<br><b>S</b>:S<br><b>CPU</b>:0%<br>%<b>MEM</b>:3.2%<br><b>TIME+</b>:0:01.70<br>","$area":33},"id":"proc-1-24893","name":"apache2"},{"children":[],"data":{"PID":"24897","$color":"#0EAB06","cmdinfo":"<br><b>USER</b>:www-data<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:363m<br><b>RES</b>:62m<br><b>SHR</b>:38m<br><b>S</b>:S<br><b>CPU</b>:0%<br>%<b>MEM</b>:4.1%<br><b>TIME+</b>:0:02.44<br>","$area":42},"id":"proc-1-24897","name":"apache2"},{"children":[],"data":{"PID":"24900","$color":"#0EAB06","cmdinfo":"<br><b>USER</b>:www-data<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:365m<br><b>RES</b>:63m<br><b>SHR</b>:39m<br><b>S</b>:S<br><b>CPU</b>:0%<br>%<b>MEM</b>:4.1%<br><b>TIME+</b>:0:01.82<br>","$area":42},"id":"proc-1-24900","name":"apache2"},{"children":[],"data":{"PID":"24903","$color":"#0EAB06","cmdinfo":"<br><b>USER</b>:www-data<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:364m<br><b>RES</b>:56m<br><b>SHR</b>:36m<br><b>S</b>:S<br><b>CPU</b>:0%<br>%<b>MEM</b>:3.7%<br><b>TIME+</b>:0:03.43<br>","$area":38},"id":"proc-1-24903","name":"apache2"},{"children":[],"data":{"PID":"24924","$color":"#0EAB06","cmdinfo":"<br><b>USER</b>:www-data<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:365m<br><b>RES</b>:61m<br><b>SHR</b>:37m<br><b>S</b>:S<br><b>CPU</b>:0%<br>%<b>MEM</b>:4.0%<br><b>TIME+</b>:0:02.13<br>","$area":41},"id":"proc-1-24924","name":"apache2"},{"children":[],"data":{"PID":"24926","$color":"#0EAB06","cmdinfo":"<br><b>USER</b>:www-data<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:362m<br><b>RES</b>:51m<br><b>SHR</b>:33m<br><b>S</b>:S<br><b>CPU</b>:0%<br>%<b>MEM</b>:3.3%<br><b>TIME+</b>:0:00.81<br>","$area":34},"id":"proc-1-24926","name":"apache2"},{"children":[],"data":{"PID":"24930","$color":"#0EAB06","cmdinfo":"<br><b>USER</b>:www-data<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:367m<br><b>RES</b>:61m<br><b>SHR</b>:36m<br><b>S</b>:S<br><b>CPU</b>:0%<br>%<b>MEM</b>:4.0%<br><b>TIME+</b>:0:01.32<br>","$area":41},"id":"proc-1-24930","name":"apache2"},{"children":[],"data":{"PID":"24933","$color":"#0EAB06","cmdinfo":"<br><b>USER</b>:www-data<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:355m<br><b>RES</b>:44m<br><b>SHR</b>:30m<br><b>S</b>:S<br><b>CPU</b>:0%<br>%<b>MEM</b>:2.9%<br><b>TIME+</b>:0:00.56<br>","$area":30},"id":"proc-1-24933","name":"apache2"},{"children":[],"data":{"PID":"24935","$color":"#0EAB06","cmdinfo":"<br><b>USER</b>:www-data<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:353m<br><b>RES</b>:39m<br><b>SHR</b>:24m<br><b>S</b>:S<br><b>CPU</b>:0%<br>%<b>MEM</b>:2.5%<br><b>TIME+</b>:0:00.28<br>","$area":26},"id":"proc-1-24935","name":"apache2"},{"children":[],"data":{"PID":"24936","$color":"#0EAB06","cmdinfo":"<br><b>USER</b>:www-data<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:359m<br><b>RES</b>:52m<br><b>SHR</b>:33m<br><b>S</b>:S<br><b>CPU</b>:0%<br>%<b>MEM</b>:3.4%<br><b>TIME+</b>:0:00.98<br>","$area":35},"id":"proc-1-24936","name":"apache2"},{"children":[],"data":{"PID":"24939","$color":"#0EAB06","cmdinfo":"<br><b>USER</b>:www-data<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:354m<br><b>RES</b>:41m<br><b>SHR</b>:27m<br><b>S</b>:S<br><b>CPU</b>:0%<br>%<b>MEM</b>:2.7%<br><b>TIME+</b>:0:00.28<br>","$area":28},"id":"proc-1-24939","name":"apache2"},{"children":[],"data":{"PID":"24941","$color":"#0EAB06","cmdinfo":"<br><b>USER</b>:www-data<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:362m<br><b>RES</b>:57m<br><b>SHR</b>:34m<br><b>S</b>:S<br><b>CPU</b>:0%<br>%<b>MEM</b>:3.7%<br><b>TIME+</b>:0:00.43<br>","$area":38},"id":"proc-1-24941","name":"apache2"},{"children":[],"data":{"PID":"24942","$color":"#0EAB06","cmdinfo":"<br><b>USER</b>:www-data<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:357m<br><b>RES</b>:41m<br><b>SHR</b>:26m<br><b>S</b>:S<br><b>CPU</b>:0%<br>%<b>MEM</b>:2.7%<br><b>TIME+</b>:0:00.31<br>","$area":28},"id":"proc-1-24942","name":"apache2"},{"children":[],"data":{"PID":"24943","$color":"#0EAB06","cmdinfo":"<br><b>USER</b>:www-data<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:346m<br><b>RES</b>:16m<br><b>SHR</b>:8604<br><b>S</b>:S<br><b>CPU</b>:0%<br>%<b>MEM</b>:1.1%<br><b>TIME+</b>:0:00.09<br>","$area":12},"id":"proc-1-24943","name":"apache2"},{"children":[],"data":{"PID":"24944","$color":"#0EAB06","cmdinfo":"<br><b>USER</b>:www-data<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:351m<br><b>RES</b>:34m<br><b>SHR</b>:21m<br><b>S</b>:S<br><b>CPU</b>:0%<br>%<b>MEM</b>:2.3%<br><b>TIME+</b>:0:00.18<br>","$area":24},"id":"proc-1-24944","name":"apache2"},{"children":[],"data":{"PID":"24945","$color":"#0EAB06","cmdinfo":"<br><b>USER</b>:www-data<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:363m<br><b>RES</b>:67m<br><b>SHR</b>:43m<br><b>S</b>:S<br><b>CPU</b>:0%<br>%<b>MEM</b>:4.4%<br><b>TIME+</b>:0:00.99<br>","$area":45},"id":"proc-1-24945","name":"apache2"},{"children":[],"data":{"PID":"24946","$color":"#0EAB06","cmdinfo":"<br><b>USER</b>:www-data<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:342m<br><b>RES</b>:5552<br><b>SHR</b>:1800<br><b>S</b>:S<br><b>CPU</b>:0%<br>%<b>MEM</b>:0.4%<br><b>TIME+</b>:0:00.03<br>","$area":5},"id":"proc-1-24946","name":"apache2"},{"children":[],"data":{"PID":"24950","$color":"#0EAB06","cmdinfo":"<br><b>USER</b>:www-data<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:360m<br><b>RES</b>:48m<br><b>SHR</b>:30m<br><b>S</b>:S<br><b>CPU</b>:0%<br>%<b>MEM</b>:3.2%<br><b>TIME+</b>:0:00.39<br>","$area":33},"id":"proc-1-24950","name":"apache2"}],"data":{"PID":"apache2","$area":11400},"id":"proc-apache2","name":"apache2(32)"},"newrelic-daemon":{"children":[{"children":[],"data":{"PID":"399","$color":"#0EAB06","cmdinfo":"<br><b>USER</b>:root<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:16232<br><b>RES</b>:292<br><b>SHR</b>:288<br><b>S</b>:S<br><b>CPU</b>:0%<br>%<b>MEM</b>:0.0%<br><b>TIME+</b>:0:00.00<br>","$area":1},"id":"proc-1-399","name":"newrelic-daemon"},{"children":[],"data":{"PID":"400","$color":"#0EAB06","cmdinfo":"<br><b>USER</b>:root<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:264m<br><b>RES</b>:7284<br><b>SHR</b>:2360<br><b>S</b>:S<br><b>CPU</b>:0%<br>%<b>MEM</b>:0.5%<br><b>TIME+</b>:40:33.01<br>","$area":6},"id":"proc-1-400","name":"newrelic-daemon"}],"data":{"PID":"newrelic-daemon","$area":80},"id":"proc-newrelic-daemon","name":"newrelic-daemon(2)"},"top":{"children":[{"children":[],"data":{"PID":"24988","$color":"#0EAB06","cmdinfo":"<br><b>USER</b>:root<br><b>PR</b>:20<br><b>NI</b>:0<br><b>VIRT</b>:19196<br><b>RES</b>:1328<br><b>SHR</b>:1048<br><b>S</b>:R<br><b>CPU</b>:0%<br>%<b>MEM</b>:0.1%<br><b>TIME+</b>:0:00.00<br>","$area":2},"id":"proc-1-24988","name":"top"}],"data":{"PID":"top","$area":30},"id":"proc-top","name":"top(1)"}}"
I then convert this into a JavaScript Object using JSON.parse(...) and assign it to data .
Then the actual InfoVis code:
function getCanvasConfig() {
var ua = navigator.userAgent,
iStuff = ua.match(/iPhone/i) || ua.match(/iPad/i),
typeOfCanvas = typeof HTMLCanvasElement,
nativeCanvasSupport = (typeOfCanvas == 'object' || typeOfCanvas == 'function'),
textSupport = nativeCanvasSupport
&& (typeof document.createElement('canvas').getContext('2d').fillText == 'function');
//I'm setting this based on the fact that ExCanvas provides text support for IE
//and that as of today iPhone/iPad current text support is lame
return {
labelType: (!nativeCanvasSupport || (textSupport && !iStuff))? 'Native' : 'HTML',
nativeTextSupport: (!nativeCanvasSupport || (textSupport && !iStuff)),
useGradients: nativeCanvasSupport,
animate: !(iStuff || !nativeCanvasSupport)
};
}
var config = getCanvasConfig();
var attrs = {id: "infovis"};
var tmConfig = {
//where to inject the visualization
injectInto: attrs.id,
//parent box title heights
titleHeight: 15,
//enable animations
animate: config.animate,
//box offsets
offset: 1,
//Attach left and right click events
Events: {
enable: true,
onClick: function(node) {
if(node) tm.enter(node);
},
onRightClick: function() {
tm.out();
}
},
duration: 1000,
//Enable tips
Tips: {
enable: true,
//add positioning offsets
offsetX: 20,
offsetY: 20,
//implement the onShow method to
//add content to the tooltip when a node
//is hovered
onShow: function(tip, node, isLeaf, domElement) {
var html = "<div class=\"tip-title\">" + node.name
+ "</div><div class=\"tip-text\">";
var data = node.data;
if(data.PID) {
html += "<br><b>PID</b>: " + data.PID;
}
if(data.cmdinfo) {
html += ""+ data.cmdinfo +"";
}
tip.innerHTML = html;
}
},
//Add the name of the node in the correponding label
//This method is called once, on label creation.
onCreateLabel: function(domElement, node){
domElement.innerHTML = node.name;
var data = node.data;
var PID = data.PID;
var style = domElement.style;
style.display = '';
style.border = '1px solid transparent';
domElement.onclick = function() {
$('input#PIDtext').val(PID);
};
domElement.onmouseover = function() {
style.border = '1px solid #efefef';
};
domElement.onmouseout = function() {
style.border = '1px solid transparent';
};
}
};
var tm = new $jit.TM.Squarified(tmConfig);
tm.loadJSON(data);
tm.refresh();
However, all I keep getting is "undefined" injected into the canvas. Any clues?
Just leaving this here:
The problem was with the data. I need to have a root node with appropriate name & ID that had the rest of the data as children.
I'm trying to develop a jQuery plugin to display adaptive image galleries. I'm using .data() to store the information for each slide of the gallery.
Everything appears to be working okay when displaying a single gallery, but gets mixed up when trying to have multiple gallery instances on a single page. A rough demo can be viewed here.
Here is the code that is being run:
(function($) {
$.Gallery = function(element, options) {
this.$el = $(element);
this._init(options);
};
$.Gallery.defaults = {
showCarousel : true,
};
$.Gallery.prototype = {
_init : function(options) {
var $this = $(this);
var instance = this;
// Get settings from stored instance
var settings = $this.data('settings');
var slides = $this.data('slides');
// Create or update the settings of the current gallery instance
if (typeof(settings) == 'undefined') {
settings = $.extend(true, {}, $.Gallery.defaults, options);
}
else {
settings = $.extend(true, {}, settings, options);
}
$this.data('settings', settings);
if (typeof(slides) === 'undefined') {
slides = [];
}
$this.data('slides', slides);
instance.updateCarousel();
},
addItems : function(newItems) {
var $this = $(this),
slides = $this.data('slides');
for (var i=0; i<newItems.length; i++) {
slides.push(newItems[i]);
};
},
updateCarousel : function() {
var instance = this,
$this = $(this);
slides = $(instance).data('slides');
var gallery = instance.$el.attr('id');
/* Create carousel if it doesn't exist */
if (instance.$el.children('.carousel').length == 0) {
$('<div class="carousel"><ul></ul></div>').appendTo(instance.$el);
var image = instance.$el.find('img');
};
var carouselList = instance.$el.find('.carousel > ul'),
slideCount = slides.length,
displayCount = carouselList.find('li').length;
if (displayCount < slideCount) {
for (var i=displayCount; i<slides.length; i++) {
slides[i].id = gallery + '-slide-' + i;
slide = $('<img>').attr({src : slides[i].thumb}).appendTo(carouselList).wrap(function() {
return '<li id="' + slides[i].id + '" />'
});
slide.on({
click : function() {
instance.slideTo($(this).parent().attr('id'));
},
});
};
};
},
slideTo : function(slideID) {
var $this = $(this);
var slides = $this.data('slides');
var image;
var $instance = $(this.$el);
$(slides).each( function() {
if (this.id == slideID){
image = this.img;
};
});
$('<img/>').load( function() {
$instance.find('div.image').empty().append('<img src="' + image + '"/>');
}).attr( 'src', image );
},
};
$.fn.gallery = function(options) {
args = Array.prototype.slice.call(arguments, 1);
this.each(function() {
var instance = $(this).data('gallery');
if (typeof(options) === 'string') {
if (!instance) {
console.error('Methods cannot be called until jquery.responsiveGallery has been initialized.');
}
else if (!$.isFunction(instance[options])) {
console.error('The method "' + options + '" does not exist in jquery.responsiveGallery.');
}
else {
instance[options].apply(instance, args);
}
}
else {
if (!instance) {
$(this).data('gallery', new $.Gallery(this, options));
}
}
});
return this;
};
})(jQuery);
$(window).load(function() {
$('#gallery2').gallery();
$('#gallery3').gallery();
$('#gallery2').gallery('addItems', [
{
img: 'images/image2.jpg',
thumb: 'images/image2_thumb.jpg',
desc: 'Image of number 2'
},
{
img: 'images/image3.jpg',
thumb: 'images/image3_thumb.jpg',
desc: 'Image of number 3'
},
{
img: 'images/image4.jpg',
thumb: 'images/image4_thumb.jpg',
desc: 'Image of number 4'
},
{
img: 'images/image5.jpg',
thumb: 'images/image5_thumb.jpg',
desc: 'Image of number 5'
}
]);
$('.pGallery').gallery('addItems', [
{
img: 'images/2.jpg',
thumb: 'images/2_thumb.jpg',
desc: 'Image of number 0'
},
{
img: 'images/image1.jpg',
thumb: 'images/image1_thumb.jpg',
desc: 'The second image'
}
]);
$('.pGallery').gallery('updateCarousel');
});
On the surface it appears to create two galleries with the proper slide structure of:
gallery2
gallery2-slide-0
gallery2-slide-1
gallery2-slide-2
gallery2-slide-3
gallery2-slide-4
gallery2-slide-5
gallery3
gallery3-slide-0
gallery3-slide-1
However, the onclick action doesn't work for the last two slides of Gallery2 (the slides duplicated in both galleries). Upon closer inspection of the DOM, I can see that the slides stored in data for gallery2, have the following ids:
gallery2
gallery2-slide-0
gallery2-slide-1
gallery2-slide-2
gallery2-slide-3
gallery3-slide-0
gallery3-slide-1
I'm not sure what is causing the mix-up or how to fix, so any help would be greatly appreciated.
Thanks
Your problem is that calling $('.pGallery').gallery('addItems'... cause the same objects to be added to the internal structure of both galleries, when you call $('.pGallery').gallery('updateCarousel'); the ids stored in those objects are overwritten.
You need to put a copy of the original objects in there. Do:
addItems : function(newItems) {
var $this = $(this),
slides = $this.data('slides');
for (var i=0; i<newItems.length; i++) {
//slides.push(newItems[i]);
slides.push(jQuery.extend({}, newItems[i]));
};
},
With jQuery.extend({}, oldObject) you can perform a shallow copy;