Transition from CodePen
This commit is contained in:
		
							
								
								
									
										116
									
								
								hollow.js
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										116
									
								
								hollow.js
									
									
									
									
									
										Normal file
									
								
							@@ -0,0 +1,116 @@
 | 
				
			|||||||
 | 
					"use strict";
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					/**
 | 
				
			||||||
 | 
					 * @author Arsen Mirzaev Tatyano-Muradovich <arsen@mirzaev.sexy>
 | 
				
			||||||
 | 
					 */
 | 
				
			||||||
 | 
					class hollow {
 | 
				
			||||||
 | 
					  // Размытие дальних слоёв
 | 
				
			||||||
 | 
					  blur = true;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  // Затемнение дальних слоёв
 | 
				
			||||||
 | 
					  blackout = false;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  // Увеличение размера дальнего слоя до краёв
 | 
				
			||||||
 | 
					  expand = false;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  next() {
 | 
				
			||||||
 | 
					    // Инициализация идентификатора активного слоя
 | 
				
			||||||
 | 
					    const current = this.current();
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    // Генерация с защитой от выхода за предел масштабирования
 | 
				
			||||||
 | 
					    this.generate(
 | 
				
			||||||
 | 
					      current === document.getElementsByTagName("section").length - 1
 | 
				
			||||||
 | 
					        ? current
 | 
				
			||||||
 | 
					        : current + 1
 | 
				
			||||||
 | 
					    );
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  previous() {
 | 
				
			||||||
 | 
					    // Инициализация идентификатора активного слоя
 | 
				
			||||||
 | 
					    const current = this.current();
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    // Генерация с защитой от выхода за предел масштабирования
 | 
				
			||||||
 | 
					    this.generate(current === 0 ? current : current - 1);
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  current() {
 | 
				
			||||||
 | 
					    // Инициализация номера слоя
 | 
				
			||||||
 | 
					    let id = 0;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    for (const layer of document.getElementsByTagName("section")) {
 | 
				
			||||||
 | 
					      // Перебор слоёв
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					      // Поиск активного слоя
 | 
				
			||||||
 | 
					      if (layer.style.scale === "1") return id;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					      // Запись идентификатора следующего слоя
 | 
				
			||||||
 | 
					      ++id;
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					  generate(zoom = 0) {
 | 
				
			||||||
 | 
					    // Инициализация номера слоя
 | 
				
			||||||
 | 
					    let id = 1;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    for (const layer of document.getElementsByTagName("section")) {
 | 
				
			||||||
 | 
					      // Перебор слоёв
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					      // Запись размера
 | 
				
			||||||
 | 
					      layer.style.scale = (zoom * 0.2 + 1 - 0.2 * (id - 1)).toFixed(1);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					      // Запись минимального размера
 | 
				
			||||||
 | 
					      if (+layer.style.scale < 0) layer.style.scale = 0;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					      // Запись максимального размера
 | 
				
			||||||
 | 
					      if (+layer.style.scale > 2) layer.style.scale = 2;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					      // Запись индекса
 | 
				
			||||||
 | 
					      layer.style.zIndex = zoom * 100 + 100 - id * 100;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					      if (this.expand && +layer.style.scale < 1) {
 | 
				
			||||||
 | 
					        // Расширение слоёв до границ
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        // Запись степени расширения
 | 
				
			||||||
 | 
					        const expand = +layer.style.scale <= 0.1 ? 0.1 : layer.style.scale;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        layer.style.width = "calc(100% / " + expand + ")";
 | 
				
			||||||
 | 
					        layer.style.height = "calc(100% / " + expand + ")";
 | 
				
			||||||
 | 
					        layer.style.left = "calc((-100% / " + expand + " + 100%) / 2)";
 | 
				
			||||||
 | 
					        layer.style.top = "calc((-100% / " + expand + " + 100%) / 2)";
 | 
				
			||||||
 | 
					      }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					      if (+layer.style.scale <= 0 || +layer.style.scale > 1) {
 | 
				
			||||||
 | 
					        // Слой вышел за рамки отображаемых размеров
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        // Запись прозрачности
 | 
				
			||||||
 | 
					        layer.style.opacity = 0;
 | 
				
			||||||
 | 
					      } else if (+layer.style.scale === 1) {
 | 
				
			||||||
 | 
					        // Активный слой
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        // Запись эффектов
 | 
				
			||||||
 | 
					        layer.style.filter = null;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        // Запись прозрачности
 | 
				
			||||||
 | 
					        layer.style.opacity = 1;
 | 
				
			||||||
 | 
					      } else {
 | 
				
			||||||
 | 
					        // Дальние слои
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        // Запись эффектов
 | 
				
			||||||
 | 
					        if (this.blur)
 | 
				
			||||||
 | 
					          layer.style.filter = "blur(" + (4 - layer.style.scale * 2) + "px)";
 | 
				
			||||||
 | 
					        if (this.blackout)
 | 
				
			||||||
 | 
					          layer.style.filter += "brightness(" + layer.style.scale * 100 + "%)";
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        // Запись прозрачности
 | 
				
			||||||
 | 
					        layer.style.opacity = layer.style.scale - 0.2;
 | 
				
			||||||
 | 
					      }
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					      // Запись активности слушателей
 | 
				
			||||||
 | 
					      if (id === zoom + 1) layer.style.pointerEvents = "all";
 | 
				
			||||||
 | 
					      else layer.style.pointerEvents = "none";
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					      // Запись идентификатора следующего слоя
 | 
				
			||||||
 | 
					      ++id;
 | 
				
			||||||
 | 
					    }
 | 
				
			||||||
 | 
					  }
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
		Reference in New Issue
	
	Block a user