Donnerstag, 22. August 2013
Mein Raspberry Pi, welcher ein 24″ Dashboard speist, hat sich in den letzten Tagen vermehrt aufgehängt. Dies mag mit einer Aktualisierung der Dashboard-Software zusammenhängen, insbesondere wohl mit Anpassungen am JavaScript-Code.
Ich setze jQuery als JavaScript-Framework ein und steure damit einige visuelle Gimmicks; beispielsweise schwarze Eselsohren an aktualisierten Tiles, welche innert 30 Sekunden nach der Aktualisierung verblassen und dann ganz verschwinden. Auch wird das Doppelpunkt der Zeitanzeige (HH:MM) so animiert, dass es jede zweite Sekunde ausgeblendet wird.
Dies scheint dazu geführt zu haben, dass die schwachbrüstige CPU des Raspberry Pis voll ausgelastet war. Der Browser Midori, welcher als Vollbild läuft, beanspruchte teilweise bis zu 50% CPU-Last und auch das X-Window-System wieso ähnlich hohe Werte auf. Die Load Average des Raspberry Pis war über 1.
Ich entschied mich deshalb, in den JavaScript-Code eine Weiche einzubauen, welche die grafischen Animationen für schwachbrünstige Browser/Systeme auf ein Minimum beschränkte.
Leider hatte die jQuery-eigenen Konfigurationseinstellung Kollateralschäden zur Folge, weshalb ich den Code selber optimieren musste:
jQuery.fx.off = true;
… funktionierte nicht zufriedenstellend.
Nachfolgend einige Konstrukte, die seit gestern Abend in der Produktion laufen:
Browser-Weiche
var browserIsPerformant = true;
if(navigator.userAgent.match(/(Midori)/)) {
browserIsPerformant = false;
}
Delay statt FadeOuts
An den zwei Orten, wo ich schnelle (250ms – eine Viertelsekunde) und langsame (30000ms – 30 Sekunden) FadeOuts implementiert hatte, baute ich mit der Variable browserIsPerformant eine Weiche ein. jQuery kennt die .delay()-Funktion, mit welcher Aktionen für eine benutzerdefinierte Zeit (Millisekunden) hinausgezögert werden können. Damit konnte ich sicherstellen, dass die Effekte sowohl in der abgespeckten als auch in der Vollversion des Dashboards zur selben Zeit endeten.
Leider kann .delay() nicht auf .toggle(), .show() und .hide() angewendet werden.
Eselsohren
if(browserIsPerformant) {
$(obj).children('.updated').fadeToggle(30000);
}
else {
$(obj).children('.updated').delay(30000).fadeOut(1);
}
Indem ich im else-Abschnitt den Delay auf 30 Sekunden setzte und den fadeOut auf 1 Millisekunde, ergab sich unter Midori neu keine Performance-Einbusse mehr.
Sekundenanzeige (Doppelpunkte)
if(browserIsPerformant) {
$('.separator').fadeTo(250,clockSeparatorMap[opacity]);
}
else {
$('.separator').delay(250).fadeTo(1,clockSeparatorMap[opacity]);
}
Auch hier arbeite ich mit der .delay()-Funktion, setze sie hier aber „nur“ auf 250 Millisekunden. Anschliessen wird der FadeOut innert 1 Millisekunde gemacht.
Nachtrag
Obwohl Midori nach diesen Anpassungen vorerst stabil lief, fror der Browser nach ca. 10 Stunden erneut ein.
Ich entschied mich deshalb, statt Midori auf Chromium zu setzen:
# apt-get install chromium
… und den Google-Browser folgendermassen zu starten (/etc/xdg/lxsession/LXDE/autostart, via Raspberry PI kiosk mode with Chromium.):
@xset s off
@xset -dpms
@xset s noblank
@chromium --kiosk --incognito http://domain.tld/dash
Auch Chromium (Version 22) hat Probleme mit den opulenten jQuery-Animationen, weshalb ich den JavaScript-Code noch ein wenig anpassen musste:
var browserIsPerformant = true;
if(navigator.userAgent.match(/(Midori)/) || navigator.userAgent.match(/(armv6l)/)) {
browserIsPerformant = false;
}
Chromium trägt aktuell auch die Prozessorplattform im User Agent-String, im Falle von Raspberry Pi ist das ARM.