Intelligent Assistant
Chat with our virtual assistant to get answers promptly.
Since the CPU needs to decompress the images into the texture format for the GPU to directly read them, the CPU processing time increases and image loading is delayed when the number or size of images exceeds a specific threshold. In addition, the images generated after decompression occupy a large amount of memory, which increases the memory pressure and may cause frame freezing and frame loss. This topic describes solutions for optimizing preset and non-preset images. Preset images are mainly optimized by using a texture compression technology. Non-preset image loading optimization policies are as follows: compressing images by using an image editing tool, reducing GIF image resolution, optimizing network images, preferentially using WebP images, and performing down-sampling on images by using autoResize.
Preset images are local images packed in the app package and stored in the resource/base/media directory. You can optimize the loading of preset images using texture compression.
Texture compression is used to reduce the size of texture image files. You can use texture compression to transcode and compress preset images during the build process, thereby reducing the CPU processing time, lowering memory usage, and improving app performance.
How to Implement
Without texture compression, preset images must be decoded by the CPU into a pixel map before being uploaded to the GPU for texture generation. This process is time-consuming. You can use texture compression technology to complete CPU decoding and texture generation in advance in the compilation and build phases, reducing the time for the CPU to process images. For texture compression, relevant properties must be configured in the compilation file. During the build process, preset images are located and converted into texture streams based on these configurations. Super-compression encoding is then applied to generate super-compression streams. After compilation, during runtime, super-compressed data is decoded to generate texture streams. The GPU then reads these streams for rendering and display.

Texture compression compresses preset images in the compilation and build processes. You need to configure texture compression parameters in the compilation file of the editor. Based on the parameters, Hvigor reads the files to be compressed, constructs the restool command to parse resources, and then generates a resource file list. Then, Hvigor traverses the file list and transcodes the files to be converted to the texture format. Converted resource files are no longer packaged into build products. The texture files and unconverted files are then built to generate resource products.
The following figure shows the timing for enabling texture compression for compiling and building resource files.

Texture compression processes preset images in advance during compilation and build processes, which may increase the compilation time and package size. If images occupy a large amount of space and have a significant impact on the package size, you are advised to filter images to reduce the texture compression overhead.
Scenario Case
Images cannot be directly rendered by the GPU. The CPU needs to decode the images and upload them to the GPU, which takes time. When a certain number of preset images are rendered on a page at the same time, the image completion delay may increase. The following figure shows how to switch between tabs. When you swipe right to switch to tab2, the new page loads 40 PNG images and 40 JPG images using the horizontal layout. The image completion delay is significantly different when texture compression is enabled and disabled. The following figure shows the switching process when texture compression is disabled.

If texture compression is not used, when you swipe right to switch to tab2, the loading of some images may be delayed because multiple preset images need to be loaded on the new page. As a result, white blocks occur.
Project Configuration
Before using texture compression, you need to perform basic configurations and select the preset image to be super-compressed. You can add the media and filters properties to the compression object in the build-profile.json5 configuration file at the project or module level.
media: contains the enable property that specifies whether to enable texture compression. The default value is false, indicating that texture compression is disabled. To enable texture compression, set enable to true.
filters: contains the method, files, and exclude property objects.
For details, see compression. The sample code for configuring texture compression is as follows:
- "buildOption": {
- "resOptions": {
- "compression": {
- "media": {
- "enable": true // Whether to enable texture compression for media images
- },
- // Filtering of texture compression files. This field is not mandatory. If this field is not set, all images in the resource directory will be compressed
- "filters": [
- {
- "method": {
- "type": "sut", // conversion type
- "blocks": "4x4" // The extended parameters of the conversion type
- },
- // Specifies the files used for compression. Only files that meet all conditions and are not excluded can be compressed
- "files": {
- "path": ["./**/*"], // All files in the specified resource directory
- "size": [[0, '1000k']], // Files with a specified size of less than 1000k
- // Pictures with a resolution smaller than 3000 x 3000
- "resolution": [
- [
- { "width": 0, "height": 0 }, // minimum width and height
- { "width": 3000, "height": 3000 } // Maximum width and height
- ]
- ]
- },
- // Remove files that do not need to be compressed from the files list. Only files that meet all filtering conditions are deleted
- "exclude": {
- "path": ["./**/*.webp"], // Filter all webp files
- "size": [[0, '1k']], // Filter files smaller than 1k in size
- // Filter images with a resolution smaller than 1024 x 1024
- "resolution": [
- [
- { "width": 0, "height": 0 }, // minimum width and height
- { "width": 1024, "height": 1024 } // Maximum width and height
- ]
- ]
- }
- }
- ]
- }
- }},
NOTE
Therefore, the value range of [0-1k, 1k-2k] is the same as that of [0-2k] for size matching.
When matching is performed by resolution, the width and height of the resolution are two-dimensional arrays. In the following figure, the left part indicates all images whose resolution is less than 2048 × 2048, and the right part indicates images whose resolution is less than 1024 × 1024 and images whose resolution is between 1024 × 1024 and 2048 × 2048. The two formats seem to be the same, but their value ranges are different.

