Good morning,
I have a website that should always be running on a monitor in the form of information for people who enter the company to see news, economic data, etc.
The main page manages the rest of the screens that are shown creating a slider effect to the left adding iframes and eliminating them.
With the first load and with each complete round an object called ScreenManager makes a query by ajax to get what screens it should show and what time it gives to each one.
This object is responsible for creating iframe elements for the current page and the next one, in addition to inserting them in the corresponding container to perform the slide effect.
The fact is that it works quite well for 1 full day or so, but when we return to work the next day we find a default Google Chrome page indicating that it has run out of memory.
I understand that the error must be on the main page that is where the ScreenManager object is executed, which is what the Ajax does.
I chose the use of iframes since you can configure two screens in a row with different language (and the javascript code of each screen was pasted with its version in another language in the case of going one after the other) and also because I understood that when removing the iframes the memory used by the sub-screens would be released immediately.
Does anyone have any idea how to optimize the use of memory? Should I assign the variable Screens to null before doing the Ajax to clean it? Does the use of iframes significantly increase long-term memory use?
To give you a clearer idea of the code I leave an example: Home.html
<!DOCTYPE html>
<html>
<head>
<meta charset="UTF8"/>
<style>
#Mask{position: absolute; width: 100%; height: 100%; top: 0px; left: 0px; background-color: transparent; z-index: 1000000;}
</style>
</head>
<body>
<div id="main"></div>
<div id="Mask">
<!-- Zone to control key events , because we lose the events in iframes.pages -->
</div>
<!-- Scripts -->
<script src="https://ajax.googleapis.com/ajax/libs/jquery/2.1.1/jquery.min.js"></script>
<script>
$.fn.ScreenManager = function (options) {
/**
* Helpper var to this
*/
var PL = this;
/**
* RebindData
*/
this.RebindData = function (firstTime) {
/** the original code is ajax request **/
PL.DataManager.CurrentPage = 0;
PL.NextScreenLoad = true;
/** fake Screen Array Objects **/
PL.DataManager.ScreensData = [
{
Title:"Wikipedi Javascript",
Controller:'https://es.wikipedia.org/wiki/JavaScript',
TimeToNext:10 //seconds
},
{
Title:"wikipedia home",
Controller:'https://es.wikipedia.org/wiki/Wikipedia:Portada',
TimeToNext:10 //seconds
}];
if (firstTime)
PL.ChargeFirstScreen();
else {
PL.ChargeScreen();
}
}
this.ChargeFirstScreen = function () {
PL.NextScreenLoad = false;
var screen = PL.DataManager.ScreensData[0];
$(document).prop('title', screen.Title);
var firstScreen = $(PL.DataManager.PageHTML);
PL.PrevTitle = screen.Title;
firstScreen.attr("src", screen.Controller);
firstScreen.addClass('current');
firstScreen.css('left','0px');
firstScreen.load(function () {
try {
//this is for prevent init screen efects on document ready
//$(PL).find('iframe.current')[0].contentWindow.InitOnCharge();
} catch (e) {
window.location.href = window.location.href;
}
});
$(PL).append(firstScreen);
if (!PL.CheckIfRebind(screen, true)) {
PL.DataManager.CurrentPage = PL.WhatIsTheNext();
var screen2 = PL.DataManager.ScreensData[PL.DataManager.CurrentPage];
PL.PrintTheNextScreen(screen2, PL.WhatIsTheNext());
PL.TransitionTimeOut = setTimeout(function() {
PL.ChargeScreen();
}, screen.TimeToNext * 1000);
}
}
this.CheckIfRebind = function (screen, firstTime) {
if (PL.WhatIsTheNext() == 0) {
if (firstTime) {
PL.PrintTheNextScreen(screen,0);
PL.TransitionTimeOut = setTimeout(function () {
PL.RebindData(false);
}, screen.TimeToNext * 1000);
}
return true;
} else {
return false;
}
}
this.PrintTheNextScreen = function (screen,n) {
var nextScreen = $(PL.DataManager.PageHTML);
PL.PrevTitle = screen.Title;
nextScreen.attr("src", screen.Controller);
nextScreen.addClass('next');
nextScreen.load(function () {
PL.NextScreenLoad = true;
});
$(PL).append(nextScreen);
}
this.NextScreen = function (screen) {
//clean the global vars
PL.NextScreenLoad = false;
$(document).prop('title', PL.PrevTitle);
PL.PrevTitle = screen.Title;
$(PL).find('.current').animate({
left: '-100%'
}, 'slow', function () {
$(this).remove();
});
$(PL).find('.next').animate({
left: '0%'
}, 'slow', function () {
$(this).removeClass('next').addClass('current');
try {
//this is for prevent init screen efects on document ready
//$(PL).find('iframe.current')[0].contentWindow.InitOnCharge();
} catch (e) {
window.location.href = window.location.href;
}
if (PL.WhatIsTheNext() == 0) {
PL.DataManager.CurrentPage = PL.WhatIsTheNext();
PL.PrintTheNextScreen(PL.DataManager.ScreensData[PL.DataManager.CurrentPage], PL.DataManager.CurrentPage);
PL.TransitionTimeOut = setTimeout(function () {
PL.RebindData(false);
}, screen.TimeToNext * 1000);
} else {
PL.DataManager.CurrentPage ++;
PL.PrintTheNextScreen(PL.DataManager.ScreensData[PL.DataManager.CurrentPage], PL.DataManager.CurrentPage);
PL.TransitionTimeOut = setTimeout(function() {
PL.ChargeScreen();
}, screen.TimeToNext * 1000);
}
});
}
this.WhatIsTheNext = function() {
if (PL.DataManager.CurrentPage == PL.DataManager.ScreensData.length - 1)
return 0;
else return PL.DataManager.CurrentPage+1;
}
this.WhatIsThePrev = function () {
if (PL.DataManager.CurrentPage != 0)
return PL.DataManager.CurrentPage -1;
else return PL.DataManager.ScreensData.length-1;
}
this.ChargeScreen = function () {
if (PL.NextScreenLoad) {
PL.NextScreen(PL.DataManager.ScreensData[PL.DataManager.CurrentPage]);
}
else
PL.TransitionTimeOut = setTimeout(function () {
PL.ChargeScreen();
}, 10);
}
/**
* Initialize function
*/
this.Initialize = function () {
if (this.Select != '' || this.Select != null) {
$(this).css({
position: 'absolute',
width: '100%',
height: '100%',
top: '0px',
left: '0px',
overflow: 'hidden'
});
this.RebindData(true);
}
else
alert("Hay un error en el parametro Select de Screen Manager");
}
/**
* Properties
*/
this.Select = options.Select;
this.TransitionTimeOut = false;
this.NextScreenLoad = false;
this.PrevTitle = null;
//default Configuration
this.DataManager = {
ScreenTimeToNext: 30,
CurrentPage: 0,
ScreensData: [],
PageHTML: '<iframe style="position: absolute;width: 100%; height: 100%;left:100%;top:0px;border:none;" class="page" />'
}
//run Init
this.Initialize();
//set this plugin to data element
this.data('ScreenManager', this);
//return this plugin
return this;
}
</script>
<script>
var ScreenManager = null;
$(document).ready(function() {
ScreenManager = $('#main').ScreenManager({
Select: 'UrlToGetScreensJson', Callback: "InitOnCharge"
});
$(document).keydown(function(e) {
if (e.keyCode == 39) {
clearInterval(ScreenManager.TransitionTimeOut);
ScreenManager.ChargeScreen();
}
});
});
</script>
</body>
</html>
ScreenManager.js
Thanks and best regards.