Как можно полностью перезапустить библиотеку PixiJS?

У меня есть код инициализации, в котором создается экземпляр app, изменяется размер и рисуется холст (canvas) в виде меша. При первом запуске всё работает корректно. Однако, если я устанавливаю app = null, затем изменяю размер холста canvC и повторно запускаю код инициализации, то холст в pixijs становится черным, и в консоли появляется предупреждение: <b>"[.WebGL-0000082802A50D00] GL_INVALID_VALUE: Offset overflows texture dimensions."</b> <br/> В связи с этим у меня возник вопрос: правильно ли я пересоздаю экземпляр pixijs, или нужно выполнить дополнительные действия? Есть ощущение, что новое создание не очищает предыдущие данные, а накладывает новые. <br/> <pre><code class="javascript">app = new PIXI.Application();
        await app.init({resizeTo:canvC});
        app.renderer.resize(canvC.width,canvC.height);
        document.querySelector('#pix').innerHTML='';
        document.querySelector('#pix').appendChild(app.canvas);
        texture = new PIXI.Texture.from(canvC);
        plane = new PIXI.MeshPlane({ texture, verticesX: vert, verticesY: vert });
        app.stage.addChild(plane);
        buffer = plane.geometry.getAttribute('aPosition').buffer;
        buffer.on('update',()=&gt;{
            setTimeout(()=&gt;{
                fPix();
            },100);
        });
        bufferCopy = [...buffer.data];</code></pre>
  • 7 ноября 2024 г. 20:53
Ответы на вопрос 2
Чтобы полностью перезапустить приложение PixiJS и избежать проблем с предыдущими экземплярами и их данными, вам необходимо убедиться, что вы очищаете все ресурсы перед созданием нового экземпляра приложения. Давайте рассмотрим шаги, необходимые для этого:

1. **Удалите все объекты из сцены**: Перед тем как перезапустить приложение, убедитесь, что вы удаляете все объекты из `app.stage`.

2. **Очистите ресурсы**: Освободите память, связанную с текстурами и другими графическими элементами, которые могут остаться существующими. Это можно сделать с помощью метода `destroy()`.

3. **Удалите канвас из документа**: Вам нужно сначала удалить канвас из DOM перед созданием нового экземпляра приложения.

4. **Обнуляйте переменные**: Обнуляйте ссылки на используемые вами ресурсы, чтобы избежать случайных утечек памяти.

Вот пример, как можно это сделать:

```javascript
function resetPixi() {
    // Если приложение уже существует, уничтожьте его
    if (app) {
        // Удалите все дочерние элементы со сцены
        app.stage.removeChildren();

        // Уничтожьте текстуры и другие ресурсы
        app.renderer.destroy(true); // true - для глубокого уничтожения
        app.destroy(true); // так же уничтожаем приложение

        // Обнуляем переменную
        app = null;
    }
}

async function initializePixi() {
    resetPixi(); // Сбрасываем предыдущее состояние

    // Создаем новое приложение PixiJS
    app = new PIXI.Application();
    await app.init({resizeTo:canvC});
    app.renderer.resize(canvC.width,canvC.height);

    // Обновляем DOM
    document.querySelector('#pix').innerHTML = ''; // очищаем предыдущий холст
    document.querySelector('#pix').appendChild(app.view); // добавляем новый холст

    // Создаем текстуру и меш
    texture = PIXI.Texture.from(canvC);
    plane = new PIXI.MeshPlane({ texture, verticesX: vert, verticesY: vert });
    app.stage.addChild(plane);

    // Настройка модуля буфера
    buffer = plane.geometry.getAttribute('aPosition').buffer;
    buffer.on('update', () => {
        setTimeout(() => {
            fPix();
        }, 100);
    });
    bufferCopy = [...buffer.data];
}

// Теперь вы можете вызвать initializePixi в любой момент, чтобы перезапустить приложение
```

Сделав эти шаги, вы должны избежать проблем, связанных с предыдущими экземплярами приложения, и ваш канвас должен корректно обновляться каждый раз, когда вы вызываете `initializePixi()`.
GL_INVALID_VALUE: Offset overflows texture dimensions.

Ошибки такого рода в мире WebGL обычно связаны с тем фактом, что мы пытаемся использовать текстуру, но у нас левые ее размеры, и мы, например, пытаемся получать из нее пиксели за ее границами. Искать проблему нужно вокруг этого факта. На сайте PixiJS можно найти описание основ работы с текстурами, и там сказано, что они кешируются. Если мы делаем Texture.from с тем же источником, то получаем не новую текстуру, а ту, которая уже была. Но в вашем коде где-то по дороге меняются размеры. А сама текстура, сам буфер с пикселями, получается старый, закешированный. Это, вполне вероятно, и вызывает несоответствие. Решением должно быть использование метода destroy() у текстуры, чтобы ее уничтожить с концами при переинициализации. Альтернативно у конструктора Texture.from есть второй параметр skipCache , который по идее даст схожий результат.
Похожие вопросы