Compilation and Execution
After setting related parameters, compile and build the project. During compilation, Hvigor obtains preset images based on configuration parameters, compresses them into textures using the transcoding component, and packs the textures. The following figure shows the switching effect of the tabs after texture compression.

As shown in the figure, when texture compression is used, images are displayed immediately when the screen switches to tab2, without any delay or white blocks.
Benefits and Overheads
When using texture compression to convert preset images, pay attention to the number of covered resource files to ensure that the overhead is minimized while maximizing the benefits. Therefore, the performance improvement of texture super-compression should be analyzed from both benefits and overheads.
Benefits
Texture compression converts preset images into texture formats, which are directly read by the GPU. This reduces the CPU and DDR load and speeds up image loading. The following figure shows the durations for reading a preset image in .png, .sut, and .astc formats.

The following table lists the durations for H:CreateImagePixelMap.
File | Duration | Benefits |
|---|---|---|
.png | 62.103ms | - |
.sut | 15.309ms | 4.13 times |
.astc | 38.239ms | 1.63 times |
Loading a .png image takes roughly four times longer than loading a .sut image, while loading an .astc image takes about twice as long as loading a .sut image. When sut or astc is enabled, the preset images can be loaded more quickly.
After comparing the time required for loading images, switch tabs to check the memory usage before and after texture compression is enabled. The following figures show the related data.



The following table lists the memory usage before and after texture compression is enabled.
Whether To Enable Texture Compression | Memory Usage |
|---|---|
Enabled (.sut) | 165015KB |
Enabled (.astc) | 167723KB |
Disabled | 598965KB |
The table shows that when texture compression is enabled, the memory usage decreases from 598,965 KB to 165,015 KB (.sut) or 167,723 KB (.astc), and the memory usage for image loading decreases significantly.
Overheads
When texture compression is used, preset images are converted during compilation, which increases the compilation duration. Once preset images are converted to the texture format, their size varies based on the image format, which may cause the package to expand or shrink.
The compilation takes a long time because it includes the texture compression process. You can use 87 preset PNG, WebP, and JPG images for compilation and package them in three scenarios: full compilation, modifying parameters of resolution, and adding 1 to 100 images. The following table lists the compilation time when texture compression is enabled and disabled.
Test Case | Texture Compression Disabled | Texture Compression Enabled | Added Time Consumption |
|---|---|---|---|
Full compilation | 19s 74ms | 1min 16s | Traversing resource files, texture compression and moving resource files. |
Modifying parameters of resolution | - | 16s 487ms | Traversing and moving resource files. |
Adding 1 to 100 images | 10s 177ms~10s 283ms | 16s 491ms~16s 673ms | Traversing resource files. |
As shown in the preceding table, after texture compression is enabled, full compilation takes a longer time. However, reapplying texture compression after filtering preset images by resolution greatly shortens the compilation duration.
Analysis of several sample apps confirms that the expansion rate of .jpg and .webp images is two to three times. The following table lists the expansion rate data after texture super-compression is enabled.
Image Format | Expansion Rate |
|---|---|
.jpg | 3.05 |
.png | 0.92 |
.webp | 2.50 |
The package body expansion rate varies depending on the resource size, format, resolution, and quantity of the app. The preceding data is for reference only.
After texture compression, the size of the .png image package remains unchanged, but the size of the .jpg and .webp image packages increases significantly. To optimize performance with texture super-compression in package size-sensitive scenarios, consider compressing all .png images into textures and selectively converting frequently used .jpg and .webp images or those critical to key frames.
Non-preset images are not resources in the app. Instead, they are usually obtained from the network or local file system. These images are not fixed, for example, user profile pictures, images in dynamic content, and product images obtained from the server. The following describes several solutions for optimizing non-preset image loading before and during image use.
Pre-compress images to the actual UI size, including compressing images using the image editing tool and reducing the resolution of GIF images.
Before building an app, you are advised to use an image editing tool or script to adjust the image resolution to the actual display size in the UI and compress the image to reduce its size and improve the loading performance.
The FFmpeg third-party library provides the following two methods to reduce the resolution of GIF images. You can also combine the two methods.
- ffmpeg -i input.gif -s 90x90 -y output.gif (set the width and height to 90 pixels.)
Alternatively, use the -vf parameter and the scale filter to set the width to 90 pixels and the height to be automatically scaled proportionally.
- ffmpeg -i input.gif -vf "scale=90:-1" -y output.gif
The parameters in the preceding commands are described as follows:
Pre-compression Scenario Case
For example, directly scaling an image of 4180 × 4180 pixels to a profile of 80 × 80 pixels on a web page or app will cause high memory usage, slow decoding, and frame freezing. In this case, you are advised to compress and scale the image to a small image of 80 x 80 pixels before loading the image. The image completion delay is significantly different when the image is compressed and when the image is not compressed.

Time Consumption Comparison
Click to switch the test example and check the time consumption for reading images before and after compression. The following figures show the related data.


The following table lists the image decoding duration before and after the image is compressed to the actual UI size.
Whether the Pre-compression Is Performed | Image Decoding Duration |
|---|---|
No | 93ms |
Yes | 740us |
The table shows that after the image is pre-compressed to the actual UI size, the image loading time decreases significantly from 183 μs to 95 μs.
Memory Usage Comparison
Click to switch the test example and check the memory usage before and after compression. The following figures show the related data.


The following table lists the memory usage before and after the image is compressed to the actual UI size.
Whether the Pre-compression Is Performed | Memory Usage |
|---|---|
No | 90224KB |
Yes | 21230KB |
The table shows that after the pre-compression is performed, the memory usage for image loading decreases significantly from 90,224 KB to 21,230 KB.
Optimizing network images helps improve user experience, reduce traffic consumption, reduce memory usage, and accelerate page rendering. Content Delivery Network (CDN) is a network technology that accelerates content distribution. Using CDN to crop images is an efficient way to optimize image loading performance. With the dynamic processing capability provided by CDN, you can adjust the image size, quality, and format as required, reducing bandwidth consumption and accelerating page loading.
How to Implement
Most CDN service providers (such as Huawei Cloud) allow you to dynamically adjust the image size and format by appending query parameters to the image URL. These parameters can control the width, height, and cropping mode of an image. The following are common parameters:
For example, use the cover cropping mode to convert the network image (URL: https://your-cdn-url.com/path/to/image.jpg) to a .webp image with a width of 200 pixels, height of 150 pixels, and quality of 85% (quality includes comprehensive indicators such as image definition) as follows:
- // It needs to be replaced with the image resource address required by the developer.
- private imgUrl = 'https://******.com/path/to/image.jpg?w=200&h=150&fit=cover&q=85&format=webp';
-
- build() {
- NavDestination() {
- Column() {
- Image(this.imgUrl)
- .width(200)
- .height(150)
- .objectFit(ImageFit.Cover)
- }
- .width('100%')
- .height('100%')
- }
- .backgroundColor('#F1F3F5')
- }
Not all CDN services support the same parameters. For more information, see the documents provided by your CDN service provider.
WebP supports both lossy and lossless compression. WebP images are smaller in size and can be transmitted at high quality, providing comprehensive functionalities and applicable to various scenarios.
Advantages | Description | Application Scenario |
|---|---|---|
Smaller file size, faster loading, and less bandwidth | WebP images are 25% to 35% smaller than JPG images and 25% smaller than PNG images of the same quality. | Website images |
Transparent channel supported | PNG images also support transparent channels, but WebP images are smaller. | UI icons, buttons, and transparent images |
Animation supported | WebP images can replace GIF images with higher quality and smaller size. | Stickers |
autoResize is applicable to scenarios where the component size needs to be dynamically adapted. For example, when the page content changes or the device form (such as different screen sizes and the unfolded/collapsed state of a foldable screen) is different, the image needs to be automatically resized based on the size of the parent container. In this case, autoResize can be used to avoid image overflow or blank space, improving the UI adaptation capability. When autoResize is set to true for the Image component, the component determines the size of the image source used for drawing based on the size of the display area, which reduces the memory usage.
- Image(this.imageUrl)
- .width(300)
- .height(200)
- .autoResize(true)
The optimization policy varies depending on whether the image is preset (that is, packed in the app). For preset images, you are advised to use the texture compression technology. For non-preset images before use, you can compress them to the actual UI size, optimize network images, compress GIF images, and preferentially use WebP images. For non-preset images in use, you can use autoResize to optimize them. You need to select a proper solution or solution combination to optimize the image performance based on the actual situation.