纹理Texture

纹理Texture可以理解为GPU内代表图像数据的一个对象

Flutter展示Native端大数据:外接纹理

背景

问:在Flutter与原生的混合开发中,资源在Native和Flutter重复加载,导致内存占了双份的性能问题怎么解决?

答:用Texture外接纹理的方式缓解内存压力。

Flutter 多引擎渲染,外接纹理实践

二、外接纹理

三、共享纹理

ShareGroup是OpenGL ES中的一个概念,用于在不同的EAGLContext之间共享纹理和其他资源。即在Flutter和iOS之间实现纹理共享,可以通过使用ShareGroup来实现。(在iOS开发中,ShareGroup对应于EAGLSharegroup,而在Flutter中,可以通过Texture控件来使用共享的纹理 。)

使用ShareGroup实现Flutter和iOS原生纹理共享的基本步骤:

1
2
3
4
5
6
7
8
9
10
11
12
// 1、创建一个 EAGLContext 并设置其 sharegroup,这个 sharegroup 将被用于后续创建共享纹理。
EAGLSharegroup *sharegroup = [[EAGLSharegroup alloc] init];
EAGLContext *sharedContext = [[EAGLContext alloc] initWithAPI:kEAGLRenderingAPIOpenGLES3 sharegroup:sharegroup];

// 2、创建纹理并设置为共享:使用上述创建的 EAGLContext 来生成纹理,并确保这些纹理可以被共享。
// 创建纹理,配置纹理参数(省略具体参数设置)
GLuint textureID;
glGenTextures(1, &textureID);
glBindTexture(GL_TEXTURE_2D, textureID);
.......
// 确保纹理可以被共享
[sharedContext presentRenderbuffer:GL_RENDERBUFFER];
1
2
3
4
5
6
7
8
9
10
11
12
// 在 Flutter 中使用
import 'package:flutter/widgets.dart';

class SharedTextureWidget extends StatelessWidget {
SharedTextureWidget({required this.textureId});

@override
Widget build(BuildContext context) {
int textureId = getNativeTextureId(); // 调用原生方法获取纹理ID
return Texture(textureId: textureId);
}
}
  1. 配置Flutter的Texture控件:在Flutter代码中,创建一个Texture控件,并通过PlatformView注册一个视图工厂,该工厂将返回一个实现了FlutterTexture协议的对象。这个对象负责管理原生纹理,并实现copyPixelBuffer方法来提供纹理数据给

以下内容摘自:谈一谈Flutter外接纹理

1 背景知识

当我们用flutter做实时视频渲染时,往往是要对视频或者相机画面做滤镜处理的,如图:

img

如果我们要用flutter定义的消息通道机制来实现这个功能,就需要将摄像头采集的每一帧图片都要从原生传递到flutter中,这样做代价将会非常大,因为将图像或视频数据通过消息通道实时传输必然会引起内存和CPU的巨大消耗。为此,flutter提供了两种机制实现这一功能:

  • PlatformView
  • Texture Widget

PlatformView实质上是将原有的NativeView嵌入到Flutter中显示,虽然使用和移植很简单,但并不是性能最优的做法。

Texture Widget是flutter提供的另一种机制,可以将native纹理共享给flutter进行渲染。但由于native纹理与flutter是两个OpenGL Context,如果直接使用的话,需要经过GPU -> CPU -> GPU的转换开销,这对于实时视频渲染是很难令人接受的。

所以解决方案就是共享纹理

一个方案提升Flutter内存利用率(干货)