Сегодня только заметил что буковки все разного цвета, а это несколько меняет ситуацию.
Значит строки двигать я не могу ( innerHTML юзать западло
). Окей тогда попробуем сгенеририть контейнеры для символов для каждой строки. Мы будем перебирать контейнеры снизу вверх и копировать значение в текущий контейнер из вышестоящего. Затем нам останется просто добавить новый символ в самый верхний контейнер. Помимо символа я могу скопировать с верхнего контейнера и любые свойства (к примеру цвет).
Кстатии когда столбец заполне не полностью можно немного похимичить и избавится от лишнего копирования, это как идея.
На ноуте с производительность муть какая то, обычно выдает 60fps, но иногда 15 fps. Не в первом скрипте подмечаю сильные колебания в скорости с причинами не зависящими от скрипта.
<!DOCTYPE HTML>
<html>
<head>
<style>
.textline{
color:green;
width: 3%;
height:300px;
overflow:hidden;
text-align: center;
font: Consolas, Monaco, monospac;
font-size:20px;
float:left;
}
</style>
</head>
<body style="height:100%;background:black;">
<div id="stage"></div>
<script>
//Генератор случайных чисел
function getRandomInt(min, max) {
return Math.floor(Math.random() * (max-min) ) + min;
}
//сцена на которой происходит анимация
function Stage(el){
//Действующие лица анимации
var children=[];
//добавляет новых актеров на сцену
this.add=function(line){
children.push(line);
el.appendChild(line.el);
}
//обновляет состояние актеров на сцене
this.update=function(time){
for (var i=0;i<children.length;i++){
children[i].update(time);
}
}
}
//Действующие лица анимации
function Line(){
var frameLength=getRandomInt(10,50),
oldTime=0,
interval=getRandomInt(10,400);
this.el=document.createElement('div');
this.el.classList.add('textline')
//сгенерируем контейнеры в которые будем помещать буковки
for (var i=0;i<12;i++){
this.el.appendChild( document.createElement('div') );
}
var children=this.el.children;
//обновляем линию
this.update=function(time){
var sym="",
count=11;
if (time-oldTime>interval){ //анимируется только если временной промежуток больше интервала
//счетчик кадров
frameLength--;
//Сместим старые элементы вниз
while( count-- && count>0){
children[count].innerText=children[count-1].innerText;
children[count].style.color=children[count-1].style.color
}
//Добавим новые
if (frameLength>12){ //если больше 12 кадров добавим символ
sym=String.fromCharCode(getRandomInt(97,122));
children[0].innerText=sym;
children[0].style.color="rgb(0,"+getRandomInt(90,255)+",0)";
} else if(frameLength==0){
frameLength=getRandomInt(10,50); //сгенерируем новую длинну
interval=getRandomInt(10,400); //сгенерируем новую скорость
} else { //если меньше 12 кадров то фигачим \n
children[0].innerText='\n';
}
oldTime=time;
}
}
}
//Счетчик кадров
function FPS(){
var oldTime='0',
count=0,
sec=0;
this.el=document.createElement('div');
this.el.style.color="#777";
this.el.innerText="0";
this.update=function(time){
//new Date медленная операция, как альтернативу можно юзать переменную time но точность измерения будет ниже
sec=new Date().getSeconds();
if (sec!=oldTime){
this.el.innerText='FPS='+count;
oldTime=sec;
count=0;
}
count++;
}
}
//=========== инициализация приложения ================//
var stage=new Stage(document.getElementById('stage') );
for (var i=0;i<33;i++){
stage.add( new Line() );
}
stage.add( new FPS() );
+function animloop(time){
stage.update(time);
requestAnimationFrame(animloop);
}(0);
</script>
</body>
</html>