利用先进的策略和技术将您的 PixiJS 应用程序提升到一个新的水平
前言
这篇文章介绍了在 CPU / 内存方面可以最好地优化 pixiJS 中多个元素的渲染的不同方法。例如,考虑在没有任何缓存的情况下重新渲染每一帧(在 CPU 使用率方面表现良好)或将渲染的图形缓存在内存中之间的区别。这将根据场景中的图形数量按比例增加内存使用量。
有多种策略可以处理此类优化。特别值得注意的是面向数据的设计,它提供了一组与更传统的常见面向对象编程方式完全不同的方法。
其他主要方法包括:例如,剔除和利用更加结构化的格式 - C# 中的 NativeArrays 和 TypeScript 中的 TypedArrays。这些将允许更好地管理内存缓冲区,这可能会限制缓存未命中,但这也需要大量的工程经验和/或定制。
在这篇文章中,我将重点介绍一种使用 PixiJS 优化 WebGL 环境的工作方法:面向对象的方法,包括最佳实践。这将为您提供一种组织良好的方法来提高 PixiJS 应用程序的速度和效率。
在我的下一篇文章中,我将讨论另一种强大的优化方法:实体组件系统方法。 ECS 方法非常以数据为导向,并且在高性能环境中优化 PixiJS 时提供了全新的外观。在 Medium 上继续阅读本文,我将深入探讨 ECS 方法的本质。
永远记住,为了优化和进一步增强 Pixi 应用程序的性能,总有一些事情可以做得更好。更好并不意味着最优化或最快。最佳解决方案是在优化投入的时间和投资回报之间进行权衡的问题,以确保您能够满足项目期限,但有足够的优化来满足任何潜在用户的需求,而不会过度扩展您的资源。
面向对象的方法
在本节中,我将指导您了解优化 PixiJS 应用程序的最佳方法。
此部分基于官方提示,值得查看!
我们的其余讨论将围绕 Pixi 图形、精灵、网格以及何时使用粒子容器而不是默认的 Pixi 容器。本章应该让您清楚地了解如何在面向对象的上下文中最佳地使用所有内容,以便您的 PixiJS 项目正常运行并以最高效率进行渲染。
了解 Pixi 图形的内部工作原理
为了有效地使用 Pixi 图形,我们需要了解它们的内部功能。让我们首先展示一个在 Pixi 中创建图形对象的非常基本的示例:
const graphics = new PIXI.Graphics(); graphics.beginFill(0xff0000); graphics.drawRect(0, 0, 200, 100); graphics.endFill();
然而,在这个简单的实现中重要的是“幕后”发生的事情。在创建这种图形时,Pixi 创建了一个称为 GraphicsGeometry 对象的东西。该对象的形状和大小取决于您为正在绘制的形状指定的尺寸和属性。然后,最终的 Geometry 对象存储在 Graphics 对象内的 GeometryList 内。
请注意,每次您在 PIXI.Graphics 的帮助下绘制某些内容时,GeometryList 都会更新。有时,您只想清除此列表,但同时保持 Graphics 对象处于活动状态 - 这就是 .clear() 方法发挥作用的地方。了解此过程的工作原理将对您使用 Pixi 时有很大帮助,因为它直接影响 Pixi 如何处理和渲染应用程序中的图形。
Pixi 图形优化技术
让我们通过在 PixiJS 中创建 100 个 Graphics 对象的用例来探索优化策略。
function createGraphics(x, y) { const graphic = new PIXI.Graphics(); graphic.beginFill(0xDE3249); graphic.drawCircle(x, y, 10); graphic.endFill(); return graphic; } for (let i = 0; i <p>在这种情况下,如果所有 100 个 Graphics 对象共享相同的宽度和高度,我们可以通过重用几何体进行优化。</p> <p><img src="/static/imghwm/default1.png" data-src="https://img.php.cn/upload/article/000/000/000/172544598152954.jpg?x-oss-process=image/resize,p_40" class="lazy" alt="Maximising Performance: A Deep Dive into PixiJS Optimization"></p> <h2> 传递 GraphicsGeometry 作为参考 </h2> <p>为圆创建单个几何图形并重复使用它:<br> </p> <pre class="brush:php;toolbar:false">// Create a single geometry for a circle const circleGeometry = new PIXI.Graphics(); circleGeometry.beginFill(0xDE3249); circleGeometry.drawCircle(0, 0, 10); // Draw a circle at the origin circleGeometry.endFill(); // Function to create a graphic using the circle geometry function createCircle(x, y) { const circle = new PIXI.Graphics(circleGeometry.geometry); circle.x = x; circle.y = y; return circle; } // Create 100 circles using the same geometry for (let i = 0; i <p>此方法通过引用相同的几何图形而不是为每个对象重复它,显着减少了内存使用量。</p> <p><img src="/static/imghwm/default1.png" data-src="https://img.php.cn/upload/article/000/000/000/172544598361728.jpg?x-oss-process=image/resize,p_40" class="lazy" alt="Maximising Performance: A Deep Dive into PixiJS Optimization"></p> <h2> Draw All in One Graphics Object </h2> <p>For static graphics or complex structures, drawing all elements in a single Graphics object is another optimization technique:<br> </p> <pre class="brush:php;toolbar:false">const graphics = new PIXI.Graphics(); // Draw 100 circles using the same PIXI.Graphics instance for (let i = 0; i <p>In this approach, instead of creating new Graphics objects, we add new geometries to the GeometryList of a single Graphics instance. This method is particularly efficient for more complex graphic structures.</p> <p><img src="/static/imghwm/default1.png" data-src="https://img.php.cn/upload/article/000/000/000/172544598467239.jpg?x-oss-process=image/resize,p_40" class="lazy" alt="Maximising Performance: A Deep Dive into PixiJS Optimization"></p> <hr> <h2> Leveraging the Power of CacheAsBitmap in PixiJS </h2> <p>One of the most powerful features within PixiJS is CacheAsBitmap. Essentially, it lets the engine treat graphics like sprites. This can bring performance up substantially in certain cases.</p>
Only use CacheAsBitmap if the object is not updated too often.
Big batch of Graphics can be cached as bitmap in container. Instead having 100 Graphics re-rendered, pixi will take a snapshot and pre-render it as a bitmap.
Always consider the memory usage, cached bitmaps are using a lot of memory.
When to Use CacheAsBitmap
One should use cacheAsBitmap judiciously. It will be most effective when applied to objects that need to update seldom. For instance, if one happens to have thousands of volume of Graphics that are static or have only a rare change, caching them as a bitmap radically reduces rendering overhead.
Instead of re-rendering 100 individual Graphics, PixiJS can take a 'snapshot' of these and render them as single bitmap. This is how you can implement:
const graphicsContainer = new PIXI.Container(); // Add your graphics to the container // ... // Cache the entire container as a bitmap graphicsContainer.cacheAsBitmap = true;
Memory Usage Consideration
However, it's important to be mindful of memory usage. Cached bitmaps can consume a significant amount of memory. Therefore, while cacheAsBitmap can drastically reduce the rendering load, it trades off by using more memory. This trade-off should be carefully considered based on the specific needs and constraints of your application.
In summary, cacheAsBitmap is an effective tool for optimizing performance in PixiJS, particularly for static or seldom-updated graphics. It simplifies rendering by treating complex graphics as single bitmaps, but it's essential to balance this with the memory footprint implications.
Why Sprites Are Often More Efficient than Graphics in PixiJS
When it comes to memory efficiency in PixiJS, sprites generally have the upper hand over graphics. This is particularly evident when dealing with multiple objects that share the same shape or texture. Let's revisit the example of creating 100 circle graphics, but this time using sprites.
Creating Sprites from a Single Texture
First, we create a texture from the geometry of a single circle graphic:
const circleGraphic = new PIXI.Graphics(); circleGraphic.beginFill(0xDE3249); circleGraphic.drawCircle(0, 0, 10); circleGraphic.endFill(); // Generate a texture from the graphic const circleTexture = app.renderer.generateTexture(circleGraphic); Next, we use this texture to create sprites: // Function to create a sprite using the circle texture function createCircleSprite(x, y) { const sprite = new PIXI.Sprite(circleTexture); sprite.x = x; sprite.y = y; return sprite; } // Create and add 100 circle sprites to the stage for (let i = 0; i <p>In this approach, instead of re-rendering graphics and managing a growing geometry list for each object, we create one texture and reuse it across multiple sprites. This significantly reduces the rendering load and memory usage.</p> <h2> Limitations and Creative Solutions </h2> <p>One limitation of this method is that you're constrained by the textures you've created. However, this is where creativity becomes key. You can generate various shaped textures using PIXI.Graphics and apply them to Sprites. An especially efficient approach is to create a baseTexture, like a 1x1 pixel bitmap, and reuse it for all rectangular sprites. By resizing the sprite to different dimensions, you can leverage the same baseTexture across multiple sprites without redundancy.<br> For instance:<br> </p> <pre class="brush:php;toolbar:false">// This creates a 16x16 white texture const baseTexture = PIXI.Texture.WHITE; // Use this baseTexture for all rectangular shapes const sprite= new PIXI.Sprite(baseTexture); sprite.tint = 0xDE3249; // Set the sprite color sprite.position.set(x, y); sprite.width = width; sprite.height = height;
With this method, .tint() allows you to color the sprite without triggering a full re-render, as the tint is applied as an additional shader effect directly on the GPU.
Using 100k Sprites in Particle Container
To illustrate the power of this technique, imagine running 100,000 individual sprites with random tints, each transforming on every frame, all while maintaining a smooth 60 FPS.
For further reading on optimizing PixiJS, I highly recommend an insightful article by one of the original creators of PixiJS, which delves deeply into the renderTexture technique.
You can find it here
哇! 如果您已经完成了这一步,我真诚地感谢您在 PixiJS 优化的深入研究中与我同行。我希望您发现这里分享的见解和技术对您的项目有价值。请继续关注我的下一篇文章,我将更详细地探讨实体组件系统 (ECS) 方法和 NativeArrays 的强大功能。这些方法将使您的 PixiJS 应用程序的性能和效率达到新的高度。感谢您的阅读,我们下一篇再见!
以上是最大化性能:深入探讨 PixiJS 优化的详细内容。更多信息请关注PHP中文网其他相关文章!

JavaScript是现代网站的核心,因为它增强了网页的交互性和动态性。1)它允许在不刷新页面的情况下改变内容,2)通过DOMAPI操作网页,3)支持复杂的交互效果如动画和拖放,4)优化性能和最佳实践提高用户体验。

C 和JavaScript通过WebAssembly实现互操作性。1)C 代码编译成WebAssembly模块,引入到JavaScript环境中,增强计算能力。2)在游戏开发中,C 处理物理引擎和图形渲染,JavaScript负责游戏逻辑和用户界面。

JavaScript在网站、移动应用、桌面应用和服务器端编程中均有广泛应用。1)在网站开发中,JavaScript与HTML、CSS一起操作DOM,实现动态效果,并支持如jQuery、React等框架。2)通过ReactNative和Ionic,JavaScript用于开发跨平台移动应用。3)Electron框架使JavaScript能构建桌面应用。4)Node.js让JavaScript在服务器端运行,支持高并发请求。

Python更适合数据科学和自动化,JavaScript更适合前端和全栈开发。1.Python在数据科学和机器学习中表现出色,使用NumPy、Pandas等库进行数据处理和建模。2.Python在自动化和脚本编写方面简洁高效。3.JavaScript在前端开发中不可或缺,用于构建动态网页和单页面应用。4.JavaScript通过Node.js在后端开发中发挥作用,支持全栈开发。

C和C 在JavaScript引擎中扮演了至关重要的角色,主要用于实现解释器和JIT编译器。 1)C 用于解析JavaScript源码并生成抽象语法树。 2)C 负责生成和执行字节码。 3)C 实现JIT编译器,在运行时优化和编译热点代码,显着提高JavaScript的执行效率。

JavaScript在现实世界中的应用包括前端和后端开发。1)通过构建TODO列表应用展示前端应用,涉及DOM操作和事件处理。2)通过Node.js和Express构建RESTfulAPI展示后端应用。

JavaScript在Web开发中的主要用途包括客户端交互、表单验证和异步通信。1)通过DOM操作实现动态内容更新和用户交互;2)在用户提交数据前进行客户端验证,提高用户体验;3)通过AJAX技术实现与服务器的无刷新通信。

理解JavaScript引擎内部工作原理对开发者重要,因为它能帮助编写更高效的代码并理解性能瓶颈和优化策略。1)引擎的工作流程包括解析、编译和执行三个阶段;2)执行过程中,引擎会进行动态优化,如内联缓存和隐藏类;3)最佳实践包括避免全局变量、优化循环、使用const和let,以及避免过度使用闭包。


热AI工具

Undresser.AI Undress
人工智能驱动的应用程序,用于创建逼真的裸体照片

AI Clothes Remover
用于从照片中去除衣服的在线人工智能工具。

Undress AI Tool
免费脱衣服图片

Clothoff.io
AI脱衣机

Video Face Swap
使用我们完全免费的人工智能换脸工具轻松在任何视频中换脸!

热门文章

热工具

VSCode Windows 64位 下载
微软推出的免费、功能强大的一款IDE编辑器

Atom编辑器mac版下载
最流行的的开源编辑器

EditPlus 中文破解版
体积小,语法高亮,不支持代码提示功能

Dreamweaver CS6
视觉化网页开发工具

SublimeText3 英文版
推荐:为Win版本,支持代码提示!