Структура приложения на Paper.js

В Paper.js всё приложение строится вокруг PaperScope, который является пространством имён для всех объектов Paper.js. Он обеспечивает изоляцию контекста холста, позволяя работать с несколькими канвасами одновременно без конфликтов. Каждый PaperScope содержит следующие ключевые элементы:

  • project — главный объект проекта, содержащий все слои, объекты и активные элементы.
  • view — объект, представляющий область отображения (Canvas), обеспечивает управление размерами, событием onFrame и перерисовкой.
  • tool — объект для обработки пользовательских событий (мышь, клавиатура), упрощает привязку обработчиков.
// Инициализация нового проекта Paper.js
paper.setup(document.getElementById('myCanvas'));
const circle = new paper.Path.Circle({
    center: [50, 50],
    radius: 30,
    fillColor: 'red'
});

В этом примере создаётся новый круг, привязанный к текущему project. Все объекты автоматически добавляются в активный слой проекта (project.activeLayer), что позволяет структурировать графику по уровням.


Проекты и слои

Каждый проект содержит один или несколько слоев (Layer). Слой является контейнером для всех графических элементов, управляет их порядком отображения и группировкой.

  • project.activeLayer — слой, на который по умолчанию добавляются новые объекты.
  • Layer.insertAbove() / Layer.insertBelow() — методы для изменения порядка слоёв.
  • Layer.remove() — удаление слоя вместе с его содержимым.

Слои особенно полезны для анимации и интерактивных приложений, где необходимо контролировать видимость объектов или их порядок рендеринга.

const backgroundLayer = new paper.Layer();
const foregroundLayer = new paper.Layer();
backgroundLayer.activate();

new paper.Path.Rectangle({
    point: [0, 0],
    size: [200, 200],
    fillColor: 'lightblue'
});

foregroundLayer.activate();
new paper.Path.Circle({
    center: [100, 100],
    radius: 50,
    fillColor: 'green'
});

В этом примере создаются два слоя: задний слой с прямоугольником и передний слой с кругом. Слои позволяют изолировать элементы по смыслу и логике приложения.


Инструменты (Tool) и события

Tool — объект, обрабатывающий пользовательские события. С его помощью можно реализовать рисование, перетаскивание, взаимодействие с мышью и клавиатурой.

Ключевые события:

  • onMouseDown(event) — срабатывает при нажатии кнопки мыши.
  • onMouseDrag(event) — срабатывает при перемещении мыши с зажатой кнопкой.
  • onMouseUp(event) — срабатывает при отпускании кнопки мыши.
  • onKeyDown(event) — срабатывает при нажатии клавиши.
  • onKeyUp(event) — срабатывает при отпускании клавиши.
const tool = new paper.Tool();

tool.onMouseD own = function(event) {
    new paper.Path.Circle({
        center: event.point,
        radius: 20,
        fillColor: 'orange'
    });
};

Каждое событие получает объект event, который содержит координаты, целевые элементы и информацию о модификаторах клавиш.


Анимация и цикл обновления (onFrame)

Paper.js использует циклический рендеринг через обработчик onFrame, позволяющий создавать анимацию и динамическое взаимодействие.

  • view.onFrame(event) — вызывается на каждый кадр. Параметр event содержит:

    • event.count — номер кадра с начала анимации.
    • event.time — время с начала анимации в секундах.
    • event.delta — время между кадрами в секундах.
const movingCircle = new paper.Path.Circle({
    center: [50, 50],
    radius: 25,
    fillColor: 'purple'
});

paper.view.onFr ame = function(event) {
    movingCircle.position.x += 2;
    if (movingCircle.position.x > paper.view.size.width) {
        movingCircle.position.x = 0;
    }
};

Этот код создаёт непрерывное движение круга по горизонтали с автоматическим возвращением на левую границу холста.


Группы объектов (Group) и иерархия

Объекты Paper.js могут объединяться в группы (Group), чтобы управлять ими как единым целым. Группы позволяют применять трансформации, стили и анимацию ко всем дочерним элементам одновременно.

  • new Group(items) — создаёт группу из существующих объектов.
  • group.addChild(item) / group.removeChild(item) — добавление или удаление элементов.
  • group.position / group.rotation / group.scale — трансформации применяются ко всей группе.
const circle1 = new paper.Path.Circle([50, 50], 20);
const circle2 = new paper.Path.Circle([100, 50], 20);

const group = new paper.Group([circle1, circle2]);
group.position = new paper.Point(200, 200);
group.rotate(45);

Группы упрощают организацию сложных сцен, где объекты взаимодействуют друг с другом или движутся вместе.


Структурирование большого проекта

Для крупных приложений Paper.js важно придерживаться логической структуры:

  1. Модульность: разделение кода на отдельные файлы для инструментов, слоёв, анимаций.
  2. Слои по смыслу: фон, интерактивные элементы, пользовательский интерфейс.
  3. Использование групп: для объединения связанных объектов.
  4. Цикл onFrame для анимации: все анимационные процессы должны быть централизованы.
  5. Tools для интерактивности: каждый инструмент отвечает за отдельный тип взаимодействия.

Такая организация кода повышает читаемость, облегчает поддержку и расширение приложения.


Взаимодействие между проектами

Paper.js позволяет работать с несколькими PaperScope и проектами одновременно. Это полезно для:

  • Создания нескольких канвасов на одной странице.
  • Изоляции различных сцен.
  • Параллельной обработки и рендеринга графики.
const scope1 = new paper.PaperScope();
scope1.setup(document.getElementById('canvas1'));

const scope2 = new paper.PaperScope();
scope2.setup(document.getElementById('canvas2'));

Каждый scope полностью изолирован, что предотвращает конфликт имён и глобальных переменных.


Структура приложения на Paper.js строится на проекте, слоях, группах, инструментах и цикле анимации, обеспечивая гибкость и масштабируемость графических и интерактивных приложений